001    /**
002     * Copyright (c) 2000-2013 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.lar;
016    
017    import com.liferay.portal.kernel.lar.ExportImportPathUtil;
018    import com.liferay.portal.kernel.lar.PortletDataContext;
019    import com.liferay.portal.kernel.util.CharPool;
020    import com.liferay.portal.kernel.util.GetterUtil;
021    import com.liferay.portal.kernel.util.KeyValuePair;
022    import com.liferay.portal.kernel.util.PrimitiveLongList;
023    import com.liferay.portal.kernel.util.StringUtil;
024    import com.liferay.portal.kernel.xml.Document;
025    import com.liferay.portal.kernel.xml.Element;
026    import com.liferay.portal.kernel.xml.SAXReaderUtil;
027    import com.liferay.portal.model.Layout;
028    import com.liferay.portal.model.PortletConstants;
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.model.User;
033    import com.liferay.portal.security.permission.ResourceActionsUtil;
034    import com.liferay.portal.service.ResourcePermissionLocalServiceUtil;
035    import com.liferay.portal.service.RoleLocalServiceUtil;
036    import com.liferay.portal.service.permission.PortletPermissionUtil;
037    
038    import java.util.HashMap;
039    import java.util.List;
040    import java.util.Map;
041    import java.util.Set;
042    
043    /**
044     * @author Brian Wing Shun Chan
045     * @author Joel Kozikowski
046     * @author Charles May
047     * @author Raymond Aug??
048     * @author Jorge Ferrer
049     * @author Bruno Farache
050     * @author Zsigmond Rab
051     * @author Douglas Wong
052     */
053    public class PermissionExporter {
054    
055            public static final String ROLE_TEAM_PREFIX = "ROLE_TEAM_,*";
056    
057            protected void exportPermissions(
058                            LayoutCache layoutCache, long companyId, long groupId,
059                            String resourceName, String resourcePrimKey,
060                            Element permissionsElement, boolean portletActions)
061                    throws Exception {
062    
063                    List<Role> roles = layoutCache.getGroupRoles(groupId, resourceName);
064    
065                    List<String> actionIds = null;
066    
067                    if (portletActions) {
068                            actionIds = ResourceActionsUtil.getPortletResourceActions(
069                                    resourceName);
070                    }
071                    else {
072                            actionIds = ResourceActionsUtil.getModelResourceActions(
073                                    resourceName);
074                    }
075    
076                    if (actionIds.isEmpty()) {
077                            return;
078                    }
079    
080                    PrimitiveLongList roleIds = new PrimitiveLongList(roles.size());
081                    Map<Long, Role> roleIdsToRoles = new HashMap<Long, Role>();
082    
083                    for (Role role : roles) {
084                            String roleName = role.getName();
085    
086                            if (roleName.equals(RoleConstants.ADMINISTRATOR)) {
087                                    continue;
088                            }
089    
090                            roleIds.add(role.getRoleId());
091                            roleIdsToRoles.put(role.getRoleId(), role);
092                    }
093    
094                    Map<Long, Set<String>> roleIdsToActionIds =
095                            ResourcePermissionLocalServiceUtil.
096                                    getAvailableResourcePermissionActionIds(
097                                            companyId, resourceName, ResourceConstants.SCOPE_INDIVIDUAL,
098                                            resourcePrimKey, roleIds.getArray(), actionIds);
099    
100                    for (Role role : roleIdsToRoles.values()) {
101                            Set<String> availableActionIds = roleIdsToActionIds.get(
102                                    role.getRoleId());
103    
104                            Element roleElement = permissionsElement.addElement("role");
105    
106                            roleElement.addAttribute("name", role.getName());
107                            roleElement.addAttribute("title", role.getTitle());
108                            roleElement.addAttribute("description", role.getDescription());
109                            roleElement.addAttribute("type", String.valueOf(role.getType()));
110                            roleElement.addAttribute("subtype", role.getSubtype());
111    
112                            if ((availableActionIds == null) || availableActionIds.isEmpty()) {
113                                    continue;
114                            }
115    
116                            for (String action : availableActionIds) {
117                                    Element actionKeyElement = roleElement.addElement("action-key");
118    
119                                    actionKeyElement.addText(action);
120                            }
121                    }
122            }
123    
124            protected void exportPortletDataPermissions(
125                            PortletDataContext portletDataContext)
126                    throws Exception {
127    
128                    Document document = SAXReaderUtil.createDocument();
129    
130                    Element rootElement = document.addElement("portlet-data-permissions");
131    
132                    Map<String, List<KeyValuePair>> permissionsMap =
133                            portletDataContext.getPermissions();
134    
135                    for (Map.Entry<String, List<KeyValuePair>> entry :
136                                    permissionsMap.entrySet()) {
137    
138                            String[] permissionParts = StringUtil.split(
139                                    entry.getKey(), CharPool.POUND);
140    
141                            String resourceName = permissionParts[0];
142                            long resourcePK = GetterUtil.getLong(permissionParts[1]);
143    
144                            Element portletDataElement = rootElement.addElement("portlet-data");
145    
146                            portletDataElement.addAttribute("resource-name", resourceName);
147                            portletDataElement.addAttribute(
148                                    "resource-pk", String.valueOf(resourcePK));
149    
150                            List<KeyValuePair> permissions = entry.getValue();
151    
152                            for (KeyValuePair permission : permissions) {
153                                    String roleName = permission.getKey();
154                                    String actions = permission.getValue();
155    
156                                    Element permissionsElement = portletDataElement.addElement(
157                                            "permissions");
158    
159                                    permissionsElement.addAttribute("role-name", roleName);
160                                    permissionsElement.addAttribute("actions", actions);
161                            }
162                    }
163    
164                    portletDataContext.addZipEntry(
165                            ExportImportPathUtil.getRootPath(portletDataContext) +
166                                    "/portlet-data-permissions.xml",
167                            document.formattedString());
168            }
169    
170            protected void exportPortletPermissions(
171                            PortletDataContext portletDataContext, LayoutCache layoutCache,
172                            String portletId, Layout layout, Element portletElement)
173                    throws Exception {
174    
175                    long companyId = portletDataContext.getCompanyId();
176                    long groupId = portletDataContext.getGroupId();
177    
178                    String resourceName = PortletConstants.getRootPortletId(portletId);
179                    String resourcePrimKey = PortletPermissionUtil.getPrimaryKey(
180                            layout.getPlid(), portletId);
181    
182                    Element permissionsElement = portletElement.addElement("permissions");
183    
184                    exportPermissions(
185                            layoutCache, companyId, groupId, resourceName, resourcePrimKey,
186                            permissionsElement, true);
187            }
188    
189            protected Element exportRoles(
190                            long companyId, String resourceName, int scope,
191                            String resourcePrimKey, Element parentElement, String elName,
192                            List<Role> roles)
193                    throws Exception {
194    
195                    Element element = parentElement.addElement(elName);
196    
197                    Map<String, List<String>> resourceRoles =
198                            RoleLocalServiceUtil.getResourceRoles(
199                                    companyId, resourceName, scope, resourcePrimKey);
200    
201                    for (Map.Entry<String, List<String>> entry : resourceRoles.entrySet()) {
202                            String roleName = entry.getKey();
203    
204                            if (!hasRole(roles, roleName)) {
205                                    continue;
206                            }
207    
208                            Element roleElement = element.addElement("role");
209    
210                            roleElement.addAttribute("name", roleName);
211    
212                            List<String> actions = entry.getValue();
213    
214                            for (String action : actions) {
215                                    Element actionKeyElement = roleElement.addElement("action-key");
216    
217                                    actionKeyElement.addText(action);
218                                    actionKeyElement.addAttribute("scope", String.valueOf(scope));
219                            }
220                    }
221    
222                    return element;
223            }
224    
225            protected void exportUserRoles(
226                            LayoutCache layoutCache, long companyId, long groupId,
227                            String resourceName, Element parentElement)
228                    throws Exception {
229    
230                    Element userRolesElement = SAXReaderUtil.createElement("user-roles");
231    
232                    List<User> users = layoutCache.getGroupUsers(groupId);
233    
234                    for (User user : users) {
235                            long userId = user.getUserId();
236                            String uuid = user.getUuid();
237    
238                            List<Role> userRoles = layoutCache.getUserRoles(userId);
239    
240                            Element userElement = exportRoles(
241                                    companyId, resourceName, ResourceConstants.SCOPE_GROUP,
242                                    String.valueOf(groupId), userRolesElement, "user", userRoles);
243    
244                            if (userElement.elements().isEmpty()) {
245                                    userRolesElement.remove(userElement);
246                            }
247                            else {
248                                    userElement.addAttribute("uuid", uuid);
249                            }
250                    }
251    
252                    if (!userRolesElement.elements().isEmpty()) {
253                            parentElement.add(userRolesElement);
254                    }
255            }
256    
257            protected boolean hasRole(List<Role> roles, String roleName) {
258                    if ((roles == null) || (roles.size() == 0)) {
259                            return false;
260                    }
261    
262                    for (Role role : roles) {
263                            if (roleName.equals(role.getName())) {
264                                    return true;
265                            }
266                    }
267    
268                    return false;
269            }
270    
271    }