View Javadoc

1   /*
2    * Licensed to the Apache Software Foundation (ASF) under one or more
3    * contributor license agreements.  See the NOTICE file distributed with
4    * this work for additional information regarding copyright ownership.
5    * The ASF licenses this file to You under the Apache License, Version 2.0
6    * (the "License"); you may not use this file except in compliance with
7    * the License.  You may obtain a copy of the License at
8    * 
9    *      http://www.apache.org/licenses/LICENSE-2.0
10   * 
11   * Unless required by applicable law or agreed to in writing, software
12   * distributed under the License is distributed on an "AS IS" BASIS,
13   * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14   * See the License for the specific language governing permissions and
15   * limitations under the License.
16   */
17  package org.apache.jetspeed.portlets.layout;
18  
19  import java.io.IOException;
20  import java.io.UnsupportedEncodingException;
21  import java.net.URLEncoder;
22  import java.util.ArrayList;
23  import java.util.Iterator;
24  import java.util.List;
25  import java.util.StringTokenizer;
26  
27  import javax.portlet.ActionRequest;
28  import javax.portlet.ActionResponse;
29  import javax.portlet.PortletConfig;
30  import javax.portlet.PortletException;
31  import javax.portlet.PortletMode;
32  import javax.portlet.RenderRequest;
33  import javax.portlet.RenderResponse;
34  
35  import org.apache.commons.logging.Log;
36  import org.apache.commons.logging.LogFactory;
37  import org.apache.jetspeed.CommonPortletServices;
38  import org.apache.jetspeed.PortalReservedParameters;
39  import org.apache.jetspeed.cache.JetspeedContentCache;
40  import org.apache.jetspeed.decoration.DecorationFactory;
41  import org.apache.jetspeed.decoration.PageEditAccess;
42  import org.apache.jetspeed.desktop.JetspeedDesktop;
43  import org.apache.jetspeed.om.folder.Folder;
44  import org.apache.jetspeed.om.page.ContentFragment;
45  import org.apache.jetspeed.om.page.ContentPage;
46  import org.apache.jetspeed.om.page.Fragment;
47  import org.apache.jetspeed.om.page.Page;
48  import org.apache.jetspeed.page.FolderNotUpdatedException;
49  import org.apache.jetspeed.page.document.NodeException;
50  import org.apache.jetspeed.request.RequestContext;
51  import org.apache.pluto.om.window.PortletWindow;
52  
53  /***
54   */
55  public class MultiColumnPortlet extends LayoutPortlet
56  {
57      /*** Commons logging */
58      protected final static Log log = LogFactory.getLog(MultiColumnPortlet.class);
59  
60      protected final static String PARAM_NUM_COLUMN = "columns";
61      protected final static int DEFAULT_NUM_COLUMN = 2;
62      protected final static String PARAM_COLUMN_SIZES = "sizes";
63      protected final static String DEFAULT_ONE_COLUMN_SIZES = "100%";
64      protected final static String DEFAULT_TWO_COLUMN_SIZES = "50%,50%";
65      protected final static String DEFAULT_THREE_COLUMN_SIZES = "34%,33%,33%";
66  
67      private int numColumns = 0;
68      private String columnSizes = null;
69      private String portletName = null;
70      private String layoutType;
71      private String editorType = null;
72      protected DecorationFactory decorators;
73      protected JetspeedDesktop desktop;
74      protected JetspeedContentCache decoratorCache;
75  
76      public void init( PortletConfig config ) throws PortletException
77      {
78          super.init(config);
79          this.portletName = config.getPortletName();
80          this.layoutType = config.getInitParameter("layoutType");
81          this.editorType = config.getInitParameter("editorType");
82          if (this.layoutType == null)
83          {
84              throw new PortletException("Layout type not specified for " + this.portletName);
85          }
86          this.numColumns = Integer.parseInt(config.getInitParameter(PARAM_NUM_COLUMN));
87          if (this.numColumns < 1)
88          {
89              this.numColumns = 1;
90          }
91          this.columnSizes = config.getInitParameter(PARAM_COLUMN_SIZES);
92          if ((this.columnSizes == null) || (this.columnSizes.trim().length() == 0))
93          {
94              switch (this.numColumns)
95              {
96              case 1: this.columnSizes = DEFAULT_ONE_COLUMN_SIZES; break;
97              case 2: this.columnSizes = DEFAULT_TWO_COLUMN_SIZES; break;
98              case 3: this.columnSizes = DEFAULT_THREE_COLUMN_SIZES; break;
99              default: this.columnSizes = null; break;
100             }
101         }
102         if (this.columnSizes == null)
103         {
104             throw new PortletException("Column sizes cannot be defaulted for " + this.numColumns + " columns and are not specified for " + this.portletName);
105         }
106        
107         this.decorators = (DecorationFactory)getPortletContext().getAttribute(CommonPortletServices.CPS_DECORATION_FACTORY);
108         if (null == this.decorators)
109         {
110             throw new PortletException("Failed to find the Decoration Factory on portlet initialization");
111         }
112         
113         this.desktop = (JetspeedDesktop)getPortletContext().getAttribute(CommonPortletServices.CPS_DESKTOP);
114         
115         this.decoratorCache = (JetspeedContentCache)getPortletContext().getAttribute(CommonPortletServices.CPS_DECORATOR_CACHE);
116     }
117 
118     public void doView( RenderRequest request, RenderResponse response ) throws PortletException, IOException
119     {
120         RequestContext context = getRequestContext(request);
121 
122         ContentPage requestPage = context.getPage();       
123         PageEditAccess pageEditAccess = (PageEditAccess)context.getAttribute(PortalReservedParameters.PAGE_EDIT_ACCESS_ATTRIBUTE);
124         if ( requestPage == null || pageEditAccess == null )
125         {
126             // Targetting this portlet REQUIRES that the ProfilerValve has been invoked!
127             throw new PortletException("Current request page or PageEditAccess not available.");
128         }
129         
130         Boolean editing = ( pageEditAccess.isEditing() && 
131                             PortletMode.VIEW.equals(request.getPortletMode()) && 
132                             request.isPortletModeAllowed(PortletMode.EDIT))
133                           ? Boolean.TRUE : Boolean.FALSE;
134                                          
135         PortletWindow window = context.getPortalURL().getNavigationalState().getMaximizedWindow();
136         if (window != null)
137         {
138             super.doView(request, response);
139             return;
140         }
141         
142         // get fragment column sizes
143         Fragment f = getFragment(request, false);
144         String fragmentColumnSizes = columnSizes;
145         String fragmentColumnSizesProperty = f.getProperty(Fragment.SIZES_PROPERTY_NAME);
146         if (fragmentColumnSizesProperty != null)
147         {
148             fragmentColumnSizes = fragmentColumnSizesProperty;
149         }
150         String [] fragmentColumnSizesArray = fragmentColumnSizes.split("//,");
151         List fragmentColumnSizesList = new ArrayList(fragmentColumnSizesArray.length);
152         for (int i = 0; (i < fragmentColumnSizesArray.length); i++)
153         {
154             fragmentColumnSizesList.add(fragmentColumnSizesArray[i]);
155         }
156 
157         // construct layout object
158         ColumnLayout layout;
159         try
160         {
161             layout = new ColumnLayout(numColumns, layoutType, f.getFragments(), fragmentColumnSizesArray);
162             layout.addLayoutEventListener(new PageManagerLayoutEventListener(pageManager, context.getPage(), layoutType));
163         }
164         catch (LayoutEventException e1)
165         {
166             throw new PortletException("Failed to build ColumnLayout "+e1.getMessage(), e1);
167         }
168 
169         // invoke the JSP associated with this portlet
170         request.setAttribute("columnLayout", layout);
171         request.setAttribute("numberOfColumns", new Integer(numColumns));
172         request.setAttribute("decorationFactory", this.decorators);
173         request.setAttribute("columnSizes", fragmentColumnSizesList);
174         request.setAttribute("editing",editing);
175         request.setAttribute("fragmentNestingLevel",new Integer(getFragmentNestingLevel(requestPage,f.getId())));
176         super.doView(request, response);
177         request.removeAttribute("decorationFactory");
178         request.removeAttribute("columnLayout");
179         request.removeAttribute("numberOfColumns");
180         request.removeAttribute("columnSizes");
181         request.removeAttribute("editing");
182         request.removeAttribute(("fragmentNestingLevel"));
183     }
184 
185     public void processAction(ActionRequest request, ActionResponse response) throws PortletException, IOException
186     {
187         RequestContext requestContext = (RequestContext)request.getAttribute(PortalReservedParameters.REQUEST_CONTEXT_ATTRIBUTE);
188         
189         ContentPage requestPage = requestContext.getPage();       
190         PageEditAccess pageEditAccess = (PageEditAccess)requestContext.getAttribute(PortalReservedParameters.PAGE_EDIT_ACCESS_ATTRIBUTE);
191         if ( requestPage == null || pageEditAccess == null )
192         {
193             // Targetting this portlet with an ActionRequest REQUIRES that the ProfilerValve has been invoked!
194             throw new PortletException("Current request page or PageEditAccess not available.");
195         }
196 
197         decoratorCache.invalidate(requestContext);
198         
199         String pageMode = request.getParameter("pageMode");
200         if ( pageMode != null )
201         {
202             if ( "view".equals(pageMode) )
203             {
204                 pageEditAccess.setEditing(false);
205             }
206             else if ( "edit".equals(pageMode) && pageEditAccess.isEditAllowed() )
207             {
208                 if ( this.editorType != null && this.editorType.equals( "desktop" ) )
209                 {
210                     String redirectUrl = this.desktop.getPortalUrl( requestContext, requestContext.getPath() );
211                     redirectUrl += "?editPage=true&portal=true";
212                     response.sendRedirect( redirectUrl );
213                 }
214                 else
215                 {
216                     pageEditAccess.setEditing(true);
217                 }
218             }
219             return;
220         }
221         
222         if ( pageEditAccess.isEditAllowed() && request.isPortletModeAllowed(PortletMode.EDIT) )
223         {
224             String layout = null;
225             
226             boolean addLayout = request.getParameter("jsAddLayout") != null;
227             if ( addLayout || request.getParameter("jsChangeLayout") != null )
228             {
229                 layout = request.getParameter("layout");
230                 if ( layout != null && layout.length() > 0 )
231                 {
232                     PortletWindow window = requestContext.getActionWindow();
233                     ContentFragment targetFragment = requestPage.getContentFragmentById(window.getId().toString());
234                     
235                     if ( targetFragment == null )
236                     {
237                         // ignore no longer consistent page definition
238                         return;
239                     }
240                     
241                     if ( addLayout )
242                     {
243                         try
244                         {
245                             Fragment fragment = pageManager.newFragment();
246                             fragment.setType(Fragment.LAYOUT);
247                             fragment.setName(layout);
248                             
249                             targetFragment.getFragments().add(fragment);
250                             pageManager.updatePage(requestPage);            
251                         }
252                         catch (Exception e)
253                         {
254                             throw new PortletException("failed to add portlet " + layout + " to page: " + requestPage+": "+e.getMessage(), e);
255                         }
256                     }
257                     else if ( !layout.equals(targetFragment.getName()) )
258                     {
259                         try
260                         {
261                             // layout portlet change
262                             targetFragment.setName(layout);
263                             pageManager.updatePage(requestPage);
264                             entityAccess.updatePortletEntity(window.getPortletEntity(), targetFragment);
265                             entityAccess.storePortletEntity(window.getPortletEntity());
266 
267                             windowAccess.createPortletWindow(window.getPortletEntity(), targetFragment.getId());
268                             return;
269                         }
270                         catch (Exception e)
271                         {
272                             throw new PortletException("Unable to update page: "+e.getMessage(), e);
273                         }
274                     }
275                 }
276                 return;
277             }
278 
279             if ( request.getParameter("jsSubmitPage" ) != null )
280             {
281                 String jsPageName = request.getParameter("jsPageName");
282                 String jsPageTitle = request.getParameter("jsPageTitle");
283                 String jsPageShortTitle = request.getParameter("jsPageShortTitle");
284                 if ( jsPageName != null && jsPageName.length() > 0 && jsPageName.indexOf(Folder.PATH_SEPARATOR) == -1 )
285                 {
286                     try
287                     {                
288                         Folder parent = (Folder)requestPage.getParent();
289                         if (parent != null)
290                         {
291                             String path = parent.getPath();
292                             if (path.endsWith(Folder.PATH_SEPARATOR))
293                             {
294                                 path = path + getEscapedName(jsPageName);
295                             }
296                             else
297                             {
298                                 path = path + Folder.PATH_SEPARATOR
299                                         + getEscapedName(jsPageName);
300                             }
301                             Page page = pageManager.newPage(path);
302                             if ( layout == null || layout.length() == 0 )
303                             {
304                                 layout = requestPage.getRootFragment().getName();
305                             }
306                             page.getRootFragment().setName(layout);
307                             page.setDefaultDecorator(requestPage.getDefaultDecorator(Fragment.LAYOUT), Fragment.LAYOUT);
308                             page.setDefaultDecorator(requestPage.getDefaultDecorator(Fragment.PORTLET), Fragment.PORTLET);
309                             page.setTitle(jsPageTitle != null && !jsPageTitle.equals("") ? jsPageTitle : jsPageName);
310                             page.setShortTitle(jsPageShortTitle != null
311                                             && !jsPageShortTitle.equals("") ? jsPageShortTitle
312                                             : jsPageName);
313                             pageManager.updatePage(page);
314 
315                             List orderList = parent.getDocumentOrder();
316                             if (orderList != null)
317                             {
318                                 String name = page.getName();
319                                 if (orderList.indexOf(name) < 0)
320                                 {
321                                     orderList.add(name);
322                                     parent.setDocumentOrder(orderList);
323                                     pageManager.updateFolder(parent);
324                                 }
325                             }
326                         }
327                     }
328                     catch (Exception e)
329                     {
330                         throw new PortletException("Unable to access page for editing: "+e.getMessage(), e);
331                     }                        
332                 }
333                 return;
334             }
335 
336             if (request.getParameter("jsChangePageName") != null)
337             {
338                 String jsPageTitle = request.getParameter("jsPageTitle");
339                 String jsPageShortTitle = request
340                         .getParameter("jsPageShortTitle");
341                 try
342                 {
343                     if (jsPageTitle != null && !jsPageTitle.equals(""))
344                     {
345                         requestPage.setTitle(jsPageTitle);
346                     }
347                     if (jsPageShortTitle != null
348                             && !jsPageShortTitle.equals(""))
349                     {
350                         requestPage.setShortTitle(jsPageShortTitle);
351                     }
352                     pageManager.updatePage(requestPage);
353                 }
354                 catch (Exception e)
355                 {
356                     throw new PortletException(
357                             "Unable to access page for editing: "
358                                     + e.getMessage(), e);
359                 }
360                 return;
361             }
362 
363             if ( request.getParameter("jsDeletePage" ) != null )
364             {
365                 try
366                 {
367                     Folder parent = (Folder)requestPage.getParent();
368                     if (parent != null)
369                     {
370                         List orderList = parent.getDocumentOrder();
371                         if (orderList != null)
372                         {
373                             String name = requestPage.getName();
374                             if (orderList.indexOf(name) > -1)
375                             {
376                                 orderList.remove(name);
377                                 parent.setDocumentOrder(orderList);
378                                 pageManager.updateFolder(parent);
379                             }
380                         }
381                     }
382 
383                     pageManager.removePage(requestPage);
384                 }
385                 catch (Exception e)
386                 {
387                     throw new PortletException("Unable to access page for removing: "+e.getMessage(), e);
388                 }
389                 return;
390             }
391 
392             if (request.getParameter("jsMovePageLeft") != null)
393             {
394                 try
395                 {
396                     Folder parent = (Folder) requestPage.getParent();
397                     if (parent != null)
398                     {
399                         List orderList = parent.getDocumentOrder();
400                         String name = requestPage.getName();
401                         if (orderList != null)
402                         {
403                             int index = orderList.indexOf(name);
404                             if (index > -1)
405                             {
406                                 String type = requestPage.getType();
407                                 int i = index - 1;
408                                 while (i >= 0)
409                                 {
410                                     String value = (String) orderList.get(i);
411                                     if (value.endsWith(type))
412                                     {
413                                         orderList.remove(index);
414                                         orderList.add(i, name);
415                                         parent.setDocumentOrder(orderList);
416                                         pageManager.updateFolder(parent);
417                                         break;
418                                     }
419                                     i--;
420                                 }
421                             }
422                             else
423                             {
424                                 orderList.add(name);
425                                 parent.setDocumentOrder(orderList);
426                                 pageManager.updateFolder(parent);
427                             }
428                         }
429                         else
430                         {
431                             orderList = new ArrayList(4);
432                             orderList.add(name);
433                             parent.setDocumentOrder(orderList);
434                             pageManager.updateFolder(parent);
435                         }
436                     }
437                 }
438                 catch (Exception e)
439                 {
440                     throw new PortletException(
441                             "Unable to access page for changing the document order: "
442                                     + e.getMessage(), e);
443                 }
444                 return;
445             }
446 
447             if (request.getParameter("jsMovePageRight") != null)
448             {
449                 try
450                 {
451                     Folder parent = (Folder) requestPage.getParent();
452                     if (parent != null)
453                     {
454                         List orderList = parent.getDocumentOrder();
455                         String name = requestPage.getName();
456                         if (orderList != null)
457                         {
458                             int index = orderList.indexOf(name);
459                             if (index > -1)
460                             {
461                                 String type = requestPage.getType();
462                                 int i = index + 1;
463                                 while (i < orderList.size())
464                                 {
465                                     String value = (String) orderList.get(i);
466                                     if (value.endsWith(type))
467                                     {
468                                         orderList.remove(index);
469                                         orderList.add(i, name);
470                                         parent.setDocumentOrder(orderList);
471                                         pageManager.updateFolder(parent);
472                                         break;
473                                     }
474                                     i++;
475                                 }
476                             }
477                             else
478                             {
479                                 orderList.add(name);
480                                 parent.setDocumentOrder(orderList);
481                                 pageManager.updateFolder(parent);
482                             }
483                         }
484                         else
485                         {
486                             orderList = new ArrayList(4);
487                             orderList.add(name);
488                             parent.setDocumentOrder(orderList);
489                             pageManager.updateFolder(parent);
490                         }
491                     }
492                 }
493                 catch (Exception e)
494                 {
495                     throw new PortletException(
496                             "Unable to access page for changing the document order: "
497                                     + e.getMessage(), e);
498                 }
499                 return;
500             }            
501 
502             if (request.getParameter("jsSubmitFolder") != null)
503             {
504                 String jsFolderName = request.getParameter("jsFolderName");
505                 String jsFolderTitle = request.getParameter("jsFolderTitle");
506                 String jsFolderShortTitle = request.getParameter("jsFolderShortTitle");
507                 if (jsFolderName != null && jsFolderName.length() > 0
508                         && jsFolderName.indexOf(Folder.PATH_SEPARATOR) == -1)
509                 {
510                     try
511                     {
512                         Folder parent = (Folder) requestPage.getParent();
513                         if (parent != null)
514                         {
515                             String path = parent.getPath();
516                             if (path.endsWith(Folder.PATH_SEPARATOR))
517                             {
518                                 path = path + getEscapedName(jsFolderName);
519                             }
520                             else
521                             {
522                                 path = path + Folder.PATH_SEPARATOR
523                                         + getEscapedName(jsFolderName);
524                             }
525                             Folder folder = pageManager.newFolder(path);
526                             if (layout == null || layout.length() == 0)
527                             {
528                                 layout = requestPage.getRootFragment()
529                                         .getName();
530                             }
531                             folder.setDefaultDecorator(requestPage
532                                     .getDefaultDecorator(Fragment.LAYOUT),
533                                     Fragment.LAYOUT);
534                             folder.setDefaultDecorator(requestPage
535                                     .getDefaultDecorator(Fragment.PORTLET),
536                                     Fragment.PORTLET);
537                             folder
538                                     .setTitle(jsFolderTitle != null
539                                             && !jsFolderTitle.equals("") ? jsFolderTitle
540                                             : jsFolderName);
541                             folder
542                                     .setShortTitle(jsFolderShortTitle != null
543                                             && !jsFolderShortTitle.equals("") ? jsFolderShortTitle
544                                             : jsFolderName);
545                             pageManager.updateFolder(folder);
546 
547                             List orderList = parent.getDocumentOrder();
548                             if (orderList != null)
549                             {
550                                 String name = folder.getName();
551                                 if (orderList.indexOf(name) < 0)
552                                 {
553                                     orderList.add(name);
554                                     parent.setDocumentOrder(orderList);
555                                     pageManager.updateFolder(parent);
556                                 }
557                             }
558 
559                             // add default page
560                             path = folder.getPath();
561                             if (path.endsWith(Folder.PATH_SEPARATOR))
562                             {
563                                 path = path + getEscapedName("default-page");
564                             }
565                             else
566                             {
567                                 path = path + Folder.PATH_SEPARATOR
568                                         + getEscapedName("default-page");
569                             }
570                             Page page = pageManager.newPage(path);
571                             if (layout == null || layout.length() == 0)
572                             {
573                                 layout = requestPage.getRootFragment()
574                                         .getName();
575                             }
576                             page.getRootFragment().setName(layout);
577                             page.setDefaultDecorator(requestPage
578                                     .getDefaultDecorator(Fragment.LAYOUT),
579                                     Fragment.LAYOUT);
580                             page.setDefaultDecorator(requestPage
581                                     .getDefaultDecorator(Fragment.PORTLET),
582                                     Fragment.PORTLET);
583                             page.setTitle(jsFolderName);
584                             pageManager.updatePage(page);
585 
586                             orderList = folder.getDocumentOrder();
587                             if (orderList != null)
588                             {
589                                 String name = page.getName();
590                                 if (orderList.indexOf(name) < 0)
591                                 {
592                                     orderList.add(name);
593                                     folder.setDocumentOrder(orderList);
594                                     pageManager.updateFolder(folder);
595                                 }
596                             }
597                         }
598                     }
599                     catch (Exception e)
600                     {
601                         throw new PortletException(
602                                 "Unable to access folder for editing: "
603                                         + e.getMessage(), e);
604                     }
605                 }
606                 return;
607             }
608 
609             if (request.getParameter("jsChangeFolderName") != null)
610             {
611                 String jsFolderTitle = request.getParameter("jsFolderTitle");
612                 String jsFolderShortTitle = request
613                         .getParameter("jsFolderShortTitle");
614                 try
615                 {
616                     Folder parent = (Folder) requestPage.getParent();
617                     if (parent != null)
618                     {
619                         if (jsFolderTitle != null && !jsFolderTitle.equals(""))
620                         {
621                             parent.setTitle(jsFolderTitle);
622                         }
623                         if (jsFolderShortTitle != null
624                                 && !jsFolderShortTitle.equals(""))
625                         {
626                             parent.setShortTitle(jsFolderShortTitle);
627                         }
628                         pageManager.updateFolder(parent);
629                     }
630 
631                 }
632                 catch (Exception e)
633                 {
634                     throw new PortletException(
635                             "Unable to access folder for editing: "
636                                     + e.getMessage(), e);
637                 }
638                 return;
639             }
640             
641             if (request.getParameter("jsDeleteFolder") != null)
642             {
643                 try
644                 {
645                     Folder targetFolder = (Folder) requestPage.getParent();
646                     Folder parent = (Folder) targetFolder.getParent();
647                     if (parent != null)
648                     {
649                         List orderList = parent.getDocumentOrder();
650                         if (orderList != null)
651                         {
652                             String name = targetFolder.getName();
653                             if (orderList.indexOf(name) > -1)
654                             {
655                                 orderList.remove(name);
656                                 parent.setDocumentOrder(orderList);
657                                 pageManager.updateFolder(parent);
658                             }
659                         }
660 
661                         // do not remove if the folder is root.
662                         pageManager.removeFolder(targetFolder);
663                     }
664                 }
665                 catch (Exception e)
666                 {
667                     throw new PortletException(
668                             "Unable to access folder for removing: "
669                                     + e.getMessage(), e);
670                 }
671                 return;
672             }
673 
674             if (request.getParameter("jsMoveFolderLeft") != null)
675             {
676                 try
677                 {
678                     Folder targetFolder = (Folder) requestPage.getParent();
679                     Folder parent = (Folder) targetFolder.getParent();
680                     if (parent != null)
681                     {
682                         List orderList = parent.getDocumentOrder();
683                         String name = targetFolder.getName();
684                         if (orderList != null)
685                         {
686                             int index = orderList.indexOf(name);
687                             if (index > -1)
688                             {
689                                 int i = index - 1;
690                                 while (i >= 0)
691                                 {
692                                     String value = (String) orderList.get(i);
693                                     if (!value.endsWith(".psml")
694                                             && !value.endsWith(".link"))
695                                     {
696                                         orderList.remove(index);
697                                         orderList.add(i, name);
698                                         parent.setDocumentOrder(orderList);
699                                         pageManager.updateFolder(parent);
700                                         break;
701                                     }
702                                     i--;
703                                 }
704                             }
705                             else
706                             {
707                                 orderList.add(name);
708                                 parent.setDocumentOrder(orderList);
709                                 pageManager.updateFolder(parent);
710                             }
711                         }
712                         else
713                         {
714                             orderList = new ArrayList(4);
715                             orderList.add(name);
716                             parent.setDocumentOrder(orderList);
717                             pageManager.updateFolder(parent);
718                         }
719                     }
720                 }
721                 catch (Exception e)
722                 {
723                     throw new PortletException(
724                             "Unable to access folder for changing the document order: "
725                                     + e.getMessage(), e);
726                 }
727                 return;
728             }
729 
730             if (request.getParameter("jsMoveFolderRight") != null)
731             {
732                 try
733                 {
734                     Folder targetFolder = (Folder) requestPage.getParent();
735                     Folder parent = (Folder) targetFolder.getParent();
736                     if (parent != null)
737                     {
738                         List orderList = parent.getDocumentOrder();
739                         String name = targetFolder.getName();
740                         if (orderList != null)
741                         {
742                             int index = orderList.indexOf(name);
743                             if (index > -1)
744                             {
745                                 int i = index + 1;
746                                 while (i < orderList.size())
747                                 {
748                                     String value = (String) orderList.get(i);
749                                     if (!value.endsWith(".psml")
750                                             && !value.endsWith(".link"))
751                                     {
752                                         orderList.remove(index);
753                                         orderList.add(i, name);
754                                         parent.setDocumentOrder(orderList);
755                                         pageManager.updateFolder(parent);
756                                         break;
757                                     }
758                                     i++;
759                                 }
760                             }
761                             else
762                             {
763                                 orderList.add(name);
764                                 parent.setDocumentOrder(orderList);
765                                 pageManager.updateFolder(parent);
766                             }
767                         }
768                         else
769                         {
770                             orderList = new ArrayList(4);
771                             orderList.add(name);
772                             parent.setDocumentOrder(orderList);
773                             pageManager.updateFolder(parent);
774                         }
775                     }
776                 }
777                 catch (Exception e)
778                 {
779                     throw new PortletException(
780                             "Unable to access folder for changing the document order: "
781                                     + e.getMessage(), e);
782                 }
783                 return;
784             }
785 
786             String theme = request.getParameter("theme");
787             if ( theme != null && theme.length() > 0 && !theme.equals(requestPage.getDefaultDecorator(Fragment.LAYOUT)) )
788             {
789                 requestPage.setDefaultDecorator(theme, Fragment.LAYOUT);
790                 try
791                 {
792                     pageManager.updatePage(requestPage);
793                 }
794                 catch (Exception e)
795                 {
796                     throw new PortletException("Unable to update page: "+e.getMessage(), e);
797                 }
798                 return;
799             }
800             
801             String fragmentId = request.getParameter("fragment");
802             if ( fragmentId != null && fragmentId.length() > 0 )
803             {
804                 String move = request.getParameter("move");
805                 if ( move != null && move.length() > 0 )
806                 {
807                     int moveCode = Integer.parseInt(move);                    
808                     PortletWindow window = requestContext.getActionWindow();
809                     Fragment currentFragment = requestPage.getFragmentById(window.getId().toString());
810                     Fragment fragmentToMove = requestPage.getFragmentById(fragmentId);
811                     
812                     if ( currentFragment == null || fragmentToMove == null )
813                     {
814                         // ignore no longer consistent page definition
815                         return;
816                     }
817                     
818                     ColumnLayout columnLayout;
819                     try
820                     {
821                         columnLayout = new ColumnLayout(numColumns, layoutType, currentFragment.getFragments(), null);
822                         columnLayout.addLayoutEventListener(new PageManagerLayoutEventListener(pageManager, requestPage, layoutType));
823                     }
824                     catch (LayoutEventException e1)
825                     {
826                         throw new PortletException("Failed to build ColumnLayout "+e1.getMessage(), e1);
827                     }
828 
829                     try
830                     {                
831                         switch (moveCode)
832                         {
833                         case LayoutEvent.MOVED_UP:
834                             columnLayout.moveUp(fragmentToMove);
835                             break;
836                         case LayoutEvent.MOVED_DOWN:
837                             columnLayout.moveDown(fragmentToMove);
838                             break;
839                         case LayoutEvent.MOVED_RIGHT:
840                             columnLayout.moveRight(fragmentToMove);
841                             break;
842                         case LayoutEvent.MOVED_LEFT:
843                             columnLayout.moveLeft(fragmentToMove);
844                             break;
845                         default:
846                             throw new PortletException("Invalid movement code " + moveCode);
847                         }
848                        
849                     }
850                     catch (SecurityException se)
851                     {
852                         // ignore page security constraint violations, only
853                         // permitted users can edit managed pages; page
854                         // update will remain transient
855                         log.info("Unable to update page " + requestPage.getId() + " layout due to security permission/constraint.", se);
856                     }
857                     catch (Exception e)
858                     {
859                         if (e instanceof PortletException)
860                         {
861                             throw (PortletException)e;
862                         }
863                         else
864                         {
865                             throw new PortletException("Unable to process layout for page " + requestPage.getId() + " layout: " + e.toString(), e);
866                         }
867                     }
868                     return;
869                 }
870                 
871                 String remove = request.getParameter("remove");
872                 if ( remove != null && remove.length() > 0 )
873                 {
874                     Page page = null;
875                     try
876                     {
877                         // TODO: for now retrieve the real Page instead of ContentPage
878                         //       because removing fragments isn't working through the ContentFragment wrapping
879                         page = pageManager.getPage(requestPage.getPath());
880                     }
881                     catch (Exception e)
882                     {
883                         throw new PortletException("Unable to retrieve page "+requestPage.getId(),e);
884                     }
885 
886                     PortletWindow window = requestContext.getActionWindow();
887                     Fragment currentFragment = page.getFragmentById(window.getId().toString());
888 
889                     if ( currentFragment == null )
890                     {
891                         // ignore no longer consistent page definition
892                         return;
893                     }
894                     
895                     removeFragment(page, currentFragment, fragmentId);
896                     return;
897                 }
898                 
899                 String decorator = request.getParameter("decorator");
900                 if ( decorator != null )
901                 {
902                     Fragment fragment = requestPage.getFragmentById(fragmentId);
903 
904                     if ( fragment == null )
905                     {
906                         // ignore no longer consistent page definition
907                         return;
908                     }
909                     
910                     if (decorator.trim().length() == 0)
911                         fragment.setDecorator(null);
912                     else
913                         fragment.setDecorator(decorator);
914                     try
915                     {
916                         pageManager.updatePage(requestPage);
917                     }
918                     catch (Exception e)
919                     {
920                         throw new PortletException("Unable to update page for fragment decorator: "+e.getMessage(), e);
921                     }
922                     return;
923                 }
924                 // evlach
925                 String decorators = request.getParameter("decorators");                
926                 // change style for all pages in user folder 
927                 String jsChangeUserPagesTheme = request.getParameter("jsChangeUserPagesTheme");
928                 if ( jsChangeUserPagesTheme != null )
929                 {
930                    String user_pages_theme = request.getParameter("user_pages_theme");
931                    try
932                     {
933                        Folder f = pageManager.getUserFolder(request.getRemoteUser());
934                        applyStyle(f,user_pages_theme,Fragment.LAYOUT);
935                        decorators=null;
936                     }
937                     catch (Exception e)
938                     {
939                        throw new PortletException("Unable to update folder for defUserLayoutDeco decorator: "+e.getMessage(), e);
940                     }
941                 }                
942                 String jsChangeUserPortletsDeco = request.getParameter("jsChangeUserPortletsDeco");
943                 if ( jsChangeUserPortletsDeco != null )
944                 {                  
945                    String user_portlets_deco = request.getParameter("user_portlets_deco");
946                    try
947                     {
948                        Folder f = pageManager.getUserFolder(request.getRemoteUser());
949                        applyStyle(f,user_portlets_deco,Fragment.PORTLET);
950                         decorators = null; //do insert next if
951                     }
952                    catch (Exception e)
953                     {
954                         throw new PortletException("Unable to update folder for defUserPortletDeco decorator: "+e.getMessage(), e);
955                     }
956                 }                                
957                 
958                 if ( decorators != null && decorators.length() > 1)
959                 {
960                     Iterator fragmentsIter = requestPage.getRootFragment().getFragments().iterator();
961                     while(fragmentsIter.hasNext())
962                     {
963                     	Fragment fragment = (Fragment) fragmentsIter.next();
964                     	if ( fragment == null )
965                         {
966                             // ignore no longer consistent page definition
967                             return;
968                         }
969                         
970                         if (decorators.trim().length() == 0)
971                             fragment.setDecorator(null);
972                         else
973                             fragment.setDecorator(decorators);
974                     }
975                     try
976                     {
977                         pageManager.updatePage(requestPage);
978                     }
979                     catch (Exception e)
980                     {
981                         throw new PortletException("Unable to update page for fragment decorator: "+e.getMessage(), e);
982                     }
983                     return;
984                 }                
985             }
986             
987             String portlets = request.getParameter("portlets");
988             if ( portlets != null && portlets.length() > 0 )
989             {
990                 PortletWindow window = requestContext.getActionWindow();
991                 Fragment targetFragment = requestPage.getFragmentById(window.getId().toString());
992 
993                 if ( targetFragment == null )
994                 {
995                     // ignore no longer consistent page definition
996                     return;
997                 }
998                 
999                 StringTokenizer tokenizer = new StringTokenizer(portlets, ",");            
1000                 while (tokenizer.hasMoreTokens())
1001                 {
1002                     String portlet = tokenizer.nextToken();
1003                     if (portlet.startsWith("box_"))
1004                     {
1005                         portlet = portlet.substring("box_".length());                        
1006                         addPortletToPage(requestPage, targetFragment, portlet);
1007                     }
1008                 }
1009                 return;
1010             }
1011         }
1012     }
1013         
1014     protected int getFragmentNestingLevel(Page page, String fragmentId)
1015     {
1016         Fragment root = page.getRootFragment();
1017         if ( root.getId().equals(fragmentId) )
1018         {
1019             return 0;
1020         }
1021         else
1022         {
1023             return getFragmentNestingLevel(root, 1, fragmentId);
1024         }
1025     }
1026     
1027     protected int getFragmentNestingLevel(Fragment parent, int level, String fragmentId)
1028     {
1029         Iterator iter = parent.getFragments().iterator();
1030         Fragment child;
1031         int childLevel;
1032         while ( iter.hasNext() )
1033         {
1034             child = (Fragment)iter.next();
1035             if (child.getId().equals(fragmentId))
1036             {
1037                 return level;
1038             }
1039             else
1040             {
1041                 childLevel = getFragmentNestingLevel(child, level+1, fragmentId);
1042                 if ( childLevel != -1 )
1043                 {
1044                     return childLevel;
1045                 }
1046             }
1047         }
1048         return -1;
1049     }
1050 
1051     protected String getEscapedName(String pageName)
1052     {
1053         try
1054         {
1055             return URLEncoder.encode(pageName, "UTF-8").replace('%', '_');
1056         }
1057         catch (UnsupportedEncodingException e)
1058         {
1059             log.warn("Unsupported Encoding Exception.", e);
1060             return pageName;
1061         }
1062     }
1063     
1064     private void applyStyle(Folder f, String theme, String theme_type) throws FolderNotUpdatedException, NodeException 
1065     {
1066        f.setDefaultDecorator(theme, theme_type);
1067        pageManager.updateFolder(f);
1068        Iterator pagesIter = f.getPages().iterator();
1069        while(pagesIter.hasNext())
1070        {
1071            Page pp = (Page) pagesIter.next();
1072            pp.setDefaultDecorator(theme, theme_type);
1073            pageManager.updatePage(pp);
1074        }                       
1075        Iterator userFoldersIter = pageManager.getFolders(f).iterator();
1076        while(userFoldersIter.hasNext()) 
1077        {
1078            Folder ff = (Folder) userFoldersIter.next();
1079            applyStyle(ff,theme,theme_type);
1080        }
1081     }    
1082 }