001/* 002 * Copyright 2013 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.cms.workflow; 017 018import java.util.HashMap; 019import java.util.Map; 020 021import javax.jcr.Node; 022import javax.jcr.RepositoryException; 023import javax.jcr.lock.Lock; 024import javax.jcr.lock.LockManager; 025 026import org.apache.avalon.framework.activity.Initializable; 027 028import org.ametys.cms.ObservationConstants; 029import org.ametys.cms.repository.WorkflowAwareContent; 030import org.ametys.core.observation.Event; 031import org.ametys.core.observation.ObservationManager; 032import org.ametys.plugins.repository.RepositoryConstants; 033import org.ametys.plugins.repository.lock.LockAwareAmetysObject; 034import org.ametys.plugins.repository.version.VersionableAmetysObject; 035import org.ametys.plugins.workflow.support.WorkflowProvider; 036import org.ametys.plugins.workflow.support.WorkflowProvider.AmetysObjectWorkflow; 037 038import com.opensymphony.workflow.FunctionProvider; 039import com.opensymphony.workflow.WorkflowException; 040import com.opensymphony.workflow.spi.Step; 041 042/** 043 * Abstract workflow function working on a Content, which provides common content methods. 044 */ 045public abstract class AbstractContentFunction extends AbstractContentWorkflowComponent implements FunctionProvider, Initializable 046{ 047 048 /** The workflow provider. */ 049 protected WorkflowProvider _workflowProvider; 050 /** The observation manager */ 051 protected ObservationManager _observationManager; 052 053 @Override 054 public void initialize() throws Exception 055 { 056 _workflowProvider = (WorkflowProvider) _manager.lookup(WorkflowProvider.ROLE); 057 _observationManager = (ObservationManager) _manager.lookup(ObservationManager.ROLE); 058 } 059 060 /** 061 * Add the content lock token to the current session if the content is locked. 062 * @param content the content. 063 * @throws WorkflowException if an error occurs. 064 * @throws RepositoryException if a repository error occurs. 065 */ 066 protected void _addLockToken(WorkflowAwareContent content) throws WorkflowException, RepositoryException 067 { 068 if (content != null && content instanceof LockAwareAmetysObject) 069 { 070 LockAwareAmetysObject lockAwareContent = (LockAwareAmetysObject) content; 071 if (lockAwareContent.isLocked()) 072 { 073 Node node = content.getNode(); 074 075 LockManager lockManager = node.getSession().getWorkspace().getLockManager(); 076 077 Lock lock = lockManager.getLock(node.getPath()); 078 Node lockHolder = lock.getNode(); 079 080 lockManager.addLockToken(lockHolder.getProperty(RepositoryConstants.METADATA_LOCKTOKEN).getString()); 081 } 082 } 083 } 084 085 /** 086 * Set the content's current step ID without notifying the observers that the content's workflow has changed. 087 * @param content the content. 088 * @param transientVars The workflow transient vars. 089 * @throws WorkflowException if an error occurs. 090 */ 091 protected void _setCurrentStepId(WorkflowAwareContent content, Map transientVars) throws WorkflowException 092 { 093 if (content != null) 094 { 095 // Save the current step. 096 AmetysObjectWorkflow workflow = _workflowProvider.getAmetysObjectWorkflow(content); 097 Step currentStep = (Step) workflow.getCurrentSteps(content.getWorkflowId()).iterator().next(); 098 content.setCurrentStepId(currentStep.getStepId()); 099 content.saveChanges(); 100 } 101 } 102 103 /** 104 * Set the content's current step ID and notify the observers that the content's workflow has changed. 105 * @param content the content. 106 * @param transientVars The workflow transient vars. 107 * @throws WorkflowException if an error occurs. 108 */ 109 protected void _setCurrentStepIdAndNotify(WorkflowAwareContent content, Map transientVars) throws WorkflowException 110 { 111 if (content != null) 112 { 113 // Save the current step. 114 AmetysObjectWorkflow workflow = _workflowProvider.getAmetysObjectWorkflow(content); 115 Step currentStep = (Step) workflow.getCurrentSteps(content.getWorkflowId()).iterator().next(); 116 content.setCurrentStepId(currentStep.getStepId()); 117 content.saveChanges(); 118 119 Map<String, Object> eventParams = new HashMap<>(); 120 eventParams.put(ObservationConstants.ARGS_CONTENT, content); 121 eventParams.put(ObservationConstants.ARGS_CONTENT_ID, content.getId()); 122 _observationManager.notify(new Event(ObservationConstants.EVENT_CONTENT_WORKFLOW_CHANGED, getUser(transientVars), eventParams)); 123 } 124 } 125 126 /** 127 * Persists the current version and create a new one. 128 * @param content the content. 129 * @throws WorkflowException if an error occurs. 130 */ 131 protected void _createVersion(WorkflowAwareContent content) throws WorkflowException 132 { 133 if (content != null) 134 { 135 // Create a new version 136 if (content instanceof VersionableAmetysObject) 137 { 138 ((VersionableAmetysObject) content).checkpoint(); 139 } 140 } 141 } 142 143 /** 144 * Add a label on the content. 145 * @param content the content. 146 * @param label the label to add. 147 * @throws WorkflowException if an error occurs. 148 * @throws RepositoryException if an error occurs. 149 */ 150 protected void _addLabel(WorkflowAwareContent content, String label) throws WorkflowException, RepositoryException 151 { 152 if (content != null) 153 { 154 if (content instanceof VersionableAmetysObject) 155 { 156 ((VersionableAmetysObject) content).addLabel(label, true); 157 } 158 } 159 } 160 161}