001/*
002 *  Copyright 2016 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.forms.workflow;
017
018import java.util.HashMap;
019import java.util.Map;
020
021import org.apache.avalon.framework.parameters.Parameters;
022import org.apache.avalon.framework.service.ServiceException;
023import org.apache.avalon.framework.service.ServiceManager;
024import org.apache.cocoon.environment.ObjectModelHelper;
025import org.apache.cocoon.environment.Redirector;
026import org.apache.cocoon.environment.Request;
027import org.apache.commons.collections.MapUtils;
028
029import org.ametys.cms.repository.Content;
030import org.ametys.cms.workflow.AbstractContentWorkflowComponent;
031import org.ametys.core.cocoon.ActionResultGenerator;
032import org.ametys.core.user.CurrentUserProvider;
033import org.ametys.core.user.User;
034import org.ametys.core.user.UserIdentity;
035import org.ametys.core.user.UserManager;
036import org.ametys.core.util.JSONUtils;
037import org.ametys.plugins.forms.Form;
038import org.ametys.plugins.forms.data.UserEntry;
039import org.ametys.plugins.forms.jcr.FormPropertiesManager;
040import org.ametys.plugins.forms.table.FormTableManager;
041import org.ametys.plugins.workflow.AbstractWorkflowComponent;
042import org.ametys.plugins.workflow.cocoon.WorkflowAction;
043import org.ametys.plugins.workflow.store.JdbcWorkflowStore;
044
045import com.opensymphony.workflow.InvalidInputException;
046import com.opensymphony.workflow.Workflow;
047import com.opensymphony.workflow.WorkflowException;
048
049/**
050 * Action for executing a transition on a form entry workflow.<p>
051 * The following parameters are supported:
052 * <dl>
053 *  <dt>actionId
054 *  <dd>the id of the action to fire
055 * </dl>
056 */
057public class FormEntriesWorkflowAction extends WorkflowAction
058{
059    /** Component gathering utility methods to work with the forms JCR representations */
060    private FormPropertiesManager _formPropertiesManager;
061    
062    /** Helper to manipulation the forms SQL tables */
063    private FormTableManager _formTableManager;
064    
065    /** Helper to retrieve the current user */
066    private CurrentUserProvider _currentUserProvider;
067    
068    /** The users manager */
069    private UserManager _userManager;
070    
071    /** Utility component for the handling of object represented in JSON */
072    private JSONUtils _jsonUtils;
073    
074    @Override
075    public void service(ServiceManager serviceManager) throws ServiceException
076    {
077        super.service(serviceManager);
078        _formPropertiesManager = (FormPropertiesManager) serviceManager.lookup(FormPropertiesManager.ROLE);
079        _formTableManager = (FormTableManager) serviceManager.lookup(FormTableManager.ROLE);
080        _currentUserProvider = (CurrentUserProvider) serviceManager.lookup(CurrentUserProvider.ROLE);
081        _userManager = (UserManager) serviceManager.lookup(UserManager.ROLE);
082        _jsonUtils = (JSONUtils) serviceManager.lookup(JSONUtils.ROLE);
083    }
084    
085    @Override
086    protected Map _act(Redirector redirector, Map objectModel, String source, Parameters parameters, int actionId, Map inputs) throws InvalidInputException, WorkflowException
087    {
088        Workflow workflow = _workflowProvider.getExternalWorkflow(JdbcWorkflowStore.ROLE);
089        workflow.doAction(_getWorkflowId(objectModel, source, parameters), actionId, inputs);
090        return _getActionResult(redirector, objectModel, source, parameters);
091    }
092    
093    @Override
094    protected long _getWorkflowId(Map objectModel, String source, Parameters parameters)
095    {
096        try
097        {
098            String entryId = parameters.getParameter("entryId");
099            String formId = parameters.getParameter("formId");
100        
101            Form form = _formPropertiesManager.getForm(formId);
102            UserEntry submission = _formTableManager.getSubmission(form, new HashMap<>(), Integer.valueOf(entryId));
103        
104            if (submission == null)
105            {
106                throw new RuntimeException("Unable to retrieve the workflow id for the entry '" + entryId + "' of the form '" + formId + "'.");
107            }
108            else
109            {
110                return submission.getWorkflowId();
111            }
112        }
113        catch (Exception e)
114        {
115            throw new RuntimeException("Missing parameter workflowId", e);
116        }
117    }
118    
119    @Override
120    protected Map<String, Object> _getInputs(Redirector redirector, Map objectModel, String source, Parameters parameters) throws Exception
121    {
122        Map<String, Object> inputs = super._getInputs(redirector, objectModel, source, parameters);
123        
124        String formId = parameters.getParameter("formId");
125        Content formContent = _formPropertiesManager.getFormContent(formId);
126        // Provide the content key
127        inputs.put(AbstractContentWorkflowComponent.CONTENT_KEY, formContent);
128        
129        // Provide a map for providing data to the generator
130        Request request = ObjectModelHelper.getRequest(objectModel);
131        Map<String, Object> result = new HashMap<>();
132        request.setAttribute(ActionResultGenerator.MAP_REQUEST_ATTR, result);
133        inputs.put(AbstractWorkflowComponent.RESULT_MAP_KEY, result);
134        
135        // Set the workflow comment into the inputs.
136        String comment = request.getParameter("comment");
137        inputs.put("comment", comment);
138        
139        // Set the values for the information request function if a mail is to be sent
140        String sendMailAsJSON = request.getParameter("sendMailInfo");
141        Map<String, Object> sendMailInfo = _jsonUtils.convertJsonToMap(sendMailAsJSON); 
142        if (MapUtils.isNotEmpty(sendMailInfo))
143        {
144            // Retrieve the current user name and email
145            UserIdentity userIdentity = _currentUserProvider.getUser();
146            User user = _userManager.getUser(userIdentity.getPopulationId(), userIdentity.getLogin());
147            
148            inputs.put(SendMailFunction.SENDER, user.getEmail());
149            inputs.put(SendMailFunction.RECIPIENT, sendMailInfo.get("recipient"));
150            inputs.put(SendMailFunction.SUBJECT, sendMailInfo.get("subject"));
151            inputs.put(SendMailFunction.BODY, sendMailInfo.get("body"));
152        }
153        else
154        {
155            inputs.put(SendMailFunction.SEND_MAIL, "false");
156        }
157        
158        
159        return inputs;
160    }
161}