/* * To change this license header, choose License Headers in Project Properties. * To change this template file, choose Tools | Templates * and open the template in the editor. */ package edu.harvard.iq.dataverse; import edu.harvard.iq.dataverse.authorization.AuthenticationServiceBean; import edu.harvard.iq.dataverse.authorization.DataverseRole; import edu.harvard.iq.dataverse.authorization.Permission; import edu.harvard.iq.dataverse.authorization.RoleAssignee; import edu.harvard.iq.dataverse.authorization.RoleAssigneeDisplayInfo; import edu.harvard.iq.dataverse.authorization.users.AuthenticatedUser; import edu.harvard.iq.dataverse.engine.command.exception.CommandException; import edu.harvard.iq.dataverse.engine.command.exception.PermissionException; import edu.harvard.iq.dataverse.engine.command.impl.AssignRoleCommand; import edu.harvard.iq.dataverse.engine.command.impl.CreateRoleCommand; import edu.harvard.iq.dataverse.engine.command.impl.RevokeRoleCommand; import edu.harvard.iq.dataverse.engine.command.impl.UpdatePermissionRootCommand; import static edu.harvard.iq.dataverse.util.JsfHelper.JH; import java.util.ArrayList; import java.util.Arrays; import java.util.Collections; import java.util.LinkedList; import java.util.List; import java.util.Set; import java.util.logging.Level; import java.util.logging.Logger; import javax.ejb.EJB; import javax.faces.application.FacesMessage; import javax.faces.event.ActionEvent; import javax.faces.view.ViewScoped; import javax.inject.Inject; import javax.inject.Named; import javax.persistence.EntityManager; import javax.persistence.PersistenceContext; import org.apache.commons.lang.StringEscapeUtils; import org.apache.commons.lang.StringUtils; /** * * @author gdurand */ @ViewScoped @Named public class RolePermissionFragment implements java.io.Serializable { private static final Logger logger = Logger.getLogger(RolePermissionFragment.class.getCanonicalName()); @EJB DataverseRoleServiceBean roleService; @EJB RoleAssigneeServiceBean roleAssigneeService; @EJB PermissionServiceBean permissionService; @EJB AuthenticationServiceBean authenticationService; @EJB EjbDataverseEngine commandEngine; @Inject DataverseRequestServiceBean dvRequestService; @PersistenceContext(unitName = "VDCNet-ejbPU") EntityManager em; @Inject DataverseSession session; DvObject dvObject; public DvObject getDvObject() { return dvObject; } public void setDvObject(DvObject dvObject) { this.dvObject = dvObject; if (dvObject instanceof Dataverse) { inheritAssignments = !((Dataverse) dvObject).isPermissionRoot(); } } /* Inherit assignments related code */ boolean inheritAssignments; public boolean isInheritAssignments() { return inheritAssignments; } public void setInheritAssignments(boolean inheritAssignments) { this.inheritAssignments = inheritAssignments; } public void updatePermissionRoot(javax.faces.event.AjaxBehaviorEvent event) throws javax.faces.event.AbortProcessingException { try { dvObject = commandEngine.submit( new UpdatePermissionRootCommand(!inheritAssignments, dvRequestService.getDataverseRequest(), (Dataverse) dvObject)); inheritAssignments = !((DvObjectContainer) dvObject).isPermissionRoot(); } catch (CommandException ex) { Logger.getLogger(RolePermissionFragment.class.getName()).log(Level.SEVERE, null, ex); } } /* permissions tab related methods */ private String assignRoleUsername; // used if input accepts a username private RoleAssignee assignRoleRoleAssignee; // used if input accepts a RoleAssignee through a converter private Long assignRoleRoleId; private final List<String> identifierList = new ArrayList<>(); public List<String> completeIdentifier(String query) { if (identifierList.isEmpty()) { for (AuthenticatedUser au : authenticationService.findAllAuthenticatedUsers()) { identifierList.add(au.getIdentifier()); } } List<String> returnList = new ArrayList<>(); for (String identifier : identifierList) { if (identifier.contains(query)) { returnList.add(identifier); } } return returnList; } private final List<RoleAssignee> roleAssigneeList = new ArrayList<>(); public List<RoleAssignee> completeRoleAssignee(String query) { if (roleAssigneeList.isEmpty()) { for (AuthenticatedUser au : authenticationService.findAllAuthenticatedUsers()) { roleAssigneeList.add(au); } } List<RoleAssignee> returnList = new ArrayList<>(); for (RoleAssignee ra : roleAssigneeList) { // @todo unsure if containsIgnore case will work for all locales if (StringUtils.containsIgnoreCase(ra.getDisplayInfo().getTitle(),query)) { returnList.add(ra); } } return returnList; } public List<DataverseRole> getAvailableRoles() { List<DataverseRole> roles = new LinkedList<>(); if (dvObject != null && (dvObject instanceof Dataverse || dvObject instanceof Dataset)) { // current the available roles for a dataset are gotten from its parent Dataverse dv = dvObject instanceof Dataverse ? (Dataverse) dvObject : ((Dataset) dvObject).getOwner(); roles.addAll(roleService.availableRoles(dv.getId())); Collections.sort(roles, DataverseRole.CMP_BY_NAME); } return roles; } public List<RoleAssignmentRow> getRoleAssignments() { List<RoleAssignmentRow> raList = null; if (dvObject != null) { Set<RoleAssignment> ras = roleService.rolesAssignments(dvObject); raList = new ArrayList<>(ras.size()); for (RoleAssignment ra : ras) { // for files, only show role assihnemnts which can download if (!(dvObject instanceof DataFile) || ra.getRole().permissions().contains(Permission.DownloadFile)) { raList.add(new RoleAssignmentRow(ra, roleAssigneeService.getRoleAssignee(ra.getAssigneeIdentifier()).getDisplayInfo())); } } } return raList; } public void toggleFileRestrict(ActionEvent evt) { DataFile file = (DataFile) dvObject; file.setRestricted(!file.isRestricted()); } public void grantAccess(ActionEvent evt) { //RoleAssignee assignRoleRoleAssignee = roleAssigneeService.getRoleAssignee(assignRoleUsername); // Find the built in file downloader role (currently by alias) assignRole(assignRoleRoleAssignee, roleService.findBuiltinRoleByAlias("fileDownloader")); } public void assignRole(ActionEvent evt) { //RoleAssignee assignRoleRoleAssignee = roleAssigneeService.getRoleAssignee(assignRoleUsername); assignRole(assignRoleRoleAssignee, roleService.find(assignRoleRoleId)); } private void assignRole(RoleAssignee ra, DataverseRole r) { try { String privateUrlToken = null; commandEngine.submit(new AssignRoleCommand(ra, r, dvObject, dvRequestService.getDataverseRequest(), privateUrlToken)); JH.addMessage(FacesMessage.SEVERITY_INFO, "Role " + r.getName() + " assigned to " + ra.getDisplayInfo().getTitle() + " on " + StringEscapeUtils.escapeHtml(dvObject.getDisplayName())); } catch (CommandException ex) { JH.addMessage(FacesMessage.SEVERITY_ERROR, "Can't assign role: " + ex.getMessage()); } } public void revokeRole(Long roleAssignmentId) { try { commandEngine.submit(new RevokeRoleCommand(em.find(RoleAssignment.class, roleAssignmentId), dvRequestService.getDataverseRequest())); JH.addMessage(FacesMessage.SEVERITY_INFO, "Role assignment revoked successfully"); } catch (PermissionException ex) { JH.addMessage(FacesMessage.SEVERITY_ERROR, "Cannot revoke role assignment - you're missing permission", ex.getRequiredPermissions().toString()); logger.log(Level.SEVERE, "Error revoking role assignment: " + ex.getMessage(), ex); } catch (CommandException ex) { JH.addMessage(FacesMessage.SEVERITY_ERROR, "Cannot revoke role assignment: " + ex.getMessage()); logger.log(Level.SEVERE, "Error revoking role assignment: " + ex.getMessage(), ex); } } public String getAssignRoleUsername() { return assignRoleUsername; } public void setAssignRoleUsername(String assignRoleUsername) { this.assignRoleUsername = assignRoleUsername; } public RoleAssignee getAssignRoleRoleAssignee() { return assignRoleRoleAssignee; } public void setAssignRoleRoleAssignee(RoleAssignee assignRoleRoleAssignee) { this.assignRoleRoleAssignee = assignRoleRoleAssignee; } public Long getAssignRoleRoleId() { return assignRoleRoleId; } public void setAssignRoleRoleId(Long assignRoleRoleId) { this.assignRoleRoleId = assignRoleRoleId; } public static class RoleAssignmentRow { private final RoleAssigneeDisplayInfo assigneeDisplayInfo; private final RoleAssignment ra; public RoleAssignmentRow(RoleAssignment anRa, RoleAssigneeDisplayInfo disInf) { ra = anRa; assigneeDisplayInfo = disInf; } public RoleAssigneeDisplayInfo getAssigneeDisplayInfo() { return assigneeDisplayInfo; } public DataverseRole getRole() { return ra.getRole(); } public String getRoleName() { return getRole().getName(); } public DvObject getDefinitionPoint() { return ra.getDefinitionPoint(); } public String getAssignedDvName() { return ra.getDefinitionPoint().getDisplayName(); } public Long getId() { return ra.getId(); } } /* Roles tab related methods */ private DataverseRole role = new DataverseRole(); private List<String> selectedPermissions; public List<Permission> getPermissions() { return Arrays.asList(Permission.values()); } public List<DataverseRole> getRoles() { if (dvObject != null) { return roleService.findByOwnerId(dvObject.getId()); } return new ArrayList<>(); } public void createNewRole(ActionEvent e) { setRole(new DataverseRole()); role.setOwner(dvObject); } public void cloneRole(String roleId) { DataverseRole clonedRole = new DataverseRole(); clonedRole.setOwner(dvObject); DataverseRole originalRole = roleService.find(Long.parseLong(roleId)); clonedRole.addPermissions(originalRole.permissions()); setRole(clonedRole); } public void editRole(String roleId) { setRole(roleService.find(Long.parseLong(roleId))); } public void updateRole(ActionEvent e) { // @todo currently only works for Dataverse since CreateRoleCommand only takes a dataverse // we need to decide if we want roles at the dataset level or not if (dvObject instanceof Dataverse) { role.clearPermissions(); for (String pmsnStr : getSelectedPermissions()) { role.addPermission(Permission.valueOf(pmsnStr)); } try { setRole(commandEngine.submit(new CreateRoleCommand(role, dvRequestService.getDataverseRequest(), (Dataverse) role.getOwner()))); JH.addMessage(FacesMessage.SEVERITY_INFO, "Role '" + role.getName() + "' saved", ""); } catch (CommandException ex) { JH.addMessage(FacesMessage.SEVERITY_ERROR, "Cannot save role", ex.getMessage()); logger.log(Level.SEVERE, "Saving role failed", ex); } } } public DataverseRole getRole() { return role; } public void setRole(DataverseRole role) { this.role = role; selectedPermissions = new LinkedList<>(); if (role != null) { for (Permission p : role.permissions()) { selectedPermissions.add(p.name()); } } } public List<String> getSelectedPermissions() { return selectedPermissions; } public void setSelectedPermissions(List<String> selectedPermissions) { this.selectedPermissions = selectedPermissions; } }