001    /**
002     * Copyright (c) 2000-2011 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.portlet.rolesadmin.action;
016    
017    import com.liferay.portal.NoSuchRoleException;
018    import com.liferay.portal.RolePermissionsException;
019    import com.liferay.portal.kernel.servlet.SessionErrors;
020    import com.liferay.portal.kernel.servlet.SessionMessages;
021    import com.liferay.portal.kernel.util.ArrayUtil;
022    import com.liferay.portal.kernel.util.Constants;
023    import com.liferay.portal.kernel.util.GetterUtil;
024    import com.liferay.portal.kernel.util.ListUtil;
025    import com.liferay.portal.kernel.util.ParamUtil;
026    import com.liferay.portal.kernel.util.StringUtil;
027    import com.liferay.portal.kernel.util.Validator;
028    import com.liferay.portal.model.GroupConstants;
029    import com.liferay.portal.model.ResourceConstants;
030    import com.liferay.portal.model.Role;
031    import com.liferay.portal.model.RoleConstants;
032    import com.liferay.portal.security.auth.PrincipalException;
033    import com.liferay.portal.security.permission.ResourceActionsUtil;
034    import com.liferay.portal.security.permission.comparator.ActionComparator;
035    import com.liferay.portal.service.PermissionServiceUtil;
036    import com.liferay.portal.service.ResourceBlockLocalServiceUtil;
037    import com.liferay.portal.service.ResourceBlockServiceUtil;
038    import com.liferay.portal.service.ResourcePermissionServiceUtil;
039    import com.liferay.portal.service.RoleLocalServiceUtil;
040    import com.liferay.portal.struts.PortletAction;
041    import com.liferay.portal.theme.ThemeDisplay;
042    import com.liferay.portal.util.PortalUtil;
043    import com.liferay.portal.util.PropsValues;
044    import com.liferay.portal.util.WebKeys;
045    
046    import java.util.HashMap;
047    import java.util.List;
048    import java.util.Map;
049    
050    import javax.portlet.ActionRequest;
051    import javax.portlet.ActionResponse;
052    import javax.portlet.PortletConfig;
053    import javax.portlet.RenderRequest;
054    import javax.portlet.RenderResponse;
055    
056    import org.apache.struts.action.ActionForm;
057    import org.apache.struts.action.ActionForward;
058    import org.apache.struts.action.ActionMapping;
059    
060    /**
061     * @author Brian Wing Shun Chan
062     * @author Jorge Ferrer
063     * @author Connor McKay
064     */
065    public class EditRolePermissionsAction extends PortletAction {
066    
067            @Override
068            public void processAction(
069                            ActionMapping mapping, ActionForm form, PortletConfig portletConfig,
070                            ActionRequest actionRequest, ActionResponse actionResponse)
071                    throws Exception {
072    
073                    String cmd = ParamUtil.getString(actionRequest, Constants.CMD);
074    
075                    try {
076                            if (cmd.equals("actions")) {
077                                    updateActions(actionRequest, actionResponse);
078                            }
079                            else if (cmd.equals("delete_permission")) {
080                                    deletePermission(actionRequest, actionResponse);
081                            }
082                    }
083                    catch (Exception e) {
084                            if (e instanceof NoSuchRoleException ||
085                                    e instanceof PrincipalException ||
086                                    e instanceof RolePermissionsException) {
087    
088                                    SessionErrors.add(actionRequest, e.getClass().getName());
089    
090                                    setForward(actionRequest, "portlet.roles_admin.error");
091                            }
092                            else {
093                                    throw e;
094                            }
095                    }
096            }
097    
098            @Override
099            public ActionForward render(
100                            ActionMapping mapping, ActionForm form, PortletConfig portletConfig,
101                            RenderRequest renderRequest, RenderResponse renderResponse)
102                    throws Exception {
103    
104                    try {
105                            ActionUtil.getRole(renderRequest);
106                    }
107                    catch (Exception e) {
108                            if (e instanceof NoSuchRoleException ||
109                                    e instanceof PrincipalException) {
110    
111                                    SessionErrors.add(renderRequest, e.getClass().getName());
112    
113                                    return mapping.findForward("portlet.roles_admin.error");
114                            }
115                            else {
116                                    throw e;
117                            }
118                    }
119    
120                    return mapping.findForward(getForward(
121                            renderRequest, "portlet.roles_admin.edit_role_permissions"));
122            }
123    
124            protected void deletePermission(
125                            ActionRequest actionRequest, ActionResponse actionResponse)
126                    throws Exception {
127    
128                    ThemeDisplay themeDisplay = (ThemeDisplay)actionRequest.getAttribute(
129                            WebKeys.THEME_DISPLAY);
130    
131                    long roleId = ParamUtil.getLong(actionRequest, "roleId");
132                    long permissionId = ParamUtil.getLong(actionRequest, "permissionId");
133                    String name = ParamUtil.getString(actionRequest, "name");
134                    int scope = ParamUtil.getInteger(actionRequest, "scope");
135                    String primKey = ParamUtil.getString(actionRequest, "primKey");
136                    String actionId = ParamUtil.getString(actionRequest, "actionId");
137    
138                    Role role = RoleLocalServiceUtil.getRole(roleId);
139    
140                    String roleName = role.getName();
141    
142                    if (roleName.equals(RoleConstants.ADMINISTRATOR) ||
143                            roleName.equals(RoleConstants.ORGANIZATION_ADMINISTRATOR) ||
144                            roleName.equals(RoleConstants.ORGANIZATION_OWNER) ||
145                            roleName.equals(RoleConstants.OWNER) ||
146                            roleName.equals(RoleConstants.SITE_ADMINISTRATOR) ||
147                            roleName.equals(RoleConstants.SITE_OWNER)) {
148    
149                            throw new RolePermissionsException(roleName);
150                    }
151    
152                    if (PropsValues.PERMISSIONS_USER_CHECK_ALGORITHM == 6) {
153                            if (ResourceBlockLocalServiceUtil.isSupported(name)) {
154                                    if (scope == ResourceConstants.SCOPE_GROUP) {
155                                            ResourceBlockServiceUtil.removeGroupScopePermission(
156                                                    themeDisplay.getScopeGroupId(),
157                                                    themeDisplay.getCompanyId(),
158                                                    GetterUtil.getLong(primKey), name, roleId, actionId);
159                                    }
160                                    else {
161                                            ResourceBlockServiceUtil.removeCompanyScopePermission(
162                                                    themeDisplay.getScopeGroupId(),
163                                                    themeDisplay.getCompanyId(), name, roleId, actionId);
164                                    }
165                            }
166                            else {
167                                    ResourcePermissionServiceUtil.removeResourcePermission(
168                                            themeDisplay.getScopeGroupId(), themeDisplay.getCompanyId(),
169                                            name, scope, primKey, roleId, actionId);
170                            }
171                    }
172                    else {
173                            PermissionServiceUtil.unsetRolePermission(
174                                    roleId, themeDisplay.getScopeGroupId(), permissionId);
175                    }
176    
177                    // Send redirect
178    
179                    SessionMessages.add(actionRequest, "permissionDeleted");
180    
181                    String redirect = PortalUtil.escapeRedirect(
182                            ParamUtil.getString(actionRequest, "redirect"));
183    
184                    if (Validator.isNotNull(redirect)) {
185                            actionResponse.sendRedirect(redirect);
186                    }
187            }
188    
189            protected void updateAction_1to5(
190                            Role role, long groupId, String selResource, String actionId,
191                            boolean selected, int scope, String[] groupIds)
192                    throws Exception {
193    
194                    long roleId = role.getRoleId();
195    
196                    if (selected) {
197                            if (scope == ResourceConstants.SCOPE_COMPANY) {
198                                    PermissionServiceUtil.setRolePermission(
199                                            roleId, groupId, selResource, scope,
200                                            String.valueOf(role.getCompanyId()), actionId);
201                            }
202                            else if (scope == ResourceConstants.SCOPE_GROUP_TEMPLATE) {
203                                    PermissionServiceUtil.setRolePermission(
204                                            roleId, groupId, selResource,
205                                            ResourceConstants.SCOPE_GROUP_TEMPLATE,
206                                            String.valueOf(GroupConstants.DEFAULT_PARENT_GROUP_ID),
207                                            actionId);
208                            }
209                            else {
210                                    PermissionServiceUtil.unsetRolePermissions(
211                                            roleId, groupId, selResource, ResourceConstants.SCOPE_GROUP,
212                                            actionId);
213    
214                                    for (String curGroupId : groupIds) {
215                                            PermissionServiceUtil.setRolePermission(
216                                                    roleId, groupId, selResource,
217                                                    ResourceConstants.SCOPE_GROUP, curGroupId, actionId);
218                                    }
219                            }
220                    }
221                    else {
222    
223                            // Remove company, group template, and group permissions
224    
225                            PermissionServiceUtil.unsetRolePermissions(
226                                    roleId, groupId, selResource, ResourceConstants.SCOPE_COMPANY,
227                                    actionId);
228    
229                            PermissionServiceUtil.unsetRolePermissions(
230                                    roleId, groupId, selResource,
231                                    ResourceConstants.SCOPE_GROUP_TEMPLATE, actionId);
232    
233                            PermissionServiceUtil.unsetRolePermissions(
234                                    roleId, groupId, selResource, ResourceConstants.SCOPE_GROUP,
235                                    actionId);
236                    }
237            }
238    
239            protected void updateAction_6(
240                            Role role, long groupId, String selResource, String actionId,
241                            boolean selected, int scope, String[] groupIds)
242                    throws Exception {
243    
244                    long companyId = role.getCompanyId();
245                    long roleId = role.getRoleId();
246    
247                    if (selected) {
248                            if (scope == ResourceConstants.SCOPE_COMPANY) {
249                                    ResourcePermissionServiceUtil.addResourcePermission(
250                                            groupId, companyId, selResource, scope,
251                                            String.valueOf(role.getCompanyId()), roleId, actionId);
252                            }
253                            else if (scope == ResourceConstants.SCOPE_GROUP_TEMPLATE) {
254                                    ResourcePermissionServiceUtil.addResourcePermission(
255                                            groupId, companyId, selResource,
256                                            ResourceConstants.SCOPE_GROUP_TEMPLATE,
257                                            String.valueOf(GroupConstants.DEFAULT_PARENT_GROUP_ID),
258                                            roleId, actionId);
259                            }
260                            else if (scope == ResourceConstants.SCOPE_GROUP) {
261                                    ResourcePermissionServiceUtil.removeResourcePermissions(
262                                            groupId, companyId, selResource,
263                                            ResourceConstants.SCOPE_GROUP, roleId, actionId);
264    
265                                    for (String curGroupId : groupIds) {
266                                            ResourcePermissionServiceUtil.addResourcePermission(
267                                                    groupId, companyId, selResource,
268                                                    ResourceConstants.SCOPE_GROUP, curGroupId, roleId,
269                                                    actionId);
270                                    }
271                            }
272                    }
273                    else {
274    
275                            // Remove company, group template, and group permissions
276    
277                            ResourcePermissionServiceUtil.removeResourcePermissions(
278                                    groupId, companyId, selResource,
279                                    ResourceConstants.SCOPE_COMPANY, roleId, actionId);
280    
281                            ResourcePermissionServiceUtil.removeResourcePermissions(
282                                    groupId, companyId, selResource,
283                                    ResourceConstants.SCOPE_GROUP_TEMPLATE, roleId, actionId);
284    
285                            ResourcePermissionServiceUtil.removeResourcePermissions(
286                                    groupId, companyId, selResource, ResourceConstants.SCOPE_GROUP,
287                                    roleId, actionId);
288                    }
289            }
290    
291            protected void updateActions_6Blocks(
292                            Role role, long scopeGroupId, String selResource, String actionId,
293                            boolean selected, int scope, String[] groupIds)
294                    throws Exception {
295    
296                    long companyId = role.getCompanyId();
297                    long roleId = role.getRoleId();
298    
299                    if (selected) {
300                            if (scope == ResourceConstants.SCOPE_GROUP) {
301                                    ResourceBlockServiceUtil.removeAllGroupScopePermissions(
302                                            scopeGroupId, companyId, selResource, roleId, actionId);
303                                    ResourceBlockServiceUtil.removeCompanyScopePermission(
304                                            scopeGroupId, companyId, selResource, roleId, actionId);
305    
306                                    for (String groupId : groupIds) {
307                                            ResourceBlockServiceUtil.addGroupScopePermission(
308                                                    scopeGroupId, companyId, GetterUtil.getLong(groupId),
309                                                    selResource, roleId, actionId);
310                                    }
311                            }
312                            else {
313                                    ResourceBlockServiceUtil.removeAllGroupScopePermissions(
314                                            scopeGroupId, companyId, selResource, roleId, actionId);
315                                    ResourceBlockServiceUtil.addCompanyScopePermission(
316                                            scopeGroupId, companyId, selResource, roleId, actionId);
317                            }
318                    }
319                    else {
320                            ResourceBlockServiceUtil.removeAllGroupScopePermissions(
321                                    scopeGroupId, companyId, selResource, roleId, actionId);
322                            ResourceBlockServiceUtil.removeCompanyScopePermission(
323                                    scopeGroupId, companyId, selResource, roleId, actionId);
324                    }
325            }
326    
327            protected void updateActions(
328                            ActionRequest actionRequest, ActionResponse actionResponse)
329                    throws Exception {
330    
331                    ThemeDisplay themeDisplay = (ThemeDisplay)actionRequest.getAttribute(
332                            WebKeys.THEME_DISPLAY);
333    
334                    long roleId = ParamUtil.getLong(actionRequest, "roleId");
335    
336                    Role role = RoleLocalServiceUtil.getRole(roleId);
337    
338                    String roleName = role.getName();
339    
340                    if (roleName.equals(RoleConstants.ADMINISTRATOR) ||
341                            roleName.equals(RoleConstants.ORGANIZATION_ADMINISTRATOR) ||
342                            roleName.equals(RoleConstants.ORGANIZATION_OWNER) ||
343                            roleName.equals(RoleConstants.OWNER) ||
344                            roleName.equals(RoleConstants.SITE_ADMINISTRATOR) ||
345                            roleName.equals(RoleConstants.SITE_OWNER)) {
346    
347                            throw new RolePermissionsException(roleName);
348                    }
349    
350                    String portletResource = ParamUtil.getString(
351                            actionRequest, "portletResource");
352                    String[] modelResources = StringUtil.split(
353                            ParamUtil.getString(actionRequest, "modelResources"));
354                    boolean showModelResources = ParamUtil.getBoolean(
355                            actionRequest, "showModelResources");
356    
357                    Map<String, List<String>> resourceActionsMap =
358                            new HashMap<String, List<String>>();
359    
360                    if (showModelResources) {
361                            for (String modelResource : modelResources) {
362                                    resourceActionsMap.put(
363                                            modelResource,
364                                            ResourceActionsUtil.getResourceActions(
365                                                    null, modelResource));
366                            }
367                    }
368                    else if (Validator.isNotNull(portletResource)) {
369                            resourceActionsMap.put(
370                                    portletResource,
371                                    ResourceActionsUtil.getResourceActions(portletResource, null));
372                    }
373    
374                    String[] selectedTargets = StringUtil.split(
375                            ParamUtil.getString(actionRequest, "selectedTargets"));
376    
377                    for (Map.Entry<String, List<String>> entry :
378                                    resourceActionsMap.entrySet()) {
379    
380                            String selResource = entry.getKey();
381                            List<String> actions = entry.getValue();
382    
383                            actions = ListUtil.sort(
384                                    actions, new ActionComparator(themeDisplay.getLocale()));
385    
386                            for (String actionId : actions) {
387                                    String target = selResource + actionId;
388    
389                                    boolean selected = ArrayUtil.contains(selectedTargets, target);
390    
391                                    String[] groupIds = StringUtil.split(
392                                            ParamUtil.getString(actionRequest, "groupIds" + target));
393    
394                                    groupIds = ArrayUtil.distinct(groupIds);
395    
396                                    int scope = ResourceConstants.SCOPE_COMPANY;
397    
398                                    if ((role.getType() == RoleConstants.TYPE_ORGANIZATION) ||
399                                            (role.getType() == RoleConstants.TYPE_PROVIDER) ||
400                                            (role.getType() == RoleConstants.TYPE_SITE)) {
401    
402                                            scope = ResourceConstants.SCOPE_GROUP_TEMPLATE;
403                                    }
404                                    else {
405                                            if (groupIds.length > 0) {
406                                                    scope = ResourceConstants.SCOPE_GROUP;
407                                            }
408                                    }
409    
410                                    if (PropsValues.PERMISSIONS_USER_CHECK_ALGORITHM == 6) {
411                                            if (ResourceBlockLocalServiceUtil.isSupported(
412                                                            selResource)) {
413    
414                                                    updateActions_6Blocks(
415                                                            role, themeDisplay.getScopeGroupId(), selResource,
416                                                            actionId, selected, scope, groupIds);
417                                            }
418                                            else {
419                                                    updateAction_6(
420                                                            role, themeDisplay.getScopeGroupId(), selResource,
421                                                            actionId, selected, scope, groupIds);
422                                            }
423                                    }
424                                    else {
425                                            updateAction_1to5(
426                                                    role, themeDisplay.getScopeGroupId(), selResource,
427                                                    actionId, selected, scope, groupIds);
428                                    }
429                            }
430                    }
431    
432                    // Send redirect
433    
434                    SessionMessages.add(actionRequest, "permissionsUpdated");
435    
436                    String redirect = PortalUtil.escapeRedirect(
437                            ParamUtil.getString(actionRequest, "redirect"));
438    
439                    if (Validator.isNotNull(redirect)) {
440                            redirect = redirect + "&" + Constants.CMD + "=" + Constants.VIEW;
441    
442                            actionResponse.sendRedirect(redirect);
443                    }
444            }
445    
446    }