1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34 package info.magnolia.module.admininterface;
35
36 import info.magnolia.cms.beans.runtime.MultipartForm;
37 import info.magnolia.cms.core.Content;
38 import info.magnolia.cms.core.HierarchyManager;
39 import info.magnolia.cms.core.ItemType;
40 import info.magnolia.cms.gui.dialog.Dialog;
41 import info.magnolia.cms.gui.dialog.DialogControlImpl;
42 import info.magnolia.cms.gui.dialog.DialogFactory;
43 import info.magnolia.cms.gui.i18n.I18nAuthoringSupport;
44 import info.magnolia.cms.gui.misc.Sources;
45 import info.magnolia.cms.i18n.Messages;
46 import info.magnolia.cms.i18n.MessagesManager;
47 import info.magnolia.cms.security.AccessDeniedException;
48 import info.magnolia.cms.servlets.MVCServletHandlerImpl;
49 import info.magnolia.cms.util.ExclusiveWrite;
50 import info.magnolia.cms.util.NodeDataUtil;
51 import info.magnolia.cms.util.RequestFormUtil;
52 import info.magnolia.context.MgnlContext;
53 import info.magnolia.objectfactory.Classes;
54 import info.magnolia.objectfactory.Components;
55 import info.magnolia.objectfactory.MgnlInstantiationException;
56 import info.magnolia.repository.RepositoryConstants;
57
58 import java.io.IOException;
59 import java.io.PrintWriter;
60
61 import javax.jcr.RepositoryException;
62 import javax.servlet.http.HttpServletRequest;
63 import javax.servlet.http.HttpServletResponse;
64 import javax.servlet.http.HttpSession;
65
66 import org.apache.commons.lang.StringUtils;
67 import org.slf4j.Logger;
68 import org.slf4j.LoggerFactory;
69
70
71
72
73
74
75
76
77 public class DialogMVCHandler extends MVCServletHandlerImpl {
78
79
80
81
82 private static Logger log = LoggerFactory.getLogger(DialogMVCHandler.class);
83
84
85
86
87 protected static final String COMMAND_SAVE = "save";
88
89 protected static final String COMMAND_SELECT_PARAGRAPH = "selectParagraph";
90
91 protected static final String COMMAND_SHOW_DIALOG = "showDialog";
92
93
94
95
96 protected static final String VIEW_CLOSE_WINDOW = "close";
97
98 protected static final String VIEW_SHOW_DIALOG = "show";
99
100
101
102
103 protected MultipartForm form;
104
105
106
107
108 protected String path = StringUtils.EMPTY;
109
110
111
112
113 private String nodeCollectionName = StringUtils.EMPTY;
114
115
116
117
118 protected String nodeName = StringUtils.EMPTY;
119
120 protected String richE = StringUtils.EMPTY;
121
122 protected String richEPaste = StringUtils.EMPTY;
123
124 protected String repository = StringUtils.EMPTY;
125
126 protected String locale;
127
128 protected HierarchyManager hm;
129
130 private Dialog dialog;
131
132 protected Messages msgs;
133
134 protected RequestFormUtil params;
135
136 protected Content storageNode;
137
138 private SaveHandler saveHandler;
139
140 private String jsExecutedAfterSaving;
141
142 private String itemType;
143
144 private final I18nAuthoringSupport i18nAuthoringSupport;
145
146 protected String treeBasePath;
147
148
149
150
151
152
153 public DialogMVCHandler(String name, HttpServletRequest request, HttpServletResponse response) {
154 super(name, request, response);
155
156 form = MgnlContext.getPostedForm();
157 if(form != null || request != null){
158 params = new RequestFormUtil(request, form);
159
160 path = params.getParameter("mgnlPath");
161 nodeCollectionName = params.getParameter("mgnlNodeCollection");
162 nodeName = params.getParameter("mgnlNode");
163 richE = params.getParameter("mgnlRichE");
164 richEPaste = params.getParameter("mgnlRichEPaste");
165 repository = params.getParameter("mgnlRepository", getRepository());
166 locale = params.getParameter("mgnlLocale");
167 treeBasePath = params.getParameter("mgnlTreeBasePath");
168 if (StringUtils.isNotEmpty(repository)) {
169 hm = MgnlContext.getHierarchyManager(repository);
170 }
171 }
172 msgs = MessagesManager.getMessages();
173
174 i18nAuthoringSupport = I18nAuthoringSupport.Factory.getInstance();
175
176 }
177
178
179
180
181 @Override
182 public String getCommand() {
183 if (form != null) {
184 return COMMAND_SAVE;
185 }
186 return COMMAND_SHOW_DIALOG;
187 }
188
189
190
191
192 public String showDialog() {
193 return VIEW_SHOW_DIALOG;
194 }
195
196 protected void configureDialog(Dialog dialog) {
197 dialog.setConfig("dialog", getName());
198 dialog.setConfig("path", path);
199 dialog.setConfig("nodeCollection", nodeCollectionName);
200 dialog.setConfig("node", nodeName);
201 dialog.setConfig("richE", richE);
202 dialog.setConfig("richEPaste", richEPaste);
203 dialog.setConfig("repository", repository);
204 dialog.setConfig("mgnlTreeBasePath", treeBasePath);
205 if (StringUtils.isNotEmpty(locale)) {
206 dialog.setConfig("locale", locale);
207 }
208
209 i18nAuthoringSupport.i18nIze(dialog);
210 }
211
212
213
214
215
216
217
218 protected Dialog createDialog(Content configNode, Content storageNode) throws RepositoryException {
219 return DialogFactory.getDialogInstance(this.getRequest(), this.getResponse(), storageNode, configNode);
220 }
221
222
223
224
225
226
227
228 public String save() {
229 if (!validate()) {
230 return onValidationFailed();
231 }
232 SaveHandler saveHandler = getSaveHandler();
233 if (!onPreSave(saveHandler)) {
234 return onSaveFailed();
235 }
236 if (!onSave(saveHandler)) {
237 return onSaveFailed();
238 }
239 synchronized (ExclusiveWrite.getInstance()) {
240 if (!onPostSave(saveHandler)) {
241 return onSaveFailed();
242 }
243 }
244 removeSessionAttributes();
245 return VIEW_CLOSE_WINDOW;
246 }
247
248 private String onValidationFailed() {
249 return showDialog();
250 }
251
252 protected boolean validate() {
253 boolean passed = this.getDialog().validate();
254
255 SaveHandler saveHandler = this.getSaveHandler();
256 if ((passed) && (saveHandler instanceof ValidatingSaveHandler)) {
257 passed = ((ValidatingSaveHandler) saveHandler).validate();
258 }
259
260 if (!passed) {
261
262 if (StringUtils.isEmpty(this.dialog.getConfigValue("paragraph"))) {
263
264 String paragraphName = params.getParameter("mgnlParagraph");
265 this.dialog.setConfig("paragraph", paragraphName);
266 }
267 if (StringUtils.isEmpty(this.dialog.getConfigValue("collectionNodeCreationItemType"))) {
268 this.dialog.setConfig("collectionNodeCreationItemType", params.getParameter("mgnlCollectionNodeCreationItemType"));
269 }
270 if (StringUtils.isEmpty(this.dialog.getConfigValue("creationItemType"))) {
271 this.dialog.setConfig("creationItemType", params.getParameter("mgnlCreationItemType"));
272 }
273 }
274
275 return passed;
276 }
277
278
279
280
281 protected String onSaveFailed() {
282 return showDialog();
283 }
284
285
286
287
288
289 protected SaveHandler getSaveHandler() {
290 if (this.saveHandler == null) {
291 createSaveHandler();
292
293 configureSaveHandler(this.saveHandler);
294 }
295 return this.saveHandler;
296 }
297
298
299
300
301
302 protected void createSaveHandler() {
303 Content configNode = this.getConfigNode();
304 if (configNode != null) {
305 String className = NodeDataUtil.getString(configNode, "saveHandler");
306 if (StringUtils.isNotEmpty(className)) {
307 try {
308 this.saveHandler = Classes.newInstance(className);
309 }
310 catch (MgnlInstantiationException e) {
311 log.error("can't create save handler", e);
312 }
313 catch (ClassNotFoundException e) {
314 log.error("can't create save handler", e);
315 }
316 }
317 }
318
319 if (this.saveHandler == null) {
320 this.saveHandler = Components.getComponentProvider().newInstance(SaveHandler.class);
321 }
322 }
323
324
325
326
327 protected void configureSaveHandler(SaveHandler saveHandler) {
328 saveHandler.init(form);
329
330 saveHandler.setPath(form.getParameter("mgnlPath"));
331 saveHandler.setNodeCollectionName(form.getParameter("mgnlNodeCollection"));
332 saveHandler.setNodeName(form.getParameter("mgnlNode"));
333 saveHandler.setParagraph(form.getParameter("mgnlParagraph"));
334 saveHandler.setRepository(form.getParameter("mgnlRepository"));
335 if (StringUtils.isNotEmpty(form.getParameter("mgnlCollectionNodeCreationItemType"))) {
336 saveHandler.setCollectionNodeCreationItemType(new ItemType(form.getParameter("mgnlCollectionNodeCreationItemType")));
337 }
338 if (StringUtils.isNotEmpty(getItemType())) {
339 saveHandler.setCreationItemType(new ItemType(getItemType()));
340 } else if (StringUtils.isNotEmpty(form.getParameter("mgnlCreationItemType"))) {
341 saveHandler.setCreationItemType(new ItemType(form.getParameter("mgnlCreationItemType")));
342 }
343
344 if (this.saveHandler instanceof DialogAwareSaveHandler) {
345 ((DialogAwareSaveHandler) saveHandler).setDialog(this.getDialog());
346 }
347 }
348
349 protected boolean onPreSave(SaveHandler control) {
350 return true;
351 }
352
353 protected boolean onSave(SaveHandler control) {
354 boolean result = control.save();
355 if (result) {
356 this.nodeName = control.getNodeName();
357 }
358 return result;
359 }
360
361 protected boolean onPostSave(SaveHandler control) {
362 return true;
363 }
364
365
366
367
368
369 public Content getStorageNode() {
370
371 if (storageNode == null && hm != null) {
372 try {
373 if(this.path == null){
374 log.debug("No path defined for a dialog called by the url [{}]", this.getRequest().getRequestURL());
375 return null;
376 }
377 Content parentContent = hm.getContent(path);
378 if (StringUtils.isEmpty(nodeName)) {
379 if (StringUtils.isEmpty(nodeCollectionName)) {
380 storageNode = parentContent;
381 }
382 else {
383 storageNode = parentContent.getContent(nodeCollectionName);
384 }
385 }
386 else {
387 if (StringUtils.isEmpty(nodeCollectionName)) {
388 storageNode = parentContent.getContent(nodeName);
389
390 }
391 else {
392 storageNode = parentContent.getContent(nodeCollectionName).getContent(nodeName);
393
394 }
395 }
396 }
397 catch(AccessDeniedException ade){
398 log.error("can't read content to edit", ade);
399 }
400 catch (RepositoryException re) {
401
402 log.debug("can't read content or it does not exist yet", re);
403 }
404 }
405 return storageNode;
406 }
407
408
409
410
411 public Content getConfigNode() {
412 return null;
413 }
414
415
416
417
418 @Override
419 public void renderHtml(String view) throws IOException {
420 PrintWriter out = this.getResponse().getWriter();
421
422
423 if (VIEW_CLOSE_WINDOW.equals(view)) {
424
425 out.write("<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Strict//EN\" ");
426 out.write(" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd\">\n");
427 out.println("<html>");
428 out.println(new Sources(this.getRequest().getContextPath()).getHtmlJs());
429 out.println("<script type=\"text/javascript\">");
430 out.println("var path = '" + this.path + "'");
431 out.println(StringUtils.defaultIfEmpty(getJsExecutedAfterSaving(), "mgnlDialogReloadOpener();"));
432 out.println("window.close();");
433 out.println("</script></html>");
434 }
435
436 else if (VIEW_SHOW_DIALOG.equals(view)) {
437 try {
438 getDialog().drawHtml(out);
439 }
440 catch (IOException e) {
441 log.error("Exception caught", e);
442 }
443 }
444 }
445
446
447
448
449 public String getRepository() {
450 return RepositoryConstants.WEBSITE;
451 }
452
453 public void removeSessionAttributes() {
454 String[] toRemove = form.getParameterValues(DialogControlImpl.SESSION_ATTRIBUTENAME_DIALOGOBJECT_REMOVE);
455 if (toRemove != null) {
456 for (int i = 0; i < toRemove.length; i++) {
457 HttpSession httpsession = this.getRequest().getSession(false);
458 if (httpsession != null) {
459 httpsession.removeAttribute(toRemove[i]);
460 }
461 }
462 }
463 }
464
465
466
467
468 public void setDialog(Dialog dialog) {
469 this.dialog = dialog;
470 }
471
472
473
474
475 public Dialog getDialog() {
476 if (this.dialog == null) {
477 try {
478 this.dialog = createDialog(this.getConfigNode(), this.getStorageNode());
479 }
480 catch (RepositoryException e) {
481 log.error("can't create dialog", e);
482 }
483 configureDialog(this.dialog);
484 }
485 return this.dialog;
486 }
487
488
489 public String getJsExecutedAfterSaving() {
490 return this.jsExecutedAfterSaving;
491 }
492
493
494 public void setJsExecutedAfterSaving(String jsExecutedAfterSaving) {
495 this.jsExecutedAfterSaving = jsExecutedAfterSaving;
496 }
497
498
499 public String getItemType() {
500 return this.itemType;
501 }
502
503
504 public void setItemType(String itemType) {
505 this.itemType = itemType;
506 }
507 }