1   /**
2    * Copyright (c) 2000-2009 Liferay, Inc. All rights reserved.
3    *
4    *
5    *
6    *
7    * The contents of this file are subject to the terms of the Liferay Enterprise
8    * Subscription License ("License"). You may not use this file except in
9    * compliance with the License. You can obtain a copy of the License by
10   * contacting Liferay, Inc. See the License for the specific language governing
11   * permissions and limitations under the License, including but not limited to
12   * distribution rights of the Software.
13   *
14   * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
15   * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
16   * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
17   * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
18   * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
19   * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
20   * SOFTWARE.
21   */
22  
23  package com.liferay.portal.events;
24  
25  import com.liferay.portal.LayoutPermissionException;
26  import com.liferay.portal.NoSuchGroupException;
27  import com.liferay.portal.NoSuchLayoutException;
28  import com.liferay.portal.NoSuchUserException;
29  import com.liferay.portal.PortalException;
30  import com.liferay.portal.SystemException;
31  import com.liferay.portal.kernel.dao.orm.QueryUtil;
32  import com.liferay.portal.kernel.events.Action;
33  import com.liferay.portal.kernel.events.ActionException;
34  import com.liferay.portal.kernel.language.LanguageUtil;
35  import com.liferay.portal.kernel.log.Log;
36  import com.liferay.portal.kernel.log.LogFactoryUtil;
37  import com.liferay.portal.kernel.portlet.LiferayWindowState;
38  import com.liferay.portal.kernel.servlet.BrowserSnifferUtil;
39  import com.liferay.portal.kernel.servlet.ImageServletTokenUtil;
40  import com.liferay.portal.kernel.servlet.SessionErrors;
41  import com.liferay.portal.kernel.util.GetterUtil;
42  import com.liferay.portal.kernel.util.HttpUtil;
43  import com.liferay.portal.kernel.util.LocaleUtil;
44  import com.liferay.portal.kernel.util.ParamUtil;
45  import com.liferay.portal.kernel.util.PropsKeys;
46  import com.liferay.portal.kernel.util.StringBundler;
47  import com.liferay.portal.kernel.util.StringPool;
48  import com.liferay.portal.kernel.util.StringUtil;
49  import com.liferay.portal.kernel.util.UnicodeProperties;
50  import com.liferay.portal.kernel.util.Validator;
51  import com.liferay.portal.lar.PortletDataHandlerKeys;
52  import com.liferay.portal.model.ColorScheme;
53  import com.liferay.portal.model.Company;
54  import com.liferay.portal.model.Group;
55  import com.liferay.portal.model.GroupConstants;
56  import com.liferay.portal.model.Image;
57  import com.liferay.portal.model.Layout;
58  import com.liferay.portal.model.LayoutConstants;
59  import com.liferay.portal.model.LayoutSet;
60  import com.liferay.portal.model.LayoutTypePortlet;
61  import com.liferay.portal.model.Organization;
62  import com.liferay.portal.model.Portlet;
63  import com.liferay.portal.model.RoleConstants;
64  import com.liferay.portal.model.Theme;
65  import com.liferay.portal.model.User;
66  import com.liferay.portal.model.impl.ColorSchemeImpl;
67  import com.liferay.portal.model.impl.LayoutImpl;
68  import com.liferay.portal.model.impl.LayoutTypePortletImpl;
69  import com.liferay.portal.model.impl.ThemeImpl;
70  import com.liferay.portal.security.auth.PrincipalException;
71  import com.liferay.portal.security.permission.ActionKeys;
72  import com.liferay.portal.security.permission.PermissionChecker;
73  import com.liferay.portal.security.permission.PermissionCheckerFactoryUtil;
74  import com.liferay.portal.security.permission.PermissionThreadLocal;
75  import com.liferay.portal.service.GroupLocalServiceUtil;
76  import com.liferay.portal.service.ImageLocalServiceUtil;
77  import com.liferay.portal.service.LayoutLocalServiceUtil;
78  import com.liferay.portal.service.LayoutSetLocalServiceUtil;
79  import com.liferay.portal.service.OrganizationLocalServiceUtil;
80  import com.liferay.portal.service.PortletLocalServiceUtil;
81  import com.liferay.portal.service.RoleLocalServiceUtil;
82  import com.liferay.portal.service.ThemeLocalServiceUtil;
83  import com.liferay.portal.service.UserLocalServiceUtil;
84  import com.liferay.portal.service.permission.GroupPermissionUtil;
85  import com.liferay.portal.service.permission.LayoutPermissionUtil;
86  import com.liferay.portal.service.permission.OrganizationPermissionUtil;
87  import com.liferay.portal.service.permission.UserPermissionUtil;
88  import com.liferay.portal.theme.ThemeDisplay;
89  import com.liferay.portal.theme.ThemeDisplayFactory;
90  import com.liferay.portal.util.CookieKeys;
91  import com.liferay.portal.util.FriendlyURLNormalizer;
92  import com.liferay.portal.util.LayoutClone;
93  import com.liferay.portal.util.LayoutCloneFactory;
94  import com.liferay.portal.util.PortalUtil;
95  import com.liferay.portal.util.PortletKeys;
96  import com.liferay.portal.util.PrefsPropsUtil;
97  import com.liferay.portal.util.PropsUtil;
98  import com.liferay.portal.util.PropsValues;
99  import com.liferay.portal.util.WebKeys;
100 import com.liferay.portlet.PortletURLImpl;
101 
102 import java.io.File;
103 
104 import java.util.ArrayList;
105 import java.util.HashMap;
106 import java.util.LinkedHashMap;
107 import java.util.List;
108 import java.util.Locale;
109 import java.util.Map;
110 import java.util.TimeZone;
111 
112 import javax.portlet.PortletMode;
113 import javax.portlet.PortletRequest;
114 import javax.portlet.PortletURL;
115 import javax.portlet.WindowState;
116 
117 import javax.servlet.http.HttpServletRequest;
118 import javax.servlet.http.HttpServletResponse;
119 import javax.servlet.http.HttpSession;
120 
121 import org.apache.commons.lang.time.StopWatch;
122 import org.apache.struts.Globals;
123 
124 /**
125  * <a href="ServicePreAction.java.html"><b><i>View Source</i></b></a>
126  *
127  * @author Brian Wing Shun Chan
128  * @author Felix Ventero
129  */
130 public class ServicePreAction extends Action {
131 
132     public ServicePreAction() {
133         initImportLARFiles();
134     }
135 
136     public void run(HttpServletRequest request, HttpServletResponse response)
137         throws ActionException {
138 
139         StopWatch stopWatch = null;
140 
141         if (_log.isDebugEnabled()) {
142             stopWatch = new StopWatch();
143 
144             stopWatch.start();
145         }
146 
147         try {
148             servicePre(request, response);
149         }
150         catch (Exception e) {
151             throw new ActionException(e);
152         }
153 
154         if (_log.isDebugEnabled()) {
155             _log.debug("Running takes " + stopWatch.getTime() + " ms");
156         }
157     }
158 
159     protected void addDefaultLayoutsByLAR(
160             long userId, long groupId, boolean privateLayout, File larFile)
161         throws PortalException, SystemException {
162 
163         Map<String, String[]> parameterMap = new HashMap<String, String[]>();
164 
165         parameterMap.put(
166             PortletDataHandlerKeys.PERMISSIONS,
167             new String[] {Boolean.TRUE.toString()});
168         parameterMap.put(
169             PortletDataHandlerKeys.PORTLET_DATA,
170             new String[] {Boolean.TRUE.toString()});
171         parameterMap.put(
172             PortletDataHandlerKeys.PORTLET_DATA_CONTROL_DEFAULT,
173             new String[] {Boolean.TRUE.toString()});
174         parameterMap.put(
175             PortletDataHandlerKeys.PORTLET_SETUP,
176             new String[] {Boolean.TRUE.toString()});
177         parameterMap.put(
178             PortletDataHandlerKeys.USER_PERMISSIONS,
179             new String[] {Boolean.FALSE.toString()});
180 
181         LayoutLocalServiceUtil.importLayouts(
182             userId, groupId, privateLayout, parameterMap, larFile);
183     }
184 
185     protected void addDefaultUserPrivateLayoutByProperties(
186             long userId, long groupId)
187         throws PortalException, SystemException {
188 
189         String friendlyURL = getFriendlyURL(
190             PropsValues.DEFAULT_USER_PRIVATE_LAYOUT_FRIENDLY_URL);
191 
192         Layout layout = LayoutLocalServiceUtil.addLayout(
193             userId, groupId, true, LayoutConstants.DEFAULT_PARENT_LAYOUT_ID,
194             PropsValues.DEFAULT_USER_PRIVATE_LAYOUT_NAME, StringPool.BLANK,
195             StringPool.BLANK, LayoutConstants.TYPE_PORTLET, false, friendlyURL);
196 
197         LayoutTypePortlet layoutTypePortlet =
198             (LayoutTypePortlet)layout.getLayoutType();
199 
200         layoutTypePortlet.setLayoutTemplateId(
201             0, PropsValues.DEFAULT_USER_PRIVATE_LAYOUT_TEMPLATE_ID, false);
202 
203         for (int i = 0; i < 10; i++) {
204             String columnId = "column-" + i;
205             String portletIds = PropsUtil.get(
206                 PropsKeys.DEFAULT_USER_PRIVATE_LAYOUT_COLUMN + i);
207 
208             String[] portletIdsArray = StringUtil.split(portletIds);
209 
210             layoutTypePortlet.addPortletIds(
211                 0, portletIdsArray, columnId, false);
212         }
213 
214         LayoutLocalServiceUtil.updateLayout(
215             layout.getGroupId(), layout.isPrivateLayout(), layout.getLayoutId(),
216             layout.getTypeSettings());
217 
218         boolean updateLayoutSet = false;
219 
220         LayoutSet layoutSet = layout.getLayoutSet();
221 
222         if (Validator.isNotNull(
223                 PropsValues.DEFAULT_USER_PRIVATE_LAYOUT_REGULAR_THEME_ID)) {
224 
225             layoutSet.setThemeId(
226                 PropsValues.DEFAULT_USER_PRIVATE_LAYOUT_REGULAR_THEME_ID);
227 
228             updateLayoutSet = true;
229         }
230 
231         if (Validator.isNotNull(
232                 PropsValues.
233                     DEFAULT_USER_PRIVATE_LAYOUT_REGULAR_COLOR_SCHEME_ID)) {
234 
235             layoutSet.setColorSchemeId(
236                 PropsValues.
237                     DEFAULT_USER_PRIVATE_LAYOUT_REGULAR_COLOR_SCHEME_ID);
238 
239             updateLayoutSet = true;
240         }
241 
242         if (Validator.isNotNull(
243                 PropsValues.DEFAULT_USER_PRIVATE_LAYOUT_WAP_THEME_ID)) {
244 
245             layoutSet.setWapThemeId(
246                 PropsValues.DEFAULT_USER_PRIVATE_LAYOUT_WAP_THEME_ID);
247 
248             updateLayoutSet = true;
249         }
250 
251         if (Validator.isNotNull(
252                 PropsValues.DEFAULT_USER_PRIVATE_LAYOUT_WAP_COLOR_SCHEME_ID)) {
253 
254             layoutSet.setWapColorSchemeId(
255                 PropsValues.DEFAULT_USER_PRIVATE_LAYOUT_WAP_COLOR_SCHEME_ID);
256 
257             updateLayoutSet = true;
258         }
259 
260         if (updateLayoutSet) {
261             LayoutSetLocalServiceUtil.updateLayoutSet(layoutSet);
262         }
263     }
264 
265     protected void addDefaultUserPrivateLayouts(User user)
266         throws PortalException, SystemException {
267 
268         Group userGroup = user.getGroup();
269 
270         if (privateLARFile != null) {
271             addDefaultLayoutsByLAR(
272                 user.getUserId(), userGroup.getGroupId(), true, privateLARFile);
273         }
274         else {
275             addDefaultUserPrivateLayoutByProperties(
276                 user.getUserId(), userGroup.getGroupId());
277         }
278     }
279 
280     protected void addDefaultUserPublicLayoutByProperties(
281             long userId, long groupId)
282         throws PortalException, SystemException {
283 
284         String friendlyURL = getFriendlyURL(
285             PropsValues.DEFAULT_USER_PUBLIC_LAYOUT_FRIENDLY_URL);
286 
287         Layout layout = LayoutLocalServiceUtil.addLayout(
288             userId, groupId, false, LayoutConstants.DEFAULT_PARENT_LAYOUT_ID,
289             PropsValues.DEFAULT_USER_PUBLIC_LAYOUT_NAME, StringPool.BLANK,
290             StringPool.BLANK, LayoutConstants.TYPE_PORTLET, false, friendlyURL);
291 
292         LayoutTypePortlet layoutTypePortlet =
293             (LayoutTypePortlet)layout.getLayoutType();
294 
295         layoutTypePortlet.setLayoutTemplateId(
296             0, PropsValues.DEFAULT_USER_PUBLIC_LAYOUT_TEMPLATE_ID, false);
297 
298         for (int i = 0; i < 10; i++) {
299             String columnId = "column-" + i;
300             String portletIds = PropsUtil.get(
301                 PropsKeys.DEFAULT_USER_PUBLIC_LAYOUT_COLUMN + i);
302 
303             String[] portletIdsArray = StringUtil.split(portletIds);
304 
305             layoutTypePortlet.addPortletIds(
306                 0, portletIdsArray, columnId, false);
307         }
308 
309         LayoutLocalServiceUtil.updateLayout(
310             layout.getGroupId(), layout.isPrivateLayout(), layout.getLayoutId(),
311             layout.getTypeSettings());
312 
313         boolean updateLayoutSet = false;
314 
315         LayoutSet layoutSet = layout.getLayoutSet();
316 
317         if (Validator.isNotNull(
318                 PropsValues.DEFAULT_USER_PUBLIC_LAYOUT_REGULAR_THEME_ID)) {
319 
320             layoutSet.setThemeId(
321                 PropsValues.DEFAULT_USER_PUBLIC_LAYOUT_REGULAR_THEME_ID);
322 
323             updateLayoutSet = true;
324         }
325 
326         if (Validator.isNotNull(
327                 PropsValues.
328                     DEFAULT_USER_PUBLIC_LAYOUT_REGULAR_COLOR_SCHEME_ID)) {
329 
330             layoutSet.setColorSchemeId(
331                 PropsValues.DEFAULT_USER_PUBLIC_LAYOUT_REGULAR_COLOR_SCHEME_ID);
332 
333             updateLayoutSet = true;
334         }
335 
336         if (Validator.isNotNull(
337                 PropsValues.DEFAULT_USER_PUBLIC_LAYOUT_WAP_THEME_ID)) {
338 
339             layoutSet.setWapThemeId(
340                 PropsValues.DEFAULT_USER_PUBLIC_LAYOUT_WAP_THEME_ID);
341 
342             updateLayoutSet = true;
343         }
344 
345         if (Validator.isNotNull(
346                 PropsValues.DEFAULT_USER_PUBLIC_LAYOUT_WAP_COLOR_SCHEME_ID)) {
347 
348             layoutSet.setWapColorSchemeId(
349                 PropsValues.DEFAULT_USER_PUBLIC_LAYOUT_WAP_COLOR_SCHEME_ID);
350 
351             updateLayoutSet = true;
352         }
353 
354         if (updateLayoutSet) {
355             LayoutSetLocalServiceUtil.updateLayoutSet(layoutSet);
356         }
357     }
358 
359     protected void addDefaultUserPublicLayouts(User user)
360         throws PortalException, SystemException {
361 
362         Group userGroup = user.getGroup();
363 
364         if (publicLARFile != null) {
365             addDefaultLayoutsByLAR(
366                 user.getUserId(), userGroup.getGroupId(), false, publicLARFile);
367         }
368         else {
369             addDefaultUserPublicLayoutByProperties(
370                 user.getUserId(), userGroup.getGroupId());
371         }
372     }
373 
374     protected void deleteDefaultUserPrivateLayouts(User user)
375         throws PortalException, SystemException {
376 
377         Group userGroup = user.getGroup();
378 
379         LayoutLocalServiceUtil.deleteLayouts(userGroup.getGroupId(), true);
380     }
381 
382     protected void deleteDefaultUserPublicLayouts(User user)
383         throws PortalException, SystemException {
384 
385         Group userGroup = user.getGroup();
386 
387         LayoutLocalServiceUtil.deleteLayouts(userGroup.getGroupId(), false);
388     }
389 
390     protected Object[] getDefaultLayout(
391             HttpServletRequest request, User user, boolean signedIn)
392         throws PortalException, SystemException {
393 
394         // Check the virtual host
395 
396         LayoutSet layoutSet = (LayoutSet)request.getAttribute(
397             WebKeys.VIRTUAL_HOST_LAYOUT_SET);
398 
399         if (layoutSet != null) {
400             List<Layout> layouts = LayoutLocalServiceUtil.getLayouts(
401                 layoutSet.getGroupId(), layoutSet.isPrivateLayout(),
402                 LayoutConstants.DEFAULT_PARENT_LAYOUT_ID);
403 
404             if (layouts.size() > 0) {
405                 Layout layout = layouts.get(0);
406 
407                 return new Object[] {layout, layouts};
408             }
409         }
410 
411         Layout layout = null;
412         List<Layout> layouts = null;
413 
414         if (signedIn) {
415 
416             // Check the user's personal layouts
417 
418             Group userGroup = user.getGroup();
419 
420             layouts = LayoutLocalServiceUtil.getLayouts(
421                 userGroup.getGroupId(), true,
422                 LayoutConstants.DEFAULT_PARENT_LAYOUT_ID);
423 
424             if (layouts.size() == 0) {
425                 layouts = LayoutLocalServiceUtil.getLayouts(
426                     userGroup.getGroupId(), false,
427                     LayoutConstants.DEFAULT_PARENT_LAYOUT_ID);
428             }
429 
430             if (layouts.size() > 0) {
431                 layout = layouts.get(0);
432             }
433 
434             // Check the user's communities
435 
436             if (layout == null) {
437                 LinkedHashMap<String, Object> groupParams =
438                     new LinkedHashMap<String, Object>();
439 
440                 groupParams.put("usersGroups", new Long(user.getUserId()));
441 
442                 List<Group> groups = GroupLocalServiceUtil.search(
443                     user.getCompanyId(), null, null, groupParams,
444                     QueryUtil.ALL_POS, QueryUtil.ALL_POS);
445 
446                 for (Group group : groups) {
447                     layouts = LayoutLocalServiceUtil.getLayouts(
448                         group.getGroupId(), true,
449                         LayoutConstants.DEFAULT_PARENT_LAYOUT_ID);
450 
451                     if (layouts.size() == 0) {
452                         layouts = LayoutLocalServiceUtil.getLayouts(
453                             group.getGroupId(), false,
454                             LayoutConstants.DEFAULT_PARENT_LAYOUT_ID);
455                     }
456 
457                     if (layouts.size() > 0) {
458                         layout = layouts.get(0);
459 
460                         break;
461                     }
462                 }
463             }
464         }
465         else {
466 
467             // Check the guest community
468 
469             Group guestGroup = GroupLocalServiceUtil.getGroup(
470                 user.getCompanyId(), GroupConstants.GUEST);
471 
472             layouts = LayoutLocalServiceUtil.getLayouts(
473                 guestGroup.getGroupId(), false,
474                 LayoutConstants.DEFAULT_PARENT_LAYOUT_ID);
475 
476             if (layouts.size() > 0) {
477                 layout = layouts.get(0);
478             }
479         }
480 
481         return new Object[] {layout, layouts};
482     }
483 
484     protected String getFriendlyURL(String friendlyURL) {
485         friendlyURL = GetterUtil.getString(friendlyURL);
486 
487         return FriendlyURLNormalizer.normalize(friendlyURL);
488     }
489 
490     protected Object[] getViewableLayouts(
491             HttpServletRequest request, User user,
492             PermissionChecker permissionChecker, Layout layout,
493             List<Layout> layouts)
494         throws PortalException, SystemException {
495 
496         if ((layouts == null) || (layouts.size() == 0)) {
497             return new Object[] {layout, layouts};
498         }
499 
500         boolean replaceLayout = true;
501 
502         if (LayoutPermissionUtil.contains(
503                 permissionChecker, layout, ActionKeys.VIEW)) {
504 
505             replaceLayout = false;
506         }
507 
508         List<Layout> accessibleLayouts = new ArrayList<Layout>();
509 
510         for (int i = 0; i < layouts.size(); i++) {
511             Layout curLayout = layouts.get(i);
512 
513             if (!curLayout.isHidden() &&
514                 LayoutPermissionUtil.contains(
515                     permissionChecker, curLayout, ActionKeys.VIEW)) {
516 
517                 if ((accessibleLayouts.size() == 0) && replaceLayout) {
518                     layout = curLayout;
519                 }
520 
521                 accessibleLayouts.add(curLayout);
522             }
523         }
524 
525         if (accessibleLayouts.size() == 0) {
526             layouts = null;
527 
528             SessionErrors.add(
529                 request, LayoutPermissionException.class.getName());
530         }
531         else {
532             layouts = accessibleLayouts;
533         }
534 
535         return new Object[] {layout, layouts};
536     }
537 
538     protected Boolean hasPowerUserRole(User user) throws Exception {
539         return RoleLocalServiceUtil.hasUserRole(
540             user.getUserId(), user.getCompanyId(), RoleConstants.POWER_USER,
541             true);
542     }
543 
544     protected void initImportLARFiles() {
545         String privateLARFileName =
546             PropsValues.DEFAULT_USER_PRIVATE_LAYOUTS_LAR;
547 
548         if (_log.isDebugEnabled()) {
549             _log.debug("Reading private LAR file " + privateLARFileName);
550         }
551 
552         if (Validator.isNotNull(privateLARFileName)) {
553             privateLARFile = new File(privateLARFileName);
554 
555             if (!privateLARFile.exists()) {
556                 _log.error(
557                     "Private LAR file " + privateLARFile + " does not exist");
558 
559                 privateLARFile = null;
560             }
561             else {
562                 if (_log.isDebugEnabled()) {
563                     _log.debug("Using private LAR file " + privateLARFileName);
564                 }
565             }
566         }
567 
568         String publicLARFileName = PropsValues.DEFAULT_USER_PUBLIC_LAYOUTS_LAR;
569 
570         if (_log.isDebugEnabled()) {
571             _log.debug("Reading public LAR file " + publicLARFileName);
572         }
573 
574         if (Validator.isNotNull(publicLARFileName)) {
575             publicLARFile = new File(publicLARFileName);
576 
577             if (!publicLARFile.exists()) {
578                 _log.error(
579                     "Public LAR file " + publicLARFile + " does not exist");
580 
581                 publicLARFile = null;
582             }
583             else {
584                 if (_log.isDebugEnabled()) {
585                     _log.debug("Using public LAR file " + publicLARFileName);
586                 }
587             }
588         }
589     }
590 
591     /**
592      * @deprecated Use <code>isViewableGroup</code>.
593      */
594     protected boolean isViewableCommunity(
595             User user, long groupId, boolean privateLayout,
596             PermissionChecker permissionChecker)
597         throws PortalException, SystemException {
598 
599         return isViewableGroup(
600             user, groupId, privateLayout, 0, permissionChecker);
601     }
602 
603     protected boolean isViewableGroup(
604             User user, long groupId, boolean privateLayout, long layoutId,
605             PermissionChecker permissionChecker)
606         throws PortalException, SystemException {
607 
608         Group group = GroupLocalServiceUtil.getGroup(groupId);
609 
610         // Inactive communities are not viewable
611 
612         if (!group.isActive()) {
613             return false;
614         }
615         else if (group.isStagingGroup()) {
616             Group liveGroup = group.getLiveGroup();
617 
618             if (!liveGroup.isActive()) {
619                 return false;
620             }
621         }
622 
623         // User private layouts are only viewable by the user and anyone who can
624         // update the user. The user must also be active.
625 
626         if (group.isUser()) {
627             long groupUserId = group.getClassPK();
628 
629             if (groupUserId == user.getUserId()) {
630                 return true;
631             }
632             else {
633                 User groupUser = UserLocalServiceUtil.getUserById(groupUserId);
634 
635                 if (!groupUser.isActive()) {
636                     return false;
637                 }
638 
639                 if (privateLayout) {
640                     if (UserPermissionUtil.contains(
641                             permissionChecker, groupUserId,
642                             groupUser.getOrganizationIds(),
643                             ActionKeys.UPDATE)) {
644 
645                         return true;
646                     }
647                     else {
648                         return false;
649                     }
650                 }
651             }
652         }
653 
654         // If the current group is staging, only users with editorial rights
655         // can access it
656 
657         if (group.isStagingGroup()) {
658             if (user.isDefaultUser()) {
659                 return false;
660             }
661 
662             if (GroupPermissionUtil.contains(
663                     permissionChecker, groupId, ActionKeys.APPROVE_PROPOSAL) ||
664                 GroupPermissionUtil.contains(
665                     permissionChecker, groupId, ActionKeys.ASSIGN_REVIEWER) ||
666                 GroupPermissionUtil.contains(
667                     permissionChecker, groupId, ActionKeys.MANAGE_LAYOUTS) ||
668                 GroupPermissionUtil.contains(
669                     permissionChecker, groupId, ActionKeys.MANAGE_STAGING) ||
670                 GroupPermissionUtil.contains(
671                     permissionChecker, groupId, ActionKeys.PUBLISH_STAGING) ||
672                 ((layoutId > 0) && LayoutPermissionUtil.contains(
673                     permissionChecker, groupId, privateLayout, layoutId,
674                     ActionKeys.UPDATE))) {
675 
676                 return true;
677             }
678 
679             return false;
680         }
681 
682         // Most public layouts are viewable
683 
684         if (!privateLayout) {
685             return true;
686         }
687 
688         // Control panel layouts are only viewable by authenticated users
689 
690         if (group.getName().equals(GroupConstants.CONTROL_PANEL)) {
691             if (user.isDefaultUser()) {
692                 return false;
693             }
694             else {
695                 return true;
696             }
697         }
698 
699         // Community or organization layouts are only viewable by users who
700         // belong to the community or organization, or by users who can update
701         // the community or organization
702 
703         if (group.isCommunity()) {
704             if (GroupLocalServiceUtil.hasUserGroup(user.getUserId(), groupId)) {
705                 return true;
706             }
707             else if (GroupPermissionUtil.contains(
708                         permissionChecker, groupId, ActionKeys.UPDATE)) {
709 
710                 return true;
711             }
712         }
713         else if (group.isOrganization()) {
714             long organizationId = group.getClassPK();
715 
716             if (OrganizationLocalServiceUtil.hasUserOrganization(
717                     user.getUserId(), organizationId, false, true, false)) {
718 
719                 return true;
720             }
721             else if (OrganizationPermissionUtil.contains(
722                         permissionChecker, organizationId, ActionKeys.UPDATE)) {
723 
724                 return true;
725             }
726 
727             if (!PropsValues.ORGANIZATIONS_MEMBERSHIP_STRICT) {
728                 List<Organization> userOrgs =
729                     OrganizationLocalServiceUtil.getUserOrganizations(
730                         user.getUserId(), true);
731 
732                 for (Organization organization : userOrgs) {
733                     for (Organization ancestorOrganization :
734                             organization.getAncestors()) {
735 
736                         if (group.getClassPK() ==
737                                 ancestorOrganization.getOrganizationId()) {
738 
739                             return true;
740                         }
741                     }
742                 }
743             }
744         }
745         else if (group.isUserGroup()) {
746             if (GroupPermissionUtil.contains(
747                     permissionChecker, groupId, ActionKeys.MANAGE_LAYOUTS)) {
748 
749                 return true;
750             }
751         }
752 
753         return false;
754     }
755 
756     protected List<Layout> mergeAdditionalLayouts(
757             HttpServletRequest request, User user,
758             PermissionChecker permissionChecker, Layout layout,
759             List<Layout> layouts)
760         throws PortalException, SystemException {
761 
762         if ((layout == null) || layout.isPrivateLayout()) {
763             return layouts;
764         }
765 
766         long layoutGroupId = layout.getGroupId();
767 
768         Group guestGroup = GroupLocalServiceUtil.getGroup(
769             user.getCompanyId(), GroupConstants.GUEST);
770 
771         if (layoutGroupId != guestGroup.getGroupId()) {
772             Group layoutGroup = GroupLocalServiceUtil.getGroup(layoutGroupId);
773 
774             UnicodeProperties props = layoutGroup.getTypeSettingsProperties();
775 
776             boolean mergeGuestPublicPages = GetterUtil.getBoolean(
777                 props.getProperty("mergeGuestPublicPages"));
778 
779             if (!mergeGuestPublicPages) {
780                 return layouts;
781             }
782 
783             List<Layout> guestLayouts = LayoutLocalServiceUtil.getLayouts(
784                 guestGroup.getGroupId(), false,
785                 LayoutConstants.DEFAULT_PARENT_LAYOUT_ID);
786 
787             Object[] viewableLayouts = getViewableLayouts(
788                 request, user, permissionChecker, layout, guestLayouts);
789 
790             guestLayouts = (List<Layout>)viewableLayouts[1];
791 
792             layouts.addAll(0, guestLayouts);
793         }
794         else {
795             HttpSession session = request.getSession();
796 
797             Long previousGroupId = (Long)session.getAttribute(
798                 WebKeys.VISITED_GROUP_ID_PREVIOUS);
799 
800             if ((previousGroupId != null) &&
801                 (previousGroupId.longValue() != layoutGroupId)) {
802 
803                 Group previousGroup = null;
804 
805                 try {
806                     previousGroup = GroupLocalServiceUtil.getGroup(
807                         previousGroupId.longValue());
808                 }
809                 catch (NoSuchGroupException nsge) {
810                     if (_log.isWarnEnabled()) {
811                         _log.warn(nsge);
812                     }
813 
814                     return layouts;
815                 }
816 
817                 UnicodeProperties props =
818                     previousGroup.getTypeSettingsProperties();
819 
820                 boolean mergeGuestPublicPages = GetterUtil.getBoolean(
821                     props.getProperty("mergeGuestPublicPages"));
822 
823                 if (!mergeGuestPublicPages) {
824                     return layouts;
825                 }
826 
827                 List<Layout> previousLayouts =
828                     LayoutLocalServiceUtil.getLayouts(
829                         previousGroupId.longValue(), false,
830                         LayoutConstants.DEFAULT_PARENT_LAYOUT_ID);
831 
832                 Object[] viewableLayouts = getViewableLayouts(
833                     request, user, permissionChecker, layout, previousLayouts);
834 
835                 previousLayouts = (List<Layout>)viewableLayouts[1];
836 
837                 layouts.addAll(previousLayouts);
838             }
839         }
840 
841         return layouts;
842     }
843 
844     protected void rememberVisitedGroupIds(
845         HttpServletRequest request, long currentGroupId) {
846 
847         String requestURI = GetterUtil.getString(request.getRequestURI());
848 
849         if (!requestURI.endsWith(_PATH_PORTAL_LAYOUT)) {
850             return;
851         }
852 
853         HttpSession session = request.getSession();
854 
855         Long recentGroupId = (Long)session.getAttribute(
856             WebKeys.VISITED_GROUP_ID_RECENT);
857 
858         Long previousGroupId = (Long)session.getAttribute(
859             WebKeys.VISITED_GROUP_ID_PREVIOUS);
860 
861         if (recentGroupId == null) {
862             recentGroupId = new Long(currentGroupId);
863 
864             session.setAttribute(
865                 WebKeys.VISITED_GROUP_ID_RECENT, recentGroupId);
866         }
867         else if (recentGroupId.longValue() != currentGroupId) {
868             previousGroupId = new Long(recentGroupId.longValue());
869 
870             recentGroupId = new Long(currentGroupId);
871 
872             session.setAttribute(
873                 WebKeys.VISITED_GROUP_ID_RECENT, recentGroupId);
874 
875             session.setAttribute(
876                 WebKeys.VISITED_GROUP_ID_PREVIOUS, previousGroupId);
877         }
878 
879         if (_log.isDebugEnabled()) {
880             _log.debug("Current group id " + currentGroupId);
881             _log.debug("Recent group id " + recentGroupId);
882             _log.debug("Previous group id " + previousGroupId);
883         }
884     }
885 
886     protected void servicePre(
887             HttpServletRequest request, HttpServletResponse response)
888         throws Exception {
889 
890         HttpSession session = request.getSession();
891 
892         // Company
893 
894         Company company = PortalUtil.getCompany(request);
895 
896         long companyId = company.getCompanyId();
897 
898         // CDN host
899 
900         String cdnHost = null;
901 
902         if (request.isSecure()) {
903             cdnHost = PortalUtil.getCDNHostHttps();
904         }
905         else {
906             cdnHost = PortalUtil.getCDNHostHttp();
907         }
908 
909         cdnHost = ParamUtil.getString(request, "cdn_host", cdnHost);
910 
911         // Portal URL
912 
913         String portalURL = PortalUtil.getPortalURL(request);
914 
915         // Paths
916 
917         String contextPath = PortalUtil.getPathContext();
918         String friendlyURLPrivateGroupPath =
919             PortalUtil.getPathFriendlyURLPrivateGroup();
920         String friendlyURLPrivateUserPath =
921             PortalUtil.getPathFriendlyURLPrivateUser();
922         String friendlyURLPublicPath = PortalUtil.getPathFriendlyURLPublic();
923         String imagePath = cdnHost.concat(PortalUtil.getPathImage());
924         String mainPath = PortalUtil.getPathMain();
925 
926         String i18nPath = (String)request.getAttribute(WebKeys.I18N_PATH);
927 
928         if (Validator.isNotNull(i18nPath)) {
929             if (Validator.isNotNull(contextPath)) {
930                 String i18nContextPath = contextPath.concat(i18nPath);
931 
932                 friendlyURLPrivateGroupPath = StringUtil.replaceFirst(
933                     friendlyURLPrivateGroupPath, contextPath, i18nContextPath);
934                 friendlyURLPrivateUserPath = StringUtil.replaceFirst(
935                     friendlyURLPrivateUserPath, contextPath, i18nContextPath);
936                 friendlyURLPublicPath = StringUtil.replaceFirst(
937                     friendlyURLPublicPath, contextPath, i18nContextPath);
938                 mainPath = StringUtil.replaceFirst(
939                     mainPath, contextPath, i18nContextPath);
940             }
941             else {
942                 friendlyURLPrivateGroupPath = i18nPath.concat(
943                     friendlyURLPrivateGroupPath);
944                 friendlyURLPrivateUserPath = i18nPath.concat(
945                     friendlyURLPrivateUserPath);
946                 friendlyURLPublicPath = i18nPath.concat(friendlyURLPublicPath);
947                 mainPath = i18nPath.concat(mainPath);
948             }
949         }
950 
951         // Company logo
952 
953         StringBundler sb = new StringBundler(5);
954 
955         sb.append(imagePath);
956         sb.append("/company_logo?img_id=");
957         sb.append(company.getLogoId());
958         sb.append("&t=");
959         sb.append(ImageServletTokenUtil.getToken(company.getLogoId()));
960 
961         String companyLogo = sb.toString();
962 
963         Image companyLogoImage = ImageLocalServiceUtil.getCompanyLogo(
964             company.getLogoId());
965 
966         int companyLogoHeight = companyLogoImage.getHeight();
967         int companyLogoWidth = companyLogoImage.getWidth();
968 
969         String realCompanyLogo = companyLogo;
970         int realCompanyLogoHeight = companyLogoHeight;
971         int realCompanyLogoWidth = companyLogoWidth;
972 
973         // User
974 
975         User user = null;
976 
977         try {
978             user = PortalUtil.getUser(request);
979         }
980         catch (NoSuchUserException nsue) {
981             if (_log.isWarnEnabled()) {
982                 _log.warn(nsue.getMessage());
983             }
984 
985             long userId = PortalUtil.getUserId(request);
986 
987             if (userId > 0) {
988                 session.invalidate();
989             }
990 
991             return;
992         }
993 
994         boolean signedIn = false;
995 
996         if (user == null) {
997             user = company.getDefaultUser();
998         }
999         else if (!user.isDefaultUser()) {
1000            signedIn = true;
1001        }
1002
1003        User realUser = user;
1004
1005        Long realUserId = (Long)session.getAttribute(WebKeys.USER_ID);
1006
1007        if (realUserId != null) {
1008            if (user.getUserId() != realUserId.longValue()) {
1009                realUser = UserLocalServiceUtil.getUserById(
1010                    realUserId.longValue());
1011            }
1012        }
1013
1014        String doAsUserId = ParamUtil.getString(request, "doAsUserId");
1015        String doAsUserLanguageId = ParamUtil.getString(
1016            request, "doAsUserLanguageId");
1017        long doAsGroupId = ParamUtil.getLong(request, "doAsGroupId");
1018        long refererPlid = ParamUtil.getLong(request, "refererPlid");
1019
1020        // Permission checker
1021
1022        PermissionChecker permissionChecker =
1023            PermissionCheckerFactoryUtil.create(user, true);
1024
1025        PermissionThreadLocal.setPermissionChecker(permissionChecker);
1026
1027        // Locale
1028
1029        Locale locale = (Locale)session.getAttribute(Globals.LOCALE_KEY);
1030
1031        if (Validator.isNotNull(doAsUserLanguageId)) {
1032            locale = LocaleUtil.fromLanguageId(doAsUserLanguageId);
1033        }
1034
1035        String i18nLanguageId = (String)request.getAttribute(
1036            WebKeys.I18N_LANGUAGE_ID);
1037
1038        if (Validator.isNotNull(i18nLanguageId)) {
1039            locale = LocaleUtil.fromLanguageId(i18nLanguageId);
1040        }
1041        else if (locale == null) {
1042            if (signedIn) {
1043                locale = user.getLocale();
1044            }
1045            else {
1046
1047                // User previously set their preferred language
1048
1049                String languageId = CookieKeys.getCookie(
1050                    request, CookieKeys.GUEST_LANGUAGE_ID);
1051
1052                if (Validator.isNotNull(languageId)) {
1053                    locale = LocaleUtil.fromLanguageId(languageId);
1054                }
1055
1056                // Get locale from the request
1057
1058                if ((locale == null) && PropsValues.LOCALE_DEFAULT_REQUEST) {
1059                    locale = request.getLocale();
1060                }
1061
1062                // Get locale from the default user
1063
1064                if (locale == null) {
1065                    locale = user.getLocale();
1066                }
1067
1068                if (Validator.isNull(locale.getCountry())) {
1069
1070                    // Locales must contain a country code
1071
1072                    locale = LanguageUtil.getLocale(locale.getLanguage());
1073                }
1074
1075                if (!LanguageUtil.isAvailableLocale(locale)) {
1076                    locale = user.getLocale();
1077                }
1078            }
1079
1080            session.setAttribute(Globals.LOCALE_KEY, locale);
1081
1082            LanguageUtil.updateCookie(request, response, locale);
1083        }
1084
1085        // Cookie support
1086
1087        try {
1088
1089            // LEP-4069
1090
1091            CookieKeys.validateSupportCookie(request);
1092        }
1093        catch (Exception e) {
1094            CookieKeys.addSupportCookie(request, response);
1095        }
1096
1097        // Time zone
1098
1099        TimeZone timeZone = user.getTimeZone();
1100
1101        if (timeZone == null) {
1102            timeZone = company.getTimeZone();
1103        }
1104
1105        // Layouts
1106
1107        if (signedIn) {
1108            updateUserLayouts(user);
1109        }
1110
1111        Layout layout = null;
1112        List<Layout> layouts = null;
1113
1114        long plid = ParamUtil.getLong(request, "p_l_id");
1115
1116        if (plid > 0) {
1117            layout = LayoutLocalServiceUtil.getLayout(plid);
1118        }
1119        else {
1120            long groupId = ParamUtil.getLong(request, "groupId");
1121            boolean privateLayout = ParamUtil.getBoolean(
1122                request, "privateLayout");
1123            long layoutId = ParamUtil.getLong(request, "layoutId");
1124
1125            if ((groupId > 0) && layoutId > 0) {
1126                layout = LayoutLocalServiceUtil.getLayout(
1127                    groupId, privateLayout, layoutId);
1128            }
1129        }
1130
1131        if (layout != null) {
1132            try {
1133                Group group = layout.getGroup();
1134
1135                if (!signedIn && PropsValues.AUTH_FORWARD_BY_REDIRECT) {
1136                    request.setAttribute(WebKeys.REQUESTED_LAYOUT, layout);
1137                }
1138
1139                boolean isViewableCommunity = isViewableGroup(
1140                    user, layout.getGroupId(), layout.isPrivateLayout(),
1141                    layout.getLayoutId(), permissionChecker);
1142
1143                if (!isViewableCommunity && group.isStagingGroup()) {
1144                    layout = null;
1145                }
1146                else if (!isViewableCommunity) {
1147                    sb = new StringBundler(6);
1148
1149                    sb.append("User ");
1150                    sb.append(user.getUserId());
1151                    sb.append(" is not allowed to access the ");
1152                    sb.append(layout.isPrivateLayout() ? "private": "public");
1153                    sb.append(" pages of group ");
1154                    sb.append(layout.getGroupId());
1155
1156                    if (_log.isWarnEnabled()) {
1157                        _log.warn(sb.toString());
1158                    }
1159
1160                    throw new PrincipalException(sb.toString());
1161                }
1162                else if (isViewableCommunity &&
1163                        !LayoutPermissionUtil.contains(
1164                            permissionChecker, layout, ActionKeys.VIEW)) {
1165
1166                    layout = null;
1167                }
1168                else {
1169                    layouts = LayoutLocalServiceUtil.getLayouts(
1170                        layout.getGroupId(), layout.isPrivateLayout(),
1171                        LayoutConstants.DEFAULT_PARENT_LAYOUT_ID);
1172
1173                    if (!group.getName().equals(GroupConstants.CONTROL_PANEL)) {
1174                        doAsGroupId = 0;
1175                    }
1176                }
1177            }
1178            catch (NoSuchLayoutException nsle) {
1179            }
1180        }
1181
1182        if (layout == null) {
1183            Object[] defaultLayout = getDefaultLayout(request, user, signedIn);
1184
1185            layout = (Layout)defaultLayout[0];
1186            layouts = (List<Layout>)defaultLayout[1];
1187
1188            request.setAttribute(WebKeys.LAYOUT_DEFAULT, Boolean.TRUE);
1189        }
1190
1191        Object[] viewableLayouts = getViewableLayouts(
1192            request, user, permissionChecker, layout, layouts);
1193
1194        String layoutSetLogo = null;
1195
1196        layout = (Layout)viewableLayouts[0];
1197        layouts = (List<Layout>)viewableLayouts[1];
1198
1199        Group group = null;
1200
1201        if (layout != null) {
1202            group = layout.getGroup();
1203
1204            if (!group.getName().equals(GroupConstants.CONTROL_PANEL)) {
1205                rememberVisitedGroupIds(request, group.getGroupId());
1206            }
1207        }
1208
1209        LayoutTypePortlet layoutTypePortlet = null;
1210
1211        layouts = mergeAdditionalLayouts(
1212            request, user, permissionChecker, layout, layouts);
1213
1214        if (layout != null) {
1215            if (company.isCommunityLogo()) {
1216                long logoId = 0;
1217
1218                if (layout.isIconImage()) {
1219                    logoId = layout.getIconImageId();
1220                }
1221                else{
1222                    LayoutSet layoutSet = layout.getLayoutSet();
1223
1224                    if (layoutSet.isLogo()) {
1225                        logoId = layoutSet.getLogoId();
1226                    }
1227                    else {
1228                        LayoutSet siblingLayoutSet =
1229                            LayoutSetLocalServiceUtil.getLayoutSet(
1230                                layout.getGroupId(), !layout.isPrivateLayout());
1231
1232                        if (siblingLayoutSet.isLogo()) {
1233                            logoId = siblingLayoutSet.getLogoId();
1234                        }
1235                    }
1236                }
1237
1238                if (logoId > 0) {
1239                    sb = new StringBundler(5);
1240
1241                    sb.append(imagePath);
1242                    sb.append("/layout_set_logo?img_id=");
1243                    sb.append(logoId);
1244                    sb.append("&t=");
1245                    sb.append(ImageServletTokenUtil.getToken(logoId));
1246
1247                    layoutSetLogo = sb.toString();
1248
1249                    Image layoutSetLogoImage =
1250                        ImageLocalServiceUtil.getCompanyLogo(logoId);
1251
1252                    companyLogo = layoutSetLogo;
1253                    companyLogoHeight = layoutSetLogoImage.getHeight();
1254                    companyLogoWidth = layoutSetLogoImage.getWidth();
1255                }
1256            }
1257
1258            plid = layout.getPlid();
1259
1260            // Updates to shared layouts are not reflected until the next time
1261            // the user logs in because group layouts are cached in the session
1262
1263            layout = (Layout)((LayoutImpl)layout).clone();
1264
1265            layoutTypePortlet = (LayoutTypePortlet)layout.getLayoutType();
1266
1267            LayoutClone layoutClone = LayoutCloneFactory.getInstance();
1268
1269            if (layoutClone != null) {
1270                String typeSettings = layoutClone.get(request, plid);
1271
1272                if (typeSettings != null) {
1273                    UnicodeProperties props = new UnicodeProperties(true);
1274
1275                    props.load(typeSettings);
1276
1277                    String stateMax = props.getProperty(
1278                        LayoutTypePortletImpl.STATE_MAX);
1279                    String stateMin = props.getProperty(
1280                        LayoutTypePortletImpl.STATE_MIN);
1281                    String modeAbout = props.getProperty(
1282                        LayoutTypePortletImpl.MODE_ABOUT);
1283                    String modeConfig = props.getProperty(
1284                        LayoutTypePortletImpl.MODE_CONFIG);
1285                    String modeEdit = props.getProperty(
1286                        LayoutTypePortletImpl.MODE_EDIT);
1287                    String modeEditDefaults = props.getProperty(
1288                        LayoutTypePortletImpl.MODE_EDIT_DEFAULTS);
1289                    String modeEditGuest = props.getProperty(
1290                        LayoutTypePortletImpl.MODE_EDIT_GUEST);
1291                    String modeHelp = props.getProperty(
1292                        LayoutTypePortletImpl.MODE_HELP);
1293                    String modePreview = props.getProperty(
1294                        LayoutTypePortletImpl.MODE_PREVIEW);
1295                    String modePrint = props.getProperty(
1296                        LayoutTypePortletImpl.MODE_PRINT);
1297
1298                    layoutTypePortlet.setStateMax(stateMax);
1299                    layoutTypePortlet.setStateMin(stateMin);
1300                    layoutTypePortlet.setModeAbout(modeAbout);
1301                    layoutTypePortlet.setModeConfig(modeConfig);
1302                    layoutTypePortlet.setModeEdit(modeEdit);
1303                    layoutTypePortlet.setModeEditDefaults(modeEditDefaults);
1304                    layoutTypePortlet.setModeEditGuest(modeEditGuest);
1305                    layoutTypePortlet.setModeHelp(modeHelp);
1306                    layoutTypePortlet.setModePreview(modePreview);
1307                    layoutTypePortlet.setModePrint(modePrint);
1308                }
1309            }
1310
1311            request.setAttribute(WebKeys.LAYOUT, layout);
1312            request.setAttribute(WebKeys.LAYOUTS, layouts);
1313
1314            if (layout.isPrivateLayout()) {
1315                permissionChecker.setCheckGuest(false);
1316            }
1317        }
1318
1319        // Scope
1320
1321        long scopeGroupId = PortalUtil.getScopeGroupId(request);
1322
1323        // Theme and color scheme
1324
1325        Theme theme = null;
1326        ColorScheme colorScheme = null;
1327
1328        boolean wapTheme = BrowserSnifferUtil.isWap(request);
1329
1330        if ((layout != null) &&
1331            group.getName().equals(GroupConstants.CONTROL_PANEL)) {
1332
1333            String themeId = PrefsPropsUtil.getString(
1334                companyId, PropsKeys.CONTROL_PANEL_LAYOUT_REGULAR_THEME_ID);
1335            String colorSchemeId =
1336                ColorSchemeImpl.getDefaultRegularColorSchemeId();
1337
1338            theme = ThemeLocalServiceUtil.getTheme(
1339                companyId, themeId, wapTheme);
1340            colorScheme = ThemeLocalServiceUtil.getColorScheme(
1341                companyId, theme.getThemeId(), colorSchemeId, wapTheme);
1342
1343            if (!wapTheme && theme.isWapTheme()) {
1344                theme = ThemeLocalServiceUtil.getTheme(
1345                    companyId,
1346                    PropsValues.CONTROL_PANEL_LAYOUT_REGULAR_THEME_ID, false);
1347                colorScheme = ThemeLocalServiceUtil.getColorScheme(
1348                    companyId, theme.getThemeId(), colorSchemeId, false);
1349            }
1350        }
1351        else if (layout != null) {
1352            if (wapTheme) {
1353                theme = layout.getWapTheme();
1354                colorScheme = layout.getWapColorScheme();
1355            }
1356            else {
1357                theme = layout.getTheme();
1358                colorScheme = layout.getColorScheme();
1359            }
1360        }
1361        else {
1362            String themeId = null;
1363            String colorSchemeId = null;
1364
1365            if (wapTheme) {
1366                themeId = ThemeImpl.getDefaultWapThemeId(companyId);
1367                colorSchemeId = ColorSchemeImpl.getDefaultWapColorSchemeId();
1368            }
1369            else {
1370                themeId = ThemeImpl.getDefaultRegularThemeId(companyId);
1371                colorSchemeId =
1372                    ColorSchemeImpl.getDefaultRegularColorSchemeId();
1373            }
1374
1375            theme = ThemeLocalServiceUtil.getTheme(
1376                companyId, themeId, wapTheme);
1377            colorScheme = ThemeLocalServiceUtil.getColorScheme(
1378                companyId, theme.getThemeId(), colorSchemeId, wapTheme);
1379        }
1380
1381        request.setAttribute(WebKeys.THEME, theme);
1382        request.setAttribute(WebKeys.COLOR_SCHEME, colorScheme);
1383
1384        boolean themeCssFastLoad = ParamUtil.getBoolean(
1385            request, "css_fast_load", PropsValues.THEME_CSS_FAST_LOAD);
1386        boolean themeImagesFastLoad = ParamUtil.getBoolean(
1387            request, "images_fast_load", PropsValues.THEME_IMAGES_FAST_LOAD);
1388
1389        boolean themeJsBarebone = PropsValues.JAVASCRIPT_BAREBONE_ENABLED;
1390
1391        if (themeJsBarebone) {
1392            if (signedIn) {
1393                themeJsBarebone = false;
1394            }
1395        }
1396
1397        boolean themeJsFastLoad = ParamUtil.getBoolean(
1398            request, "js_fast_load", PropsValues.JAVASCRIPT_FAST_LOAD);
1399
1400        String lifecycle = ParamUtil.getString(request, "p_p_lifecycle", "0");
1401
1402        String facebookCanvasPageURL = (String)request.getAttribute(
1403            WebKeys.FACEBOOK_CANVAS_PAGE_URL);
1404
1405        boolean widget = false;
1406
1407        Boolean widgetObj = (Boolean)request.getAttribute(WebKeys.WIDGET);
1408
1409        if (widgetObj != null) {
1410            widget = widgetObj.booleanValue();
1411        }
1412
1413        // Theme display
1414
1415        ThemeDisplay themeDisplay = ThemeDisplayFactory.create();
1416
1417        // Set the CDN host, portal URL, and Facebook application ID first
1418        // because other methods (setLookAndFeel) depend on them being set
1419
1420        themeDisplay.setCDNHost(cdnHost);
1421        themeDisplay.setPortalURL(portalURL);
1422        themeDisplay.setFacebookCanvasPageURL(facebookCanvasPageURL);
1423        themeDisplay.setWidget(widget);
1424
1425        themeDisplay.setCompany(company);
1426        themeDisplay.setCompanyLogo(companyLogo);
1427        themeDisplay.setCompanyLogoHeight(companyLogoHeight);
1428        themeDisplay.setCompanyLogoWidth(companyLogoWidth);
1429        themeDisplay.setRealCompanyLogo(realCompanyLogo);
1430        themeDisplay.setRealCompanyLogoHeight(realCompanyLogoHeight);
1431        themeDisplay.setRealCompanyLogoWidth(realCompanyLogoWidth);
1432        themeDisplay.setUser(user);
1433        themeDisplay.setRealUser(realUser);
1434        themeDisplay.setDoAsUserId(doAsUserId);
1435        themeDisplay.setDoAsUserLanguageId(doAsUserLanguageId);
1436        themeDisplay.setDoAsGroupId(doAsGroupId);
1437        themeDisplay.setRefererPlid(refererPlid);
1438        themeDisplay.setLayoutSetLogo(layoutSetLogo);
1439        themeDisplay.setLayout(layout);
1440        themeDisplay.setLayouts(layouts);
1441        themeDisplay.setPlid(plid);
1442        themeDisplay.setLayoutTypePortlet(layoutTypePortlet);
1443        themeDisplay.setScopeGroupId(scopeGroupId);
1444        themeDisplay.setSignedIn(signedIn);
1445        themeDisplay.setPermissionChecker(permissionChecker);
1446        themeDisplay.setLocale(locale);
1447        themeDisplay.setLanguageId(LocaleUtil.toLanguageId(locale));
1448        themeDisplay.setI18nLanguageId(i18nLanguageId);
1449        themeDisplay.setI18nPath(i18nPath);
1450        themeDisplay.setTimeZone(timeZone);
1451        themeDisplay.setLookAndFeel(contextPath, theme, colorScheme);
1452        themeDisplay.setThemeCssFastLoad(themeCssFastLoad);
1453        themeDisplay.setThemeImagesFastLoad(themeImagesFastLoad);
1454        themeDisplay.setThemeJsBarebone(themeJsBarebone);
1455        themeDisplay.setThemeJsFastLoad(themeJsFastLoad);
1456        themeDisplay.setServerName(request.getServerName());
1457        themeDisplay.setServerPort(request.getServerPort());
1458        themeDisplay.setSecure(request.isSecure());
1459        themeDisplay.setLifecycle(lifecycle);
1460        themeDisplay.setLifecycleAction(lifecycle.equals("1"));
1461        themeDisplay.setLifecycleRender(lifecycle.equals("0"));
1462        themeDisplay.setLifecycleResource(lifecycle.equals("2"));
1463        themeDisplay.setStateExclusive(LiferayWindowState.isExclusive(request));
1464        themeDisplay.setStateMaximized(LiferayWindowState.isMaximized(request));
1465        themeDisplay.setStatePopUp(LiferayWindowState.isPopUp(request));
1466        themeDisplay.setPathApplet(contextPath.concat("/applets"));
1467        themeDisplay.setPathCms(contextPath.concat("/cms"));
1468        themeDisplay.setPathContext(contextPath);
1469        themeDisplay.setPathFlash(contextPath.concat("/flash"));
1470        themeDisplay.setPathFriendlyURLPrivateGroup(
1471            friendlyURLPrivateGroupPath);
1472        themeDisplay.setPathFriendlyURLPrivateUser(friendlyURLPrivateUserPath);
1473        themeDisplay.setPathFriendlyURLPublic(friendlyURLPublicPath);
1474        themeDisplay.setPathImage(imagePath);
1475        themeDisplay.setPathJavaScript(
1476            cdnHost.concat(contextPath).concat("/html/js"));
1477        themeDisplay.setPathMain(mainPath);
1478        themeDisplay.setPathSound(contextPath.concat("/html/sound"));
1479
1480        // URLs
1481
1482        themeDisplay.setShowAddContentIcon(false);
1483        themeDisplay.setShowControlPanelIcon(signedIn);
1484        themeDisplay.setShowHomeIcon(true);
1485        themeDisplay.setShowMyAccountIcon(signedIn);
1486        themeDisplay.setShowPageSettingsIcon(false);
1487        themeDisplay.setShowPortalIcon(true);
1488        themeDisplay.setShowSignInIcon(!signedIn);
1489        themeDisplay.setShowSignOutIcon(signedIn);
1490        themeDisplay.setShowStagingIcon(false);
1491
1492        String urlControlPanel = friendlyURLPrivateGroupPath.concat(
1493            "/control_panel");
1494
1495        if (Validator.isNotNull(doAsUserId)) {
1496            urlControlPanel = HttpUtil.addParameter(
1497                urlControlPanel, "doAsUserId", doAsUserId);
1498        }
1499
1500        if (scopeGroupId > 0) {
1501            urlControlPanel = HttpUtil.addParameter(
1502                urlControlPanel, "doAsGroupId", scopeGroupId);
1503        }
1504
1505        if (refererPlid > 0) {
1506            urlControlPanel = HttpUtil.addParameter(
1507                urlControlPanel, "refererPlid", refererPlid);
1508        }
1509        else if (plid > 0) {
1510            urlControlPanel = HttpUtil.addParameter(
1511                urlControlPanel, "refererPlid", plid);
1512        }
1513
1514        themeDisplay.setURLControlPanel(urlControlPanel);
1515
1516        PortletURL createAccountURL = new PortletURLImpl(
1517            request, PortletKeys.LOGIN, plid, PortletRequest.ACTION_PHASE);
1518
1519        createAccountURL.setWindowState(WindowState.MAXIMIZED);
1520        createAccountURL.setPortletMode(PortletMode.VIEW);
1521
1522        createAccountURL.setParameter("saveLastPath", "0");
1523        createAccountURL.setParameter(
1524            "struts_action", "/login/create_account");
1525
1526        themeDisplay.setURLCreateAccount(createAccountURL);
1527
1528        String currentURL = PortalUtil.getCurrentURL(request);
1529
1530        themeDisplay.setURLCurrent(currentURL);
1531
1532        String urlHome = PortalUtil.getHomeURL(request);
1533
1534        themeDisplay.setURLHome(urlHome);
1535
1536        if (layout != null) {
1537            if (layout.getType().equals(LayoutConstants.TYPE_PORTLET)) {
1538                boolean freeformLayout =
1539                    layoutTypePortlet.getLayoutTemplateId().equals(
1540                        "freeform");
1541
1542                themeDisplay.setFreeformLayout(freeformLayout);
1543
1544                boolean hasUpdateLayoutPermission =
1545                    LayoutPermissionUtil.contains(
1546                        permissionChecker, layout, ActionKeys.UPDATE);
1547
1548                if (hasUpdateLayoutPermission) {
1549                    if (!LiferayWindowState.isMaximized(request)) {
1550                        themeDisplay.setShowAddContentIcon(true);
1551                    }
1552
1553                    themeDisplay.setShowLayoutTemplatesIcon(true);
1554
1555                    themeDisplay.setURLAddContent(
1556                        "LayoutConfiguration.toggle('".concat(
1557                            PortletKeys.LAYOUT_CONFIGURATION).concat("');"));
1558
1559                    themeDisplay.setURLLayoutTemplates(
1560                        "Liferay.Layout.showTemplates();");
1561                }
1562            }
1563
1564            boolean hasManageLayoutsPermission =
1565                GroupPermissionUtil.contains(
1566                    permissionChecker, scopeGroupId, ActionKeys.MANAGE_LAYOUTS);
1567
1568            if (group.isUser()) {
1569                if ((layout.isPrivateLayout() &&
1570                     !PropsValues.LAYOUT_USER_PRIVATE_LAYOUTS_MODIFIABLE) ||
1571                    (layout.isPublicLayout() &&
1572                     !PropsValues.LAYOUT_USER_PUBLIC_LAYOUTS_MODIFIABLE)) {
1573
1574                    hasManageLayoutsPermission = false;
1575                }
1576            }
1577
1578            if (hasManageLayoutsPermission) {
1579                themeDisplay.setShowPageSettingsIcon(true);
1580
1581                PortletURL pageSettingsURL = new PortletURLImpl(
1582                    request, PortletKeys.LAYOUT_MANAGEMENT, plid,
1583                    PortletRequest.RENDER_PHASE);
1584
1585                pageSettingsURL.setWindowState(WindowState.MAXIMIZED);
1586                pageSettingsURL.setPortletMode(PortletMode.VIEW);
1587
1588                pageSettingsURL.setParameter(
1589                    "struts_action", "/layout_management/edit_pages");
1590
1591                if (layout.isPrivateLayout()) {
1592                    pageSettingsURL.setParameter("tabs1", "private-pages");
1593                }
1594                else {
1595                    pageSettingsURL.setParameter("tabs1", "public-pages");
1596                }
1597
1598                pageSettingsURL.setParameter("redirect", currentURL);
1599                pageSettingsURL.setParameter(
1600                    "groupId", String.valueOf(scopeGroupId));
1601                pageSettingsURL.setParameter("selPlid", String.valueOf(plid));
1602
1603                themeDisplay.setURLPageSettings(pageSettingsURL);
1604
1605                PortletURL publishToLiveURL = new PortletURLImpl(
1606                    request, PortletKeys.LAYOUT_MANAGEMENT, plid,
1607                    PortletRequest.RENDER_PHASE);
1608
1609                publishToLiveURL.setWindowState(LiferayWindowState.EXCLUSIVE);
1610                publishToLiveURL.setPortletMode(PortletMode.VIEW);
1611
1612                publishToLiveURL.setParameter(
1613                    "struts_action", "/layout_management/export_pages");
1614
1615                if (layout.isPrivateLayout()) {
1616                    publishToLiveURL.setParameter("tabs1", "private-pages");
1617                }
1618                else {
1619                    publishToLiveURL.setParameter("tabs1", "public-pages");
1620                }
1621
1622                publishToLiveURL.setParameter("pagesRedirect", currentURL);
1623                publishToLiveURL.setParameter(
1624                    "groupId", String.valueOf(scopeGroupId));
1625                publishToLiveURL.setParameter("selPlid", String.valueOf(plid));
1626
1627                themeDisplay.setURLPublishToLive(publishToLiveURL);
1628            }
1629
1630            if (group.hasStagingGroup() && !group.isStagingGroup()) {
1631                themeDisplay.setShowAddContentIcon(false);
1632                themeDisplay.setShowLayoutTemplatesIcon(false);
1633                themeDisplay.setShowPageSettingsIcon(false);
1634                themeDisplay.setURLPublishToLive(null);
1635            }
1636
1637            if (group.getName().equals(GroupConstants.CONTROL_PANEL)) {
1638                themeDisplay.setShowPageSettingsIcon(false);
1639                themeDisplay.setURLPublishToLive(null);
1640            }
1641
1642            // LEP-4987
1643
1644            if (group.hasStagingGroup() || group.isStagingGroup()) {
1645                boolean hasApproveProposalPermission =
1646                    GroupPermissionUtil.contains(
1647                        permissionChecker, scopeGroupId,
1648                        ActionKeys.APPROVE_PROPOSAL);
1649
1650                boolean hasUpdateLayoutPermission =
1651                    LayoutPermissionUtil.contains(
1652                        permissionChecker, layout.getGroupId(),
1653                        layout.isPrivateLayout(), layout.getLayoutId(),
1654                        ActionKeys.UPDATE);
1655
1656                if (hasManageLayoutsPermission) {
1657                    themeDisplay.setShowStagingIcon(true);
1658                }
1659                else if (hasApproveProposalPermission) {
1660                    themeDisplay.setShowStagingIcon(true);
1661                }
1662                else if (hasUpdateLayoutPermission) {
1663                    themeDisplay.setShowStagingIcon(true);
1664                }
1665            }
1666
1667            String myAccountNamespace = PortalUtil.getPortletNamespace(
1668                PortletKeys.MY_ACCOUNT);
1669
1670            String myAccountRedirect = ParamUtil.getString(
1671                request, myAccountNamespace.concat("backURL"), currentURL);
1672
1673            Group controlPanelGroup = GroupLocalServiceUtil.getGroup(
1674                companyId, GroupConstants.CONTROL_PANEL);
1675
1676            long controlPanelPlid = LayoutLocalServiceUtil.getDefaultPlid(
1677                controlPanelGroup.getGroupId(), true);
1678
1679            PortletURLImpl myAccountURL = new PortletURLImpl(
1680                request, PortletKeys.MY_ACCOUNT, controlPanelPlid,
1681                PortletRequest.RENDER_PHASE);
1682
1683            myAccountURL.setWindowState(WindowState.MAXIMIZED);
1684            myAccountURL.setPortletMode(PortletMode.VIEW);
1685            myAccountURL.setRefererPlid(plid);
1686
1687            myAccountURL.setParameter("struts_action", "/my_account/edit_user");
1688            myAccountURL.setParameter("backURL", myAccountRedirect);
1689
1690            themeDisplay.setURLMyAccount(myAccountURL);
1691        }
1692
1693        if ((!user.isActive()) ||
1694            (PrefsPropsUtil.getBoolean(
1695                companyId, PropsKeys.TERMS_OF_USE_REQUIRED) &&
1696             !user.isAgreedToTermsOfUse())) {
1697
1698            themeDisplay.setShowAddContentIcon(false);
1699            themeDisplay.setShowMyAccountIcon(false);
1700            themeDisplay.setShowPageSettingsIcon(false);
1701        }
1702
1703        themeDisplay.setURLPortal(portalURL.concat(contextPath));
1704
1705        String urlSignIn = mainPath.concat("/portal/login");
1706
1707        if (layout != null) {
1708            urlSignIn = HttpUtil.addParameter(
1709                urlSignIn, "p_l_id", layout.getPlid());
1710        }
1711
1712        themeDisplay.setURLSignIn(urlSignIn);
1713
1714        themeDisplay.setURLSignOut(mainPath.concat("/portal/logout"));
1715
1716        PortletURL updateManagerURL = new PortletURLImpl(
1717            request, PortletKeys.UPDATE_MANAGER, plid,
1718            PortletRequest.RENDER_PHASE);
1719
1720        updateManagerURL.setWindowState(WindowState.MAXIMIZED);
1721        updateManagerURL.setPortletMode(PortletMode.VIEW);
1722
1723        updateManagerURL.setParameter("struts_action", "/update_manager/view");
1724
1725        themeDisplay.setURLUpdateManager(updateManagerURL);
1726
1727        request.setAttribute(WebKeys.THEME_DISPLAY, themeDisplay);
1728
1729        // Parallel render
1730
1731        boolean parallelRenderEnable = true;
1732
1733        if (layout != null) {
1734            List<String> portletIds = layoutTypePortlet.getPortletIds();
1735
1736            if (portletIds.size() == 1) {
1737                String portletId = portletIds.get(0);
1738
1739                Portlet portlet = PortletLocalServiceUtil.getPortletById(
1740                    portletId);
1741
1742                if ((portlet != null) && !portlet.isAjaxable()) {
1743                    parallelRenderEnable = false;
1744                }
1745            }
1746        }
1747
1748        Boolean parallelRenderEnableObj = Boolean.valueOf(ParamUtil.getBoolean(
1749            request, "p_p_parallel", parallelRenderEnable));
1750
1751        request.setAttribute(
1752            WebKeys.PORTLET_PARALLEL_RENDER, parallelRenderEnableObj);
1753    }
1754
1755    protected void updateUserLayouts(User user) throws Exception {
1756        Boolean hasPowerUserRole = null;
1757
1758        // Private layouts
1759
1760        boolean addDefaultUserPrivateLayouts = false;
1761
1762        if (PropsValues.LAYOUT_USER_PRIVATE_LAYOUTS_ENABLED &&
1763            PropsValues.LAYOUT_USER_PRIVATE_LAYOUTS_AUTO_CREATE) {
1764
1765            addDefaultUserPrivateLayouts = true;
1766
1767            if (PropsValues.LAYOUT_USER_PRIVATE_LAYOUTS_POWER_USER_REQUIRED) {
1768                if (hasPowerUserRole == null) {
1769                    hasPowerUserRole = hasPowerUserRole(user);
1770                }
1771
1772                if (!hasPowerUserRole.booleanValue()) {
1773                    addDefaultUserPrivateLayouts = false;
1774                }
1775            }
1776        }
1777
1778        if (addDefaultUserPrivateLayouts && !user.hasPrivateLayouts()) {
1779            addDefaultUserPrivateLayouts(user);
1780        }
1781
1782        boolean deleteDefaultUserPrivateLayouts = false;
1783
1784        if (!PropsValues.LAYOUT_USER_PRIVATE_LAYOUTS_ENABLED) {
1785            deleteDefaultUserPrivateLayouts = true;
1786        }
1787        else if (PropsValues.LAYOUT_USER_PRIVATE_LAYOUTS_POWER_USER_REQUIRED) {
1788            if (hasPowerUserRole == null) {
1789                hasPowerUserRole = hasPowerUserRole(user);
1790            }
1791
1792            if (!hasPowerUserRole.booleanValue()) {
1793                deleteDefaultUserPrivateLayouts = true;
1794            }
1795        }
1796
1797        if (deleteDefaultUserPrivateLayouts && user.hasPrivateLayouts()) {
1798            deleteDefaultUserPrivateLayouts(user);
1799        }
1800
1801        // Public pages
1802
1803        boolean addDefaultUserPublicLayouts = false;
1804
1805        if (PropsValues.LAYOUT_USER_PUBLIC_LAYOUTS_ENABLED &&
1806            PropsValues.LAYOUT_USER_PUBLIC_LAYOUTS_AUTO_CREATE) {
1807
1808            addDefaultUserPublicLayouts = true;
1809
1810            if (PropsValues.LAYOUT_USER_PUBLIC_LAYOUTS_POWER_USER_REQUIRED) {
1811                if (hasPowerUserRole == null) {
1812                    hasPowerUserRole = hasPowerUserRole(user);
1813                }
1814
1815                if (!hasPowerUserRole.booleanValue()) {
1816                    addDefaultUserPublicLayouts = false;
1817                }
1818            }
1819        }
1820
1821        if (addDefaultUserPublicLayouts && !user.hasPublicLayouts()) {
1822            addDefaultUserPublicLayouts(user);
1823        }
1824
1825        boolean deleteDefaultUserPublicLayouts = false;
1826
1827        if (!PropsValues.LAYOUT_USER_PUBLIC_LAYOUTS_ENABLED) {
1828            deleteDefaultUserPublicLayouts = true;
1829        }
1830        else if (PropsValues.LAYOUT_USER_PUBLIC_LAYOUTS_POWER_USER_REQUIRED) {
1831            if (hasPowerUserRole == null) {
1832                hasPowerUserRole = hasPowerUserRole(user);
1833            }
1834
1835            if (!hasPowerUserRole.booleanValue()) {
1836                deleteDefaultUserPublicLayouts = true;
1837            }
1838        }
1839
1840        if (deleteDefaultUserPublicLayouts && user.hasPublicLayouts()) {
1841            deleteDefaultUserPublicLayouts(user);
1842        }
1843    }
1844
1845    protected File privateLARFile;
1846    protected File publicLARFile;
1847
1848    private static final String _PATH_PORTAL_LAYOUT = "/portal/layout";
1849
1850    private static Log _log = LogFactoryUtil.getLog(ServicePreAction.class);
1851
1852}