Search in sources :

Example 6 with WorkflowRuntimeException

use of io.automatiko.engine.workflow.process.instance.WorkflowRuntimeException in project automatiko-engine by automatiko-io.

the class NodeInstanceImpl method executeAction.

/**
 * This method is used in both instances of the {@link ExtendedNodeInstanceImpl}
 * and {@link ActionNodeInstance} instances in order to handle exceptions thrown
 * when executing actions.
 *
 * @param action An {@link Action} instance.
 */
protected void executeAction(Action action) {
    ProcessContext context = new ProcessContext(getProcessInstance().getProcessRuntime());
    context.setNodeInstance(this);
    context.setProcessInstance(getProcessInstance());
    try {
        action.execute(context);
    } catch (Exception e) {
        String exceptionName = e.getClass().getName();
        ExceptionScopeInstance exceptionScopeInstance = (ExceptionScopeInstance) resolveContextInstance(ExceptionScope.EXCEPTION_SCOPE, exceptionName);
        if (exceptionScopeInstance == null) {
            throw new WorkflowRuntimeException(this, getProcessInstance(), "Unable to execute Action: " + e.getMessage(), e);
        }
        exceptionScopeInstance.handleException(this, exceptionName, e);
        cancel();
    }
}
Also used : WorkflowRuntimeException(io.automatiko.engine.workflow.process.instance.WorkflowRuntimeException) ProcessContext(io.automatiko.engine.workflow.base.core.context.ProcessContext) WorkflowRuntimeException(io.automatiko.engine.workflow.process.instance.WorkflowRuntimeException) ExceptionScopeInstance(io.automatiko.engine.workflow.base.instance.context.exception.ExceptionScopeInstance)

Example 7 with WorkflowRuntimeException

use of io.automatiko.engine.workflow.process.instance.WorkflowRuntimeException in project automatiko-engine by automatiko-io.

the class CompensationEventListener method signalEvent.

/**
 * When signaling compensation, you can do that in 1 of 2 ways: 1.
 * signalEvent("Compensation", <node-with-compensation-handler-id>) This is
 * specific compensation, that only possibly triggers the compensation handler
 * attached to the node referred to by the <node-with-compensation-handler-id>.
 * 2. signalEvent("Compensation", "implicit:" +
 * <node-container-containing-compensation-scope-id> ) This is implicit or
 * general compensation, in which you trigger all visible compensation handlers
 * (in the proper order, etc.) in the (sub-)process referred to by the
 * <node-container-containing-compensation-scope-id>.
 */
public void signalEvent(String compensationType, Object activityRefStr) {
    if (!(activityRefStr instanceof String)) {
        throw new WorkflowRuntimeException(null, getProcessInstance(), "Compensation can only be triggered with String events, not an event of type " + (activityRefStr == null ? "null" : activityRefStr.getClass().getSimpleName()));
    }
    // 1. parse the activity ref (is it general or specific compensation?)
    String activityRef = (String) activityRefStr;
    String toCompensateNodeId = activityRef;
    boolean generalCompensation = false;
    if (activityRef.startsWith(IMPLICIT_COMPENSATION_PREFIX)) {
        toCompensateNodeId = activityRef.substring(IMPLICIT_COMPENSATION_PREFIX.length());
        generalCompensation = true;
    }
    io.automatiko.engine.workflow.base.core.Process process = (io.automatiko.engine.workflow.base.core.Process) instance.getProcess();
    // 2. for specific compensation: find the node that will be compensated
    // for general compensation: find the compensation scope container that contains
    // all the visible compensation handlers
    Node toCompensateNode = null;
    ContextContainer compensationScopeContainer = null;
    if (generalCompensation) {
        if (toCompensateNodeId.equals(instance.getProcessId())) {
            compensationScopeContainer = process;
        } else {
            compensationScopeContainer = (ContextContainer) findNode(toCompensateNodeId);
        }
    } else {
        toCompensateNode = findNode(toCompensateNodeId);
    }
    // c. handle the exception (which also cleans up the generated node instances)
    if (toCompensateNode != null || compensationScopeContainer != null) {
        CompensationScope compensationScope = null;
        if (compensationScopeContainer != null) {
            compensationScope = (CompensationScope) compensationScopeContainer.getDefaultContext(COMPENSATION_SCOPE);
        } else {
            compensationScope = (CompensationScope) ((NodeImpl) toCompensateNode).resolveContext(COMPENSATION_SCOPE, toCompensateNodeId);
        }
        assert compensationScope != null : "Compensation scope for node [" + toCompensateNodeId + "] could not be found!";
        CompensationScopeInstance scopeInstance;
        if (compensationScope.getContextContainerId().equals(process.getId())) {
            // process level compensation
            scopeInstance = (CompensationScopeInstance) instance.getContextInstance(compensationScope);
        } else {
            // nested compensation
            Stack<NodeInstance> generatedInstances;
            if (toCompensateNode == null) {
                // logic is the same if it's specific or general
                generatedInstances = createNodeInstanceContainers((Node) compensationScopeContainer, true);
            } else {
                generatedInstances = createNodeInstanceContainers(toCompensateNode, false);
            }
            NodeInstance nodeInstanceContainer = generatedInstances.peek();
            scopeInstance = ((CompensationScopeInstance) ((ContextInstanceContainer) nodeInstanceContainer).getContextInstance(compensationScope));
            scopeInstance.addCompensationInstances(generatedInstances);
        }
        scopeInstance.handleException(null, activityRef, null);
    }
}
Also used : NodeImpl(io.automatiko.engine.workflow.process.core.impl.NodeImpl) CompensationScopeInstance(io.automatiko.engine.workflow.base.instance.context.exception.CompensationScopeInstance) Node(io.automatiko.engine.api.definition.process.Node) ExecutableProcess(io.automatiko.engine.workflow.process.executable.core.ExecutableProcess) WorkflowRuntimeException(io.automatiko.engine.workflow.process.instance.WorkflowRuntimeException) ContextContainer(io.automatiko.engine.workflow.base.core.ContextContainer) CompensationScope(io.automatiko.engine.workflow.base.core.context.exception.CompensationScope) NodeInstance(io.automatiko.engine.workflow.process.instance.NodeInstance) CompositeNodeInstance(io.automatiko.engine.workflow.process.instance.node.CompositeNodeInstance)

Aggregations

WorkflowRuntimeException (io.automatiko.engine.workflow.process.instance.WorkflowRuntimeException)7 ExceptionScopeInstance (io.automatiko.engine.workflow.base.instance.context.exception.ExceptionScopeInstance)4 WorkItemExecutionError (io.automatiko.engine.api.workflow.workitem.WorkItemExecutionError)2 ProcessContext (io.automatiko.engine.workflow.base.core.context.ProcessContext)2 Date (java.util.Date)2 Node (io.automatiko.engine.api.definition.process.Node)1 ContextContainer (io.automatiko.engine.workflow.base.core.ContextContainer)1 CompensationScope (io.automatiko.engine.workflow.base.core.context.exception.CompensationScope)1 CompensationScopeInstance (io.automatiko.engine.workflow.base.instance.context.exception.CompensationScopeInstance)1 Action (io.automatiko.engine.workflow.base.instance.impl.Action)1 DefaultWorkItemManager (io.automatiko.engine.workflow.base.instance.impl.workitem.DefaultWorkItemManager)1 NodeImpl (io.automatiko.engine.workflow.process.core.impl.NodeImpl)1 Split (io.automatiko.engine.workflow.process.core.node.Split)1 ExecutableProcess (io.automatiko.engine.workflow.process.executable.core.ExecutableProcess)1 NodeInstance (io.automatiko.engine.workflow.process.instance.NodeInstance)1 WorkflowProcessInstance (io.automatiko.engine.workflow.process.instance.WorkflowProcessInstance)1 CompositeNodeInstance (io.automatiko.engine.workflow.process.instance.node.CompositeNodeInstance)1 HashMap (java.util.HashMap)1