WorkflowStarter.java 9.29 KB
/*
 * Decompiled with CFR 0_118.
 * 
 * Could not load the following classes:
 *  com.adobe.cq.projects.api.Project
 *  com.adobe.cq.projects.api.ProjectException
 *  com.adobe.granite.workflow.WorkflowException
 *  com.adobe.granite.workflow.WorkflowSession
 *  com.adobe.granite.workflow.exec.Workflow
 *  com.adobe.granite.workflow.exec.WorkflowData
 *  com.adobe.granite.workflow.metadata.MetaDataMap
 *  com.adobe.granite.workflow.model.WorkflowModel
 *  com.day.cq.commons.jcr.JcrUtil
 *  javax.jcr.Node
 *  javax.jcr.RepositoryException
 *  javax.servlet.ServletException
 *  org.apache.commons.lang3.StringUtils
 *  org.apache.jackrabbit.commons.JcrUtils
 *  org.apache.sling.api.SlingHttpServletRequest
 *  org.apache.sling.api.resource.ModifiableValueMap
 *  org.apache.sling.api.resource.PersistenceException
 *  org.apache.sling.api.resource.Resource
 *  org.apache.sling.api.resource.ResourceResolver
 *  org.apache.sling.api.resource.ValueMap
 *  org.slf4j.Logger
 *  org.slf4j.LoggerFactory
 */
package com.adobe.cq.projects.impl.servlet;

import com.adobe.cq.projects.api.Project;
import com.adobe.cq.projects.api.ProjectException;
import com.adobe.cq.projects.impl.servlet.ProjectServletUtil;
import com.adobe.granite.workflow.WorkflowException;
import com.adobe.granite.workflow.WorkflowSession;
import com.adobe.granite.workflow.exec.Workflow;
import com.adobe.granite.workflow.exec.WorkflowData;
import com.adobe.granite.workflow.metadata.MetaDataMap;
import com.adobe.granite.workflow.model.WorkflowModel;
import com.day.cq.commons.jcr.JcrUtil;
import java.text.ParseException;
import java.util.Calendar;
import java.util.Enumeration;
import java.util.HashMap;
import java.util.Map;
import java.util.Set;
import javax.jcr.Node;
import javax.jcr.RepositoryException;
import javax.servlet.ServletException;
import org.apache.commons.lang3.StringUtils;
import org.apache.jackrabbit.commons.JcrUtils;
import org.apache.sling.api.SlingHttpServletRequest;
import org.apache.sling.api.resource.ModifiableValueMap;
import org.apache.sling.api.resource.PersistenceException;
import org.apache.sling.api.resource.Resource;
import org.apache.sling.api.resource.ResourceResolver;
import org.apache.sling.api.resource.ValueMap;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

public class WorkflowStarter {
    private static final Logger LOGGER = LoggerFactory.getLogger(WorkflowStarter.class);
    private static final String TYPE_HINT_SUFFIX = "@TypeHint";

    static Workflow startWorkflow(SlingHttpServletRequest request) throws ServletException, WorkflowException {
        Project project = (Project)request.getResource().adaptTo(Project.class);
        if (project == null) {
            throw new ServletException("Error adapting target to project");
        }
        Resource projectResource = (Resource)project.adaptTo(Resource.class);
        if (projectResource == null) {
            throw new ServletException("Error adapting project to resource");
        }
        String modelId = request.getParameter("modelId");
        if (StringUtils.isBlank((CharSequence)modelId)) {
            throw new ServletException("Unable to start a workflow when no model has been provided");
        }
        try {
            ProjectServletUtil.getOrCreateTasksFolder(request, projectResource);
        }
        catch (PersistenceException e) {
            throw new ServletException("Failed to get or create the tasks folder", (Throwable)e);
        }
        WorkflowSession wfSession = (WorkflowSession)request.getResourceResolver().adaptTo(WorkflowSession.class);
        WorkflowModel modelToStart = wfSession.getModel(modelId);
        if (modelToStart == null) {
            throw new ServletException("Workflow model with id '" + modelId + "' not found");
        }
        String contentPath = request.getParameter("contentPath");
        if (StringUtils.isBlank((CharSequence)contentPath)) {
            LOGGER.debug("content path not set for starting workflow, using dam folder: " + project.getAssetFolder().getPath());
            contentPath = project.getAssetFolder().getPath();
        }
        WorkflowData workflowData = wfSession.newWorkflowData("JCR_PATH", (Object)contentPath);
        HashMap<String, Object> metaData = new HashMap<String, Object>();
        ValueMap projectValueMap = projectResource.getValueMap();
        for (Map.Entry entry : projectValueMap.entrySet()) {
            if (!((String)entry.getKey()).startsWith("role_")) continue;
            String role = ((String)entry.getKey()).substring(((String)entry.getKey()).indexOf("role_") + "role_".length());
            metaData.put("project.group." + role, entry.getValue());
        }
        metaData.put("project.path", projectResource.getPath());
        Enumeration parameterNames = request.getParameterNames();
        while (parameterNames.hasMoreElements()) {
            String parameterName = (String)parameterNames.nextElement();
            if (parameterName.endsWith("@TypeHint") || !WorkflowStarter.includeParameter(parameterName)) continue;
            Object parameterValue = request.getParameter(parameterName);
            String typeHint = request.getParameter(parameterName + "@TypeHint");
            if (StringUtils.isNotBlank((CharSequence)typeHint)) {
                if (Calendar.class.getSimpleName().equals(typeHint) || "Date".equals(typeHint)) {
                    if (!StringUtils.isNotEmpty((CharSequence)parameterValue)) continue;
                    try {
                        parameterValue = ProjectServletUtil.parseDate((String)parameterValue);
                        metaData.put(parameterName, parameterValue);
                        continue;
                    }
                    catch (ParseException e) {
                        throw new ServletException("Unable to parse date: ", (Throwable)e);
                    }
                }
                throw new ServletException("Unknown @TypeHint conversion to type : " + typeHint);
            }
            metaData.put(parameterName, (String)parameterValue);
        }
        Resource workResource = null;
        try {
            Resource workFolder = ProjectServletUtil.getOrCreateWorkFolder(project);
            String refName = WorkflowStarter.getStringParam(request, "workflowTitle", false, modelToStart.getTitle());
            refName = JcrUtil.createValidName((String)refName).replaceAll("-", "");
            Node workNode = JcrUtils.getOrCreateUniqueByPath((Node)((Node)workFolder.adaptTo(Node.class)), (String)refName, (String)"nt:unstructured");
            metaData.put("project.workLinkPath", workNode.getPath());
            workResource = request.getResourceResolver().getResource(workNode.getPath());
        }
        catch (RepositoryException e) {
            throw new ProjectException("Failed create project workflow reference", (Throwable)e);
        }
        catch (PersistenceException e) {
            throw new ServletException("Failed create project workflow reference", (Throwable)e);
        }
        Workflow wf = wfSession.startWorkflow(modelToStart, workflowData, metaData);
        if (workResource != null) {
            try {
                ModifiableValueMap workResProps = (ModifiableValueMap)workResource.adaptTo(ModifiableValueMap.class);
                workResProps.put((Object)"workflow.id", (Object)wf.getId());
                workResProps.put((Object)"model.id", (Object)modelToStart.getId());
                if (modelToStart.getMetaDataMap().containsKey((Object)"tags")) {
                    workResProps.put((Object)"model.tags", modelToStart.getMetaDataMap().get("tags", String.class));
                }
                WorkflowStarter.createCommentingFolders(request.getResourceResolver(), workResource);
                request.getResourceResolver().commit();
                ValueMap vm = (ValueMap)request.getResource().adaptTo(ValueMap.class);
                String observerGroupId = (String)vm.get("role_observer", String.class);
            }
            catch (PersistenceException e) {
                throw new ServletException("Failed to apply project workflow reference properties", (Throwable)e);
            }
        }
        return wf;
    }

    private static void createCommentingFolders(ResourceResolver resourceResolver, Resource workResource) throws PersistenceException {
        HashMap<String, String> propsRegular = new HashMap<String, String>();
        propsRegular.put("jcr:primaryType", "nt:unstructured");
        resourceResolver.create(workResource, "default", propsRegular);
    }

    private static boolean includeParameter(String parameterName) {
        if (parameterName == null) {
            return false;
        }
        if (parameterName.startsWith(":")) {
            return false;
        }
        return !parameterName.equals("contentPath") && !parameterName.equals("linkConsolePath") && !parameterName.equals("linkSuffix") && !parameterName.equals("linkType");
    }

    private static final String getStringParam(SlingHttpServletRequest request, String name, boolean isMandatory, String defaultValue) throws ServletException {
        String valueAsString = request.getParameter(name);
        if (StringUtils.isNotEmpty((CharSequence)valueAsString)) {
            return valueAsString;
        }
        if (isMandatory) {
            throw new ServletException("Error during operation. Mandatory parameter is missing: " + name);
        }
        return defaultValue;
    }
}