001    /**
002     * Copyright (c) 2000-2012 Liferay, Inc. All rights reserved.
003     *
004     * This library is free software; you can redistribute it and/or modify it under
005     * the terms of the GNU Lesser General Public License as published by the Free
006     * Software Foundation; either version 2.1 of the License, or (at your option)
007     * any later version.
008     *
009     * This library is distributed in the hope that it will be useful, but WITHOUT
010     * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
011     * FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more
012     * details.
013     */
014    
015    package com.liferay.portal.verify;
016    
017    import com.liferay.portal.NoSuchResourceException;
018    import com.liferay.portal.kernel.dao.orm.DynamicQuery;
019    import com.liferay.portal.kernel.dao.orm.DynamicQueryFactoryUtil;
020    import com.liferay.portal.kernel.dao.orm.RestrictionsFactoryUtil;
021    import com.liferay.portal.kernel.log.Log;
022    import com.liferay.portal.kernel.log.LogFactoryUtil;
023    import com.liferay.portal.kernel.util.GetterUtil;
024    import com.liferay.portal.model.Group;
025    import com.liferay.portal.model.Layout;
026    import com.liferay.portal.model.Organization;
027    import com.liferay.portal.model.Permission;
028    import com.liferay.portal.model.Resource;
029    import com.liferay.portal.model.ResourceCode;
030    import com.liferay.portal.model.ResourcePermission;
031    import com.liferay.portal.model.Role;
032    import com.liferay.portal.model.RoleConstants;
033    import com.liferay.portal.security.permission.ActionKeys;
034    import com.liferay.portal.security.permission.PermissionCacheUtil;
035    import com.liferay.portal.security.permission.ResourceActionsUtil;
036    import com.liferay.portal.service.LayoutLocalServiceUtil;
037    import com.liferay.portal.service.PermissionLocalServiceUtil;
038    import com.liferay.portal.service.ResourceActionLocalServiceUtil;
039    import com.liferay.portal.service.ResourceCodeLocalServiceUtil;
040    import com.liferay.portal.service.ResourceLocalServiceUtil;
041    import com.liferay.portal.service.ResourcePermissionLocalServiceUtil;
042    import com.liferay.portal.service.RoleLocalServiceUtil;
043    import com.liferay.portal.service.UserLocalServiceUtil;
044    import com.liferay.portal.service.impl.ResourcePermissionLocalServiceImpl;
045    import com.liferay.portal.util.PortalInstances;
046    import com.liferay.portal.util.PropsValues;
047    
048    import java.util.List;
049    
050    /**
051     * @author Tobias Kaefer
052     * @author Douglas Wong
053     * @author Matthew Kong
054     * @author Raymond Augé
055     */
056    public class VerifyPermission extends VerifyProcess {
057    
058            protected void checkPermissions() throws Exception {
059                    List<String> modelNames = ResourceActionsUtil.getModelNames();
060    
061                    for (String modelName : modelNames) {
062                            List<String> actionIds =
063                                    ResourceActionsUtil.getModelResourceActions(modelName);
064    
065                            if (PropsValues.PERMISSIONS_USER_CHECK_ALGORITHM == 5) {
066                                    PermissionLocalServiceUtil.checkPermissions(
067                                            modelName, actionIds);
068                            }
069                            else if (PropsValues.PERMISSIONS_USER_CHECK_ALGORITHM == 6) {
070                                    ResourceActionLocalServiceUtil.checkResourceActions(
071                                            modelName, actionIds, true);
072                            }
073                    }
074            }
075    
076            protected void deleteDefaultPrivateLayoutPermissions() throws Exception {
077                    long[] companyIds = PortalInstances.getCompanyIdsBySQL();
078    
079                    for (long companyId : companyIds) {
080                            try {
081                                    if (PropsValues.PERMISSIONS_USER_CHECK_ALGORITHM == 5) {
082                                            deleteDefaultPrivateLayoutPermissions_5(companyId);
083                                    }
084                                    else if (PropsValues.PERMISSIONS_USER_CHECK_ALGORITHM == 6) {
085                                            deleteDefaultPrivateLayoutPermissions_6(companyId);
086                                    }
087                                    else {
088                                            deleteDefaultPrivateLayoutPermissions_1to4(companyId);
089                                    }
090                            }
091                            catch (Exception e) {
092                                    if (_log.isDebugEnabled()) {
093                                            _log.debug(e, e);
094                                    }
095                            }
096                    }
097            }
098    
099            protected void deleteDefaultPrivateLayoutPermissions_1to4(long companyId)
100                    throws Exception {
101    
102                    long defaultUserId = UserLocalServiceUtil.getDefaultUserId(companyId);
103    
104                    List<Permission> permissions =
105                            PermissionLocalServiceUtil.getUserPermissions(defaultUserId);
106    
107                    for (Permission permission : permissions) {
108                            Resource resource = ResourceLocalServiceUtil.getResource(
109                                    permission.getResourceId());
110    
111                            ResourceCode resourceCode =
112                                    ResourceCodeLocalServiceUtil.getResourceCode(
113                                            resource.getCodeId());
114    
115                            if (isPrivateLayout(
116                                            resourceCode.getName(), resource.getPrimKey())) {
117    
118                                    String[] actionIds = new String[] {permission.getActionId()};
119    
120                                    PermissionLocalServiceUtil.unsetUserPermissions(
121                                            defaultUserId, actionIds, permission.getResourceId());
122                            }
123                    }
124            }
125    
126            protected void deleteDefaultPrivateLayoutPermissions_5(long companyId)
127                    throws Exception {
128    
129                    Role role = RoleLocalServiceUtil.getRole(
130                            companyId, RoleConstants.GUEST);
131    
132                    List<Permission> permissions =
133                            PermissionLocalServiceUtil.getRolePermissions(role.getRoleId());
134    
135                    for (Permission permission : permissions) {
136                            Resource resource = ResourceLocalServiceUtil.getResource(
137                                    permission.getResourceId());
138    
139                            ResourceCode resourceCode =
140                                    ResourceCodeLocalServiceUtil.getResourceCode(
141                                            resource.getCodeId());
142    
143                            if (isPrivateLayout(
144                                            resourceCode.getName(), resource.getPrimKey())) {
145    
146                                    PermissionLocalServiceUtil.unsetRolePermission(
147                                            role.getRoleId(), permission.getPermissionId());
148                            }
149                    }
150            }
151    
152            protected void deleteDefaultPrivateLayoutPermissions_6(long companyId)
153                    throws Exception {
154    
155                    Role role = RoleLocalServiceUtil.getRole(
156                            companyId, RoleConstants.GUEST);
157    
158                    List<ResourcePermission> resourcePermissions =
159                            ResourcePermissionLocalServiceUtil.getRoleResourcePermissions(
160                                    role.getRoleId());
161    
162                    for (ResourcePermission resourcePermission : resourcePermissions) {
163                            if (isPrivateLayout(
164                                            resourcePermission.getName(),
165                                            resourcePermission.getPrimKey())) {
166    
167                                    ResourcePermissionLocalServiceUtil.deleteResourcePermission(
168                                            resourcePermission.getResourcePermissionId());
169                            }
170                    }
171            }
172    
173            @Override
174            protected void doVerify() throws Exception {
175                    deleteDefaultPrivateLayoutPermissions();
176    
177                    if ((PropsValues.PERMISSIONS_USER_CHECK_ALGORITHM != 5) &&
178                            (PropsValues.PERMISSIONS_USER_CHECK_ALGORITHM != 6)) {
179    
180                            return;
181                    }
182    
183                    checkPermissions();
184                    fixOrganizationRolePermissions();
185            }
186    
187            protected void fixOrganizationRolePermissions() throws Exception {
188                    if (PropsValues.PERMISSIONS_USER_CHECK_ALGORITHM == 5) {
189                            fixOrganizationRolePermissions_5();
190                    }
191                    else if (PropsValues.PERMISSIONS_USER_CHECK_ALGORITHM == 6) {
192                            fixOrganizationRolePermissions_6();
193                    }
194    
195                    PermissionCacheUtil.clearCache();
196            }
197    
198            protected void fixOrganizationRolePermissions_5() throws Exception {
199                    DynamicQuery dynamicQuery = DynamicQueryFactoryUtil.forClass(
200                            ResourceCode.class);
201    
202                    dynamicQuery.add(
203                            RestrictionsFactoryUtil.eq("name", Organization.class.getName()));
204    
205                    List<ResourceCode> resouceCodes =
206                            ResourceCodeLocalServiceUtil.dynamicQuery(dynamicQuery);
207    
208                    for (ResourceCode resourceCode : resouceCodes) {
209                            dynamicQuery = DynamicQueryFactoryUtil.forClass(Resource.class);
210    
211                            dynamicQuery.add(
212                                    RestrictionsFactoryUtil.eq("codeId", resourceCode.getCodeId()));
213    
214                            List<Resource> resources = ResourceLocalServiceUtil.dynamicQuery(
215                                    dynamicQuery);
216    
217                            for (Resource resource : resources) {
218                                    dynamicQuery = DynamicQueryFactoryUtil.forClass(
219                                            Permission.class);
220    
221                                    dynamicQuery.add(
222                                            RestrictionsFactoryUtil.eq(
223                                                    "resourceId", resource.getResourceId()));
224    
225                                    List<Permission> permissions =
226                                            PermissionLocalServiceUtil.dynamicQuery(dynamicQuery);
227    
228                                    processPermissions(resource, permissions);
229                            }
230                    }
231            }
232    
233            protected void fixOrganizationRolePermissions_6() throws Exception {
234                    DynamicQuery dynamicQuery = DynamicQueryFactoryUtil.forClass(
235                            ResourcePermission.class);
236    
237                    dynamicQuery.add(
238                            RestrictionsFactoryUtil.eq("name", Organization.class.getName()));
239    
240                    List<ResourcePermission> resourcePermissions =
241                            ResourcePermissionLocalServiceUtil.dynamicQuery(dynamicQuery);
242    
243                    for (ResourcePermission resourcePermission : resourcePermissions) {
244                            ResourcePermission groupResourcePermission = null;
245    
246                            try {
247                                    groupResourcePermission =
248                                            ResourcePermissionLocalServiceUtil.getResourcePermission(
249                                                    resourcePermission.getCompanyId(),
250                                                    Group.class.getName(), resourcePermission.getScope(),
251                                                    resourcePermission.getPrimKey(),
252                                                    resourcePermission.getRoleId());
253                            }
254                            catch (Exception e) {
255                                    ResourcePermissionLocalServiceUtil.setResourcePermissions(
256                                            resourcePermission.getCompanyId(), Group.class.getName(),
257                                            resourcePermission.getScope(),
258                                            resourcePermission.getPrimKey(),
259                                            resourcePermission.getRoleId(),
260                                            ResourcePermissionLocalServiceImpl.EMPTY_ACTION_IDS);
261    
262                                    groupResourcePermission =
263                                            ResourcePermissionLocalServiceUtil.getResourcePermission(
264                                                    resourcePermission.getCompanyId(),
265                                                    Group.class.getName(), resourcePermission.getScope(),
266                                                    resourcePermission.getPrimKey(),
267                                                    resourcePermission.getRoleId());
268                            }
269    
270                            long organizationActions = resourcePermission.getActionIds();
271                            long groupActions = groupResourcePermission.getActionIds();
272    
273                            for (Object[] actionIdToMask : _ORGANIZATION_ACTION_IDS_TO_MASKS) {
274                                    long organizationActionMask = (Long)actionIdToMask[1];
275                                    long groupActionMask = (Long)actionIdToMask[2];
276    
277                                    if ((organizationActions & organizationActionMask) ==
278                                                    organizationActionMask) {
279    
280                                            organizationActions =
281                                                    organizationActions & (~organizationActionMask);
282                                            groupActions = groupActions | groupActionMask;
283                                    }
284                            }
285    
286                            try {
287                                    resourcePermission.resetOriginalValues();
288    
289                                    resourcePermission.setActionIds(organizationActions);
290    
291                                    ResourcePermissionLocalServiceUtil.updateResourcePermission(
292                                            resourcePermission, false);
293    
294                                    groupResourcePermission.resetOriginalValues();
295                                    groupResourcePermission.setActionIds(groupActions);
296    
297                                    ResourcePermissionLocalServiceUtil.updateResourcePermission(
298                                            groupResourcePermission, false);
299                            }
300                            catch (Exception e) {
301                                    _log.error(e, e);
302                            }
303                    }
304            }
305    
306            protected boolean isPrivateLayout(String name, String primKey)
307                    throws Exception {
308    
309                    if (!name.equals(Layout.class.getName())) {
310                            return false;
311                    }
312    
313                    long plid = GetterUtil.getLong(primKey);
314    
315                    Layout layout = LayoutLocalServiceUtil.getLayout(plid);
316    
317                    if (layout.isPublicLayout() || layout.isTypeControlPanel()) {
318                            return false;
319                    }
320    
321                    return true;
322            }
323    
324            protected void processPermissions(
325                            Resource resource, List<Permission> permissions)
326                    throws Exception {
327    
328                    Resource groupResource = null;
329    
330                    try {
331                            groupResource = ResourceLocalServiceUtil.getResource(
332                                    resource.getCompanyId(), Group.class.getName(),
333                                    resource.getScope(), resource.getPrimKey());
334                    }
335                    catch (NoSuchResourceException nsre) {
336                            groupResource = ResourceLocalServiceUtil.addResource(
337                                    resource.getCompanyId(), Group.class.getName(),
338                                    resource.getScope(), resource.getPrimKey());
339                    }
340    
341                    for (Permission permission : permissions) {
342                            for (Object[] actionIdToMask : _ORGANIZATION_ACTION_IDS_TO_MASKS) {
343                                    String actionId = (String)actionIdToMask[0];
344                                    long mask = (Long)actionIdToMask[2];
345    
346                                    if (!actionId.equals(permission.getActionId())) {
347                                            continue;
348                                    }
349    
350                                    try {
351                                            if (mask != 0L) {
352                                                    permission.resetOriginalValues();
353    
354                                                    permission.setResourceId(groupResource.getResourceId());
355    
356                                                    PermissionLocalServiceUtil.updatePermission(
357                                                            permission, false);
358                                            }
359                                            else {
360                                                    PermissionLocalServiceUtil.deletePermission(
361                                                            permission.getPermissionId());
362                                            }
363                                    }
364                                    catch (Exception e) {
365                                            _log.error(e, e);
366                                    }
367    
368                                    break;
369                            }
370                    }
371            }
372    
373            private static final Object[][] _ORGANIZATION_ACTION_IDS_TO_MASKS =
374                    new Object[][] {
375                            new Object[] {"APPROVE_PROPOSAL", 2L, 0L},
376                            new Object[] {ActionKeys.ASSIGN_MEMBERS, 4L, 4L},
377                            new Object[] {"ASSIGN_REVIEWER", 8L, 0L},
378                            new Object[] {ActionKeys.MANAGE_ARCHIVED_SETUPS, 128L, 128L},
379                            new Object[] {ActionKeys.MANAGE_LAYOUTS, 256L, 256L},
380                            new Object[] {ActionKeys.MANAGE_STAGING, 512L, 512L},
381                            new Object[] {ActionKeys.MANAGE_TEAMS, 2048L, 1024L},
382                            new Object[] {ActionKeys.PUBLISH_STAGING, 16384L, 4096L}
383                    };
384    
385            private static Log _log = LogFactoryUtil.getLog(VerifyPermission.class);
386    
387    }