001/* 002 * Copyright 2018 Anyware Services 003 * 004 * Licensed under the Apache License, Version 2.0 (the "License"); 005 * you may not use this file except in compliance with the License. 006 * You may obtain a copy of the License at 007 * 008 * http://www.apache.org/licenses/LICENSE-2.0 009 * 010 * Unless required by applicable law or agreed to in writing, software 011 * distributed under the License is distributed on an "AS IS" BASIS, 012 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 013 * See the License for the specific language governing permissions and 014 * limitations under the License. 015 */ 016package org.ametys.plugins.workspaces.members; 017 018import java.io.IOException; 019import java.util.Iterator; 020import java.util.List; 021import java.util.Locale; 022import java.util.Set; 023 024import org.apache.avalon.framework.service.ServiceException; 025import org.apache.avalon.framework.service.ServiceManager; 026import org.apache.cocoon.ProcessingException; 027import org.apache.cocoon.environment.ObjectModelHelper; 028import org.apache.cocoon.environment.Request; 029import org.apache.cocoon.generation.ServiceableGenerator; 030import org.apache.cocoon.xml.AttributesImpl; 031import org.apache.cocoon.xml.XMLUtils; 032import org.apache.commons.lang.StringUtils; 033import org.apache.commons.lang3.ArrayUtils; 034import org.xml.sax.SAXException; 035 036import org.ametys.cms.contenttype.ContentType; 037import org.ametys.cms.contenttype.ContentTypeExtensionPoint; 038import org.ametys.cms.repository.Content; 039import org.ametys.core.group.GroupManager; 040import org.ametys.core.right.RightManager; 041import org.ametys.core.user.User; 042import org.ametys.core.user.UserIdentity; 043import org.ametys.plugins.core.user.UserHelper; 044import org.ametys.plugins.repository.AmetysRepositoryException; 045import org.ametys.plugins.repository.data.holder.ModelAwareDataHolder; 046import org.ametys.plugins.userdirectory.UserDirectoryHelper; 047import org.ametys.plugins.userdirectory.UserDirectoryPageHandler; 048import org.ametys.plugins.workspaces.members.JCRProjectMember.MemberType; 049import org.ametys.plugins.workspaces.members.ProjectMemberManager.ProjectMember; 050import org.ametys.plugins.workspaces.project.ProjectManager; 051import org.ametys.plugins.workspaces.project.objects.Project; 052import org.ametys.runtime.config.Config; 053import org.ametys.runtime.model.View; 054import org.ametys.runtime.model.type.DataContext; 055import org.ametys.web.WebConstants; 056import org.ametys.web.repository.page.Page; 057import org.ametys.web.repository.page.ZoneItem; 058import org.ametys.web.usermanagement.UserSignUpConfiguration; 059 060/** 061 * Generator used sax project member 062 */ 063public class ProjectMembersGenerator extends ServiceableGenerator 064{ 065 /** The project manager component */ 066 protected ProjectManager _projectManager; 067 068 /** The project member manager */ 069 protected ProjectMemberManager _projectMemberManager; 070 071 /** The user helper */ 072 protected UserHelper _userHelper; 073 074 /** The user directory helper */ 075 protected UserDirectoryHelper _userDirectoryHelper; 076 077 /** The content type extension point */ 078 protected ContentTypeExtensionPoint _cTypeEP; 079 080 /** The group manager */ 081 protected GroupManager _groupManager; 082 083 /** The sign up configuration */ 084 protected UserSignUpConfiguration _signupConfig; 085 086 /** The right manager */ 087 protected RightManager _rightManager; 088 089 @Override 090 public void service(ServiceManager serviceManager) throws ServiceException 091 { 092 _projectManager = (ProjectManager) serviceManager.lookup(ProjectManager.ROLE); 093 _projectMemberManager = (ProjectMemberManager) serviceManager.lookup(ProjectMemberManager.ROLE); 094 _userHelper = (UserHelper) serviceManager.lookup(UserHelper.ROLE); 095 _userDirectoryHelper = (UserDirectoryHelper) serviceManager.lookup(UserDirectoryHelper.ROLE); 096 _cTypeEP = (ContentTypeExtensionPoint) serviceManager.lookup(ContentTypeExtensionPoint.ROLE); 097 _groupManager = (GroupManager) serviceManager.lookup(GroupManager.ROLE); 098 _signupConfig = (UserSignUpConfiguration) serviceManager.lookup(UserSignUpConfiguration.ROLE); 099 _rightManager = (RightManager) serviceManager.lookup(RightManager.ROLE); 100 } 101 102 @Override 103 public void generate() throws IOException, SAXException, ProcessingException 104 { 105 Request request = ObjectModelHelper.getRequest(objectModel); 106 107 Page page = (Page) request.getAttribute(WebConstants.REQUEST_ATTR_PAGE); 108 String lang = page.getSitemapName(); 109 110 ZoneItem zoneItem = (ZoneItem) request.getAttribute(WebConstants.REQUEST_ATTR_ZONEITEM); 111 ModelAwareDataHolder serviceParameters2018 = zoneItem.getServiceParameters(); 112 113 long maxNbMembers = serviceParameters2018.getValue("nbMembers", false, -1L); 114 boolean expandGroup = serviceParameters2018.getValue("expandGroup", false, false); 115 116 contentHandler.startDocument(); 117 118 List<Project> projects = _projectManager.getProjectsForSite(page.getSite()); 119 Project project = projects.isEmpty() ? null : projects.get(0); 120 121 if (project == null) 122 { 123 throw new IllegalArgumentException("There is no project for site " + page.getSiteName()); 124 } 125 126 try 127 { 128 Set<ProjectMember> members = _projectMemberManager.getProjectMembers(project, expandGroup); 129 130 AttributesImpl attrs = new AttributesImpl(); 131 attrs.addCDATAAttribute("nbMembers", String.valueOf(members.size())); 132 133 String memberPageId = _getMembersPageId(project); 134 if (memberPageId != null) 135 { 136 attrs.addCDATAAttribute("memberPageId", memberPageId); 137 } 138 139 String siteName = Config.getInstance().getValue("workspaces.member.userdirectory.site.name"); 140 if (StringUtils.isNotEmpty(siteName)) 141 { 142 attrs.addCDATAAttribute("userDirectorySiteName", siteName); 143 } 144 XMLUtils.startElement(contentHandler, "project", attrs); 145 146 UserIdentity[] managers = project.getManagers(); 147 148 int count = 0; 149 Iterator<ProjectMember> it = members.iterator(); 150 while (it.hasNext() && (maxNbMembers < 1 || count < maxNbMembers)) 151 { 152 ProjectMember member = it.next(); 153 _saxMember(member, managers, lang); 154 count++; 155 } 156 157 XMLUtils.endElement(contentHandler, "project"); 158 } 159 catch (AmetysRepositoryException e) 160 { 161 throw new ProcessingException("Unable to get project members", e); 162 } 163 164 contentHandler.endDocument(); 165 } 166 167 /** 168 * Get the id of member page if exists and current user has access 169 * @param project The project 170 * @return the id of member page. Can be null. 171 */ 172 protected String _getMembersPageId(Project project) 173 { 174 Set<Page> memberPages = _projectManager.getModulePages(project, MembersWorkspaceModule.MEMBERS_MODULE_ID); 175 176 if (!memberPages.isEmpty()) 177 { 178 Page memberPage = memberPages.iterator().next(); 179 180 if (_rightManager.currentUserHasReadAccess(memberPage)) 181 { 182 return memberPage.getId(); 183 } 184 } 185 186 return null; 187 } 188 /** 189 * SAX a member 190 * @param member the member 191 * @param managers the user identities of project's manager 192 * @param lang the current language 193 * @throws SAXException if an error occurred while saxing 194 * @throws AmetysRepositoryException if an error occurred 195 * @throws IOException if failed to sax user content 196 */ 197 protected void _saxMember (ProjectMember member, UserIdentity[] managers, String lang) throws SAXException, AmetysRepositoryException, IOException 198 { 199 AttributesImpl attrs = new AttributesImpl(); 200 attrs.addCDATAAttribute("manager", String.valueOf(member.isManager())); 201 202 if (member.isManager()) 203 { 204 // Get the position of this manager 205 int position = ArrayUtils.indexOf(managers, member.getUser().getIdentity()); 206 attrs.addCDATAAttribute("managerPosition", String.valueOf(position + 1)); 207 } 208 209 attrs.addCDATAAttribute("type", member.getType().name().toLowerCase()); 210 211 XMLUtils.startElement(contentHandler, "member", attrs); 212 213 XMLUtils.createElement(contentHandler, "title", member.getTitle()); 214 XMLUtils.createElement(contentHandler, "sortabletitle", member.getSortableTitle()); 215 String role = member.getRole(); 216 if (StringUtils.isNotBlank(role)) 217 { 218 XMLUtils.createElement(contentHandler, "role", role); 219 } 220 221 if (member.getType().equals(MemberType.USER)) 222 { 223 User user = member.getUser(); 224 _saxUser(user, lang); 225 } 226 227 XMLUtils.endElement(contentHandler, "member"); 228 } 229 230 /** 231 * Sax user 232 * @param user the user 233 * @param lang the lang 234 * @throws SAXException if an error occurs saxing data 235 * @throws AmetysRepositoryException if an repository error occurs 236 * @throws IOException if an IO exception error occurs 237 */ 238 protected void _saxUser(User user, String lang) throws SAXException, AmetysRepositoryException, IOException 239 { 240 XMLUtils.startElement(contentHandler, "user"); 241 _userHelper.saxUser(user, contentHandler, "info"); 242 Content userContent = _userDirectoryHelper.getUserContent(user.getIdentity(), lang); 243 if (userContent != null) 244 { 245 AttributesImpl contentAttrs = new AttributesImpl(); 246 contentAttrs.addCDATAAttribute("id", userContent.getId()); 247 XMLUtils.startElement(contentHandler, "content", contentAttrs); 248 ContentType contentType = _cTypeEP.getExtension(UserDirectoryPageHandler.ABSTRACT_USER_CONTENT_TYPE); 249 View view = contentType.getView("abstract"); 250 userContent.dataToSAX(contentHandler, view, DataContext.newInstance().withLocale(new Locale(lang)).withEmptyValues(false)); 251 XMLUtils.endElement(contentHandler, "content"); 252 } 253 XMLUtils.endElement(contentHandler, "user"); 254 255 } 256}