001/* 002 * Copyright 2020 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.report; 017 018import java.util.Collection; 019import java.util.Comparator; 020import java.util.List; 021import java.util.Objects; 022import java.util.Set; 023import java.util.function.Function; 024import java.util.stream.Collectors; 025 026import org.apache.avalon.framework.component.Component; 027import org.apache.avalon.framework.service.ServiceException; 028import org.apache.avalon.framework.service.ServiceManager; 029import org.apache.avalon.framework.service.Serviceable; 030import org.apache.commons.lang.ArrayUtils; 031import org.apache.commons.lang3.StringUtils; 032 033import org.ametys.core.right.RightManager; 034import org.ametys.core.right.RightManager.RightResult; 035import org.ametys.core.user.CurrentUserProvider; 036import org.ametys.core.user.UserIdentity; 037import org.ametys.plugins.workspaces.categories.Category; 038import org.ametys.plugins.workspaces.categories.CategoryProviderExtensionPoint; 039import org.ametys.plugins.workspaces.project.ProjectManager; 040import org.ametys.plugins.workspaces.project.objects.Project; 041 042/** 043 * Component for reporting projects 044 */ 045public class ReportHelper implements Serviceable, Component 046{ 047 /** Avalon Role */ 048 public static final String ROLE = ReportHelper.class.getName(); 049 050 /** The right id to report all project */ 051 public static final String REPORT_ALL_RIGHT_ID = "Workspaces_Reports_Right_Report_All"; 052 053 /** The id of reports service */ 054 public static final String REPORT_SERVICE_ID = "org.ametys.plugins.workspacesReports.service.Report"; 055 056 /** The current user provider */ 057 protected CurrentUserProvider _currentUserProvider; 058 059 /** The project manager */ 060 protected ProjectManager _projectManager; 061 062 /** The right manager */ 063 protected RightManager _rightManager; 064 065 /** The catgeory provider */ 066 protected CategoryProviderExtensionPoint _categoryProviderEP; 067 068 public void service(ServiceManager manager) throws ServiceException 069 { 070 _currentUserProvider = (CurrentUserProvider) manager.lookup(CurrentUserProvider.ROLE); 071 _projectManager = (ProjectManager) manager.lookup(ProjectManager.ROLE); 072 _rightManager = (RightManager) manager.lookup(RightManager.ROLE); 073 _categoryProviderEP = (CategoryProviderExtensionPoint) manager.lookup(CategoryProviderExtensionPoint.ROLE); 074 } 075 076 /** 077 * Get the available projects (the manager's project) 078 * @return the available projects for reports 079 */ 080 public List<Project> getAvailableProjects() 081 { 082 UserIdentity user = _currentUserProvider.getUser(); 083 boolean hasSuperRight = hasSuperRight(); 084 085 Function<Project, String> getProjectTitle = Project::getTitle; 086 Comparator<Project> projectTitleComparator = Comparator.comparing(getProjectTitle.andThen(StringUtils::stripAccents), String.CASE_INSENSITIVE_ORDER); 087 088 return _projectManager.getProjects() 089 .stream() 090 .filter(p -> hasSuperRight || ArrayUtils.contains(p.getManagers(), user)) 091 .sorted(projectTitleComparator) 092 .collect(Collectors.toList()); 093 } 094 095 /** 096 * Determines if the current user has right to access to all project's reports 097 * @return if the current user has right to access to all project's reports 098 */ 099 public boolean hasSuperRight() 100 { 101 return _rightManager.hasRight(_currentUserProvider.getUser(), REPORT_ALL_RIGHT_ID, "/cms") == RightResult.RIGHT_ALLOW; 102 } 103 104 /** 105 * Get the available projects (the manager's project) 106 * @param filteredProjects the filtered projects 107 * @param filteredCategories the filtered categories 108 * @return the available projects for reports 109 */ 110 public List<Project> getAvailableProjects(List<String> filteredProjects, List<String> filteredCategories) 111 { 112 return getAvailableProjects() 113 .stream() 114 .filter(p -> filteredProjects == null || filteredProjects.isEmpty() || filteredProjects.contains(p.getId())) 115 .filter(p -> _matchCategories(p, filteredCategories)) 116 .collect(Collectors.toList()); 117 } 118 119 private boolean _matchCategories(Project project, List<String> filteredCategories) 120 { 121 if (filteredCategories == null || filteredCategories.isEmpty()) 122 { 123 return true; 124 } 125 126 for (String projectCategory : project.getCategories()) 127 { 128 Category category = _categoryProviderEP.getTag(projectCategory, null); 129 if (category != null) 130 { 131 Category rootCategory = _getRootCategory(category); 132 if (filteredCategories.contains(rootCategory.getName())) 133 { 134 return true; 135 } 136 } 137 } 138 139 return false; 140 } 141 142 /** 143 * Get the available root categories 144 * @param projects the projects 145 * @return the available categories from the given projects 146 */ 147 public Set<Category> getAvailableCategories(List<Project> projects) 148 { 149 return projects.stream() 150 .map(Project::getCategories) 151 .flatMap(Collection::stream) 152 .map(id -> _categoryProviderEP.getTag(id, null)) 153 .filter(Objects::nonNull) 154 .map(c -> _getRootCategory(c)) 155 .collect(Collectors.toSet()); 156 } 157 158 private Category _getRootCategory(Category category) 159 { 160 Category parent = category; 161 while (parent.getParent() != null) 162 { 163 parent = parent.getParent(); 164 } 165 return parent; 166 } 167}