/* * This program is free software; you can redistribute it and/or * modify it under the terms of the GNU General Public License * as published by the Free Software Foundation; either version 2 * of the License, or (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */ package net.rrm.ehour.report.service; import com.google.common.collect.Lists; import net.rrm.ehour.audit.annot.NonAuditable; import net.rrm.ehour.domain.*; import net.rrm.ehour.persistence.project.dao.ProjectDao; import net.rrm.ehour.persistence.report.dao.ReportAggregatedDao; import net.rrm.ehour.persistence.user.dao.UserDao; import net.rrm.ehour.report.criteria.AvailableCriteria; import net.rrm.ehour.report.criteria.ReportCriteria; import net.rrm.ehour.report.criteria.ReportCriteriaUpdateType; import net.rrm.ehour.report.criteria.UserSelectedCriteria; import net.rrm.ehour.timesheet.service.TimesheetLockService; import org.apache.commons.collections.CollectionUtils; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.stereotype.Service; import scala.Tuple2; import scala.collection.convert.WrapAsJava$; import java.util.Collection; import java.util.List; import static net.rrm.ehour.report.criteria.ReportCriteriaUpdateType.UPDATE_CUSTOMERS_AND_PROJECTS; /** * Report Criteria services */ @NonAuditable @Service("reportCriteriaService") public class ReportCriteriaServiceImpl implements ReportCriteriaService { private ReportAggregatedDao reportAggregatedDAO; private CustomerAndProjectCriteriaFilter customerAndProjectCriteriaFilter; private UserAndDepartmentCriteriaFilter userAndDepartmentCriteriaFilter; private IndividualUserCriteriaSync individualUserCriteriaSync; private TimesheetLockService lockService; private UserDao userDao; private ProjectDao projectDao; protected ReportCriteriaServiceImpl() { } @Autowired public ReportCriteriaServiceImpl(ReportAggregatedDao reportAggregatedDAO, CustomerAndProjectCriteriaFilter customerAndProjectCriteriaFilter, UserAndDepartmentCriteriaFilter userAndDepartmentCriteriaFilter, IndividualUserCriteriaSync individualUserCriteriaSync, TimesheetLockService lockService, UserDao userDao, ProjectDao projectDao) { this.reportAggregatedDAO = reportAggregatedDAO; this.customerAndProjectCriteriaFilter = customerAndProjectCriteriaFilter; this.userAndDepartmentCriteriaFilter = userAndDepartmentCriteriaFilter; this.individualUserCriteriaSync = individualUserCriteriaSync; this.lockService = lockService; this.userDao = userDao; this.projectDao = projectDao; } /** * Update available report criteria */ public ReportCriteria syncUserReportCriteria(ReportCriteria reportCriteria, ReportCriteriaUpdateType updateType) { UserSelectedCriteria userSelectedCriteria = reportCriteria.getUserSelectedCriteria(); AvailableCriteria availCriteria = reportCriteria.getAvailableCriteria(); List<TimesheetLock> timesheetLocks = Lists.newArrayList(WrapAsJava$.MODULE$.asJavaCollection(lockService.findAll())); availCriteria.setTimesheetLocks(timesheetLocks); if (userSelectedCriteria.isForGlobalReport() || userSelectedCriteria.isForPm()) { if (updateType == UPDATE_CUSTOMERS_AND_PROJECTS || updateType == ReportCriteriaUpdateType.UPDATE_ALL) { Tuple2<List<Customer>, List<Project>> available = customerAndProjectCriteriaFilter.getAvailableCustomers(userSelectedCriteria); List<Customer> updatedAvailableCustomers = available._1(); availCriteria.setCustomers(updatedAvailableCustomers); preserveSelectedCustomers(userSelectedCriteria, updatedAvailableCustomers); List<Project> updatedAvailableProjects = available._2(); availCriteria.setProjects(updatedAvailableProjects); preserveSelectedProjects(userSelectedCriteria, updatedAvailableProjects); } if (updateType == ReportCriteriaUpdateType.UPDATE_USERS_AND_DEPTS || updateType == ReportCriteriaUpdateType.UPDATE_ALL) { Tuple2<List<UserDepartment>, List<User>> avail = userAndDepartmentCriteriaFilter.getAvailableUsers(userSelectedCriteria); availCriteria.setUserDepartments(avail._1()); availCriteria.setUsers(avail._2()); } if (updateType == ReportCriteriaUpdateType.UPDATE_ALL) { availCriteria.setReportRange(reportAggregatedDAO.getMinMaxDateTimesheetEntry()); } } else { individualUserCriteriaSync.syncCriteriaForIndividualUser(reportCriteria); } return reportCriteria; } private void preserveSelectedProjects(UserSelectedCriteria userSelectedCriteria, List<Project> updatedAvailableProjects) { List<Project> updatedSelectedProjects = Lists.newArrayList(); if (userSelectedCriteria.getProjects() != null) { for (Project updatedAvailableProject : updatedAvailableProjects) { if (userSelectedCriteria.getProjects().contains(updatedAvailableProject)) { updatedSelectedProjects.add(updatedAvailableProject); } } } userSelectedCriteria.setProjects(updatedSelectedProjects); } private void preserveSelectedCustomers(UserSelectedCriteria userSelectedCriteria, List<Customer> updatedAvailableCustomers) { List<Customer> updatedSelectedCustomers = Lists.newArrayList(); if (userSelectedCriteria.getCustomers() != null) { for (Customer updatedAvailableCustomer : updatedAvailableCustomers) { if (userSelectedCriteria.getCustomers().contains(updatedAvailableCustomer)) { updatedSelectedCustomers.add(updatedAvailableCustomer); } } } userSelectedCriteria.setCustomers(updatedSelectedCustomers); } @Override public UsersAndProjects criteriaToUsersAndProjects(UserSelectedCriteria userSelectedCriteria) { boolean noUserRestrictionProvided = userSelectedCriteria.isEmptyDepartments() && userSelectedCriteria.isEmptyUsers(); boolean noProjectRestrictionProvided = userSelectedCriteria.isEmptyCustomers() && userSelectedCriteria.isEmptyProjects(); List<Project> projects; List<User> users; if (!noProjectRestrictionProvided || !noUserRestrictionProvided) { if (noProjectRestrictionProvided) { users = getUsersForSelectedDepartments(userSelectedCriteria); projects = Lists.newArrayList(); } else if (noUserRestrictionProvided) { projects = getProjects(userSelectedCriteria); users = Lists.newArrayList(); } else { users = getUsersForSelectedDepartments(userSelectedCriteria); projects = getProjects(userSelectedCriteria); } } else { users = Lists.newArrayList(); projects = Lists.newArrayList(); } if (userSelectedCriteria.isOnlyBillableProjects() && projects.isEmpty()) { projects = getBillableProjects(userSelectedCriteria); } return new UsersAndProjects(users, projects); } private List<User> getUsersForSelectedDepartments(UserSelectedCriteria userSelectedCriteria) { if (userSelectedCriteria.isEmptyUsers()) { if (!userSelectedCriteria.isEmptyDepartments()) { Collection<UserDepartment> departments = userSelectedCriteria.getDepartments(); return findUsersInDepartments(userSelectedCriteria, departments); } else { return Lists.newArrayList(); } } else { return userSelectedCriteria.getUsers(); } } private List<User> findUsersInDepartments(UserSelectedCriteria userSelectedCriteria, Collection<UserDepartment> departments) { List<User> allActiveUsers = userDao.findUsers(userSelectedCriteria.isOnlyActiveUsers()); List<User> matchingUsers = Lists.newArrayList(); for (User activeUser : allActiveUsers) { if (CollectionUtils.containsAny(activeUser.getUserDepartments(), departments)) { matchingUsers.add(activeUser); } } return matchingUsers; } /** * Get project id's based on selected customers */ private List<Project> getProjects(UserSelectedCriteria userSelectedCriteria) { // No projects selected by the user, use any given customer limitation if (userSelectedCriteria.isEmptyProjects()) { if (!userSelectedCriteria.isEmptyCustomers()) { return projectDao.findProjectForCustomers(userSelectedCriteria.getCustomers(), userSelectedCriteria.isOnlyActiveProjects()); } else { return Lists.newArrayList(); } } else { return userSelectedCriteria.getProjects(); } } private List<Project> getBillableProjects(UserSelectedCriteria criteria) { List<Project> projects = criteria.isOnlyActiveProjects() ? projectDao.findAllActive() : projectDao.findAll(); List<Project> filteredProjects = Lists.newArrayList(); for (Project project : projects) { boolean billableFilter = project.isBillable(); boolean customerFilter = !criteria.isOnlyActiveCustomers() || project.getCustomer().isActive(); if (billableFilter && customerFilter) { filteredProjects.add(project); } } return filteredProjects; } }