/* * (c) Copyright 2010-2011 AgileBirds * * This file is part of OpenFlexo. * * OpenFlexo 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 3 of the License, or * (at your option) any later version. * * OpenFlexo 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 OpenFlexo. If not, see <http://www.gnu.org/licenses/>. * */ package org.openflexo.foundation.wkf; import java.awt.Color; import java.io.Serializable; import java.util.ArrayList; import java.util.Collections; import java.util.Enumeration; import java.util.Vector; import java.util.logging.Level; import java.util.logging.Logger; import org.openflexo.foundation.DataFlexoObserver; import org.openflexo.foundation.DataModification; import org.openflexo.foundation.FlexoObservable; import org.openflexo.foundation.Inspectors; import org.openflexo.foundation.action.FlexoActionizer; import org.openflexo.foundation.imported.dm.RoleAlreadyImportedException; import org.openflexo.foundation.rm.FlexoProject; import org.openflexo.foundation.rm.FlexoProjectReference; import org.openflexo.foundation.rm.ProjectData; import org.openflexo.foundation.utils.FlexoColor; import org.openflexo.foundation.utils.FlexoIndexManager; import org.openflexo.foundation.validation.Validable; import org.openflexo.foundation.wkf.action.AddRole; import org.openflexo.foundation.wkf.action.DeleteRole; import org.openflexo.foundation.wkf.dm.RoleInserted; import org.openflexo.foundation.wkf.dm.RoleRemoved; import org.openflexo.foundation.xml.FlexoWorkflowBuilder; import org.openflexo.inspector.InspectableObject; import org.openflexo.localization.FlexoLocalization; import org.openflexo.toolbox.EmptyVector; import org.openflexo.toolbox.ToolBox; import org.openflexo.ws.client.PPMWebService.PPMRole; /** * Represents the list of roles for the workflow * * @author sguerin * */ public final class RoleList extends WorkflowModelObject implements DataFlexoObserver, Serializable, InspectableObject { private static final Logger logger = Logger.getLogger(RoleList.class.getPackage().getName()); private Vector<Role> _roles; public static FlexoActionizer<AddRole, WorkflowModelObject, WorkflowModelObject> addRoleActionizer; public static FlexoActionizer<DeleteRole, Role, WorkflowModelObject> deleteRoleActionizer; public Role importRole(PPMRole role) throws RoleAlreadyImportedException { Role fir = getImportedObjectWithURI(role.getUri()); if (fir != null) { throw new RoleAlreadyImportedException(role, fir); } fir = Role.createImportedRoleFromRole(this, role); try { addToRoles(fir); } catch (DuplicateRoleException e) { if (logger.isLoggable(Level.SEVERE)) { logger.log(Level.SEVERE, "Duplicate exception while importing role: " + role + " this should never happen!", e); } } return fir; } /** * Constructor used during deserialization */ public RoleList(FlexoWorkflowBuilder builder) { this(builder.getProject(), builder.workflow); initializeDeserialization(builder); } /** * Default constructor */ public RoleList(FlexoProject project, FlexoWorkflow workflow) { super(project, workflow); _roles = new Vector<Role>(); } @Override public boolean isImported() { return isImportedRoleList(); } public boolean isImportedRoleList() { return getWorkflow() != null && getWorkflow().getImportedRoleList() == this; } private RoleList roleList; @Override public RoleList getUncachedObject() { if (roleList != null) { return roleList; } if (!getWorkflow().isCache()) { return roleList = this; } if (true) { ProjectData projectData = getProject().getProjectData(); if (projectData != null) { FlexoProjectReference ref = projectData.getProjectReferenceWithURI(getWorkflow().getProjectURI()); if (ref != null) { FlexoProject referredProject = ref.getReferredProject(true); if (referredProject != null) { return roleList = referredProject.getWorkflow().getRoleList(); } } } } return null; } /** * Overrides getClassNameKey * * @see org.openflexo.foundation.FlexoModelObject#getClassNameKey() */ @Override public String getClassNameKey() { return "role_list"; } @Override public String getFullyQualifiedName() { return getProject().getFullyQualifiedName() + ".ROLE_LIST"; } public Role roleWithName(String aName) { for (Role role : getRoles()) { if (role.getName() != null && role.getName().equals(aName)) { return role; } } return null; } public Role getRoleWithFlexoID(long flexoID) { for (Role role : getRoles()) { if (role.getFlexoID() == flexoID) { return role; } } return null; } /** * Default inspector name */ @Override public String getInspectorName() { return Inspectors.WKF.ROLE_LIST_INSPECTOR; } public Vector<Role> getRoles() { return _roles; } public void setRoles(Vector<Role> roles) { _roles = roles; } public int size() { return getRoles().size(); } public Role getImportedObjectWithURI(String uri) { return getObjectWithURI(getRoles(), uri); } public void addToRoles(Role aRole) throws DuplicateRoleException { addToRoles(aRole, false); } public void addToRoles(Role aRole, boolean replaceExisting) throws DuplicateRoleException { if (!aRole.isImported() && !isImportedRoleList()) { if (aRole.getName() == null) { aRole.setName(aRole.getIsSystemRole() ? getNextNewSystemRoleName() : getNextNewUserRoleName()); } if (logger.isLoggable(Level.FINE)) { logger.fine("addToRoles with " + aRole.getFullyQualifiedName()); } Role roleWithName = roleWithName(aRole.getName()); if (roleWithName != null) { if (roleWithName == aRole) { return; } if (!replaceExisting) { if (isDeserializing()) { aRole.setName(aRole.getName() + "-1"); addToRoles(aRole); return; } throw new DuplicateRoleException(aRole.getName()); } else { _roles.remove(roleWithName); } } } if (!_roles.contains(aRole)) { _roles.add(aRole); aRole.setRoleList(this); if (!isDeserializing()) { notifyRoleAdded(aRole); if (getWorkflow() != null) { getWorkflow().clearAssignableRolesCache(); } } } } public void removeFromRoles(Role aRole) { if (_roles.contains(aRole)) { _roles.remove(aRole); aRole.setRoleList(null); if (!isDeserializing()) { notifyRoleRemoved(aRole); if (getWorkflow() != null) { getWorkflow().clearAssignableRolesCache(); } } } } /** * @return */ public Enumeration<Role> getSortedRoles() { disableObserving(); Role[] o = FlexoIndexManager.sortArray(getRoles().toArray(new Role[0])); enableObserving(); return ToolBox.getEnumeration(o); } public Vector<Role> getSortedRolesVector() { disableObserving(); Vector<Role> v = new Vector<Role>(getRoles()); Collections.sort(v, FlexoIndexManager.INDEX_COMPARATOR); enableObserving(); return v; } public Vector<Role> getTopRolesInTopDownHierachy() { Vector<Role> reply = new Vector<Role>(); for (Enumeration<Role> e = getSortedRoles(); e.hasMoreElements();) { Role r = e.nextElement(); if (r.getRoleSpecializations().size() == 0) { reply.add(r); } } return reply; } /** * used by velocity * * @return the list of roles with no incoming arrow. */ public ArrayList<Role> getRoots() { ArrayList<Role> reply = new ArrayList<Role>(); for (Enumeration<Role> e = getSortedRoles(); e.hasMoreElements();) { Role r = e.nextElement(); if (r.getInverseRoleSpecializations().size() == 0) { reply.add(r); } } Role.sort(reply); return reply; } /** * @param role * @param process */ private void notifyRoleAdded(Role role) { setChanged(); notifyObservers(new RoleInserted(role)); } /** * @param role * @param process */ private void notifyRoleRemoved(Role role) { setChanged(); notifyObservers(new RoleRemoved(role)); } public Role createNewRole() { String newRoleName = getNextNewUserRoleName(); Role newRole = new Role(getWorkflow(), newRoleName); try { addToRoles(newRole); } catch (DuplicateRoleException e) { // should never happen e.printStackTrace(); } return newRole; } public String getNextNewUserRoleName() { String baseName = FlexoLocalization.localizedForKey("role"); String newRoleName = baseName; int inc = 0; while (roleWithName(newRoleName) != null) { inc++; newRoleName = baseName + inc; } return newRoleName; } public String getNextNewSystemRoleName() { String baseName = FlexoLocalization.localizedForKey("system"); String newRoleName = baseName; int inc = 0; while (roleWithName(newRoleName) != null) { inc++; newRoleName = baseName + inc; } return newRoleName; } public void deleteRole(Role aRole) { removeFromRoles(aRole); } public boolean isRoleDeletable(Role aRole) { return true; } private Role defaultRole = null; public Role getDefaultRole() { if (defaultRole == null || defaultRole.isDeleted()) { defaultRole = null; } return defaultRole; } public void setDefaultRole(Role role) { defaultRole = role; } protected void assertDefaultRoleHasBeenCreated() { if (getDefaultRole() == null && !isDeserializing()) { // Create a default system role String defaultRoleName = FlexoLocalization.localizedForKey("no_role"); Role newRole = new Role(getWorkflow(), defaultRoleName); newRole.setColor(Color.DARK_GRAY); newRole.setIsSystemRole(true); defaultRole = newRole; } } /** * Return a Vector of all embedded WKFObjects * * @return a Vector of WKFObject instances */ @Override public Vector<Validable> getAllEmbeddedValidableObjects() { Vector<Validable> returned = new Vector<Validable>(); returned.add(this); returned.addAll(getRoles()); return returned; } public void performAddRole() { if (addRoleActionizer != null) { addRoleActionizer.run(this, EMPTY_VECTOR); } } public void performDeleteRole(Role object) { if (deleteRoleActionizer != null) { deleteRoleActionizer.run(object, EmptyVector.EMPTY_VECTOR(WorkflowModelObject.class)); } } public Color getNewRoleColor() { Vector<Color> v = new Vector<Color>(); for (Role role : getRoles()) { if (role.getColor() != null) { v.add(role.getColor()); } } return FlexoColor.getRandomColor(v); } // ========================================================================== // ================================= Delete =============================== // ========================================================================== @Override public final void delete() { _roles.clear(); super.delete(); deleteObservers(); } // =================================================================== // =========================== FlexoObserver ========================= // =================================================================== @Override public void update(FlexoObservable observable, DataModification dataModification) { // TODO Auto-generated method stub } }