alibaba/spring-ai-alibaba · info · BizException

WORKFLOW_RUN_CANCEL

WORKFLOW_RUN_CANCEL

Error message

Manually terminated

What it means

AbstractExecuteProcessor.preCheck() runs before each workflow node executes. If the workflow context's task status is NodeStatusEnum.STOP, it throws a BizException with code WORKFLOW_RUN_CANCEL to abort the run — the workflow was manually terminated by a user.

Source

Thrown at spring-ai-alibaba-admin/spring-ai-alibaba-admin-server-core/src/main/java/com/alibaba/cloud/ai/studio/core/workflow/processor/AbstractExecuteProcessor.java:181

			// Node execution error, save execution result and record error information
			NodeResult errorNodeResult = NodeResult.error(node, e.getMessage());
			errorNodeResult.setInput(JsonUtils.toJson(constructInputParamsMap(node, context)));
			handleNodeResult(graph, node, context, errorNodeResult, start);
		}
	}

	/**
	 * Pre-execution validation checks. Verifies: 1. Workflow is not stopped 2. Node has
	 * valid successors (unless it's an end node)
	 * @param graph The workflow graph
	 * @param node The node to validate
	 * @param context The workflow context
	 * @throws BizException if validation fails
	 */
	public void preCheck(DirectedAcyclicGraph<String, Edge> graph, Node node, WorkflowContext context) {
		// boolean b = workflowInnerService.checkValidFlag(context);
		if (context.getTaskStatus().equals(NodeStatusEnum.STOP.getCode())) {
			throw new BizException(ErrorCode.WORKFLOW_RUN_CANCEL.toError("Manually terminated"));
		}
		if ((!node.getId().startsWith("End_") && !node.getId().startsWith("IteratorEnd_")
				&& !node.getId().startsWith("ParallelEnd_"))
				&& CollectionUtils.isEmpty(graph.outgoingEdgesOf(node.getId()))) {
			throw new BizException(ErrorCode.WORKFLOW_CONFIG_INVALID
				.toError("the current node has no successor node, and it cannot function properly."));
		}
	}

	/**
	 * Core execution logic to be implemented by concrete processors.
	 * @param graph The workflow graph
	 * @param node The node to execute
	 * @param context The workflow context
	 * @return NodeResult containing execution results
	 */
	public abstract NodeResult innerExecute(DirectedAcyclicGraph<String, Edge> graph, Node node,
			WorkflowContext context);

View on GitHub (pinned to f82da0b50f)

Solutions

  1. Treat this as expected control flow: catch BizException with code WORKFLOW_RUN_CANCEL and mark the run as cancelled rather than failed
  2. Ensure the UI only sends cancel when the run is active, and update task status idempotently
  3. If it fires unexpectedly, check whether some service is writing NodeStatusEnum.STOP into the context erroneously

Example fix

// before
catch (BizException e) { log.error("node failed", e); }
// after
catch (BizException e) {
  if (e.getCode() == ErrorCode.WORKFLOW_RUN_CANCEL.getCode()) {
    context.setTaskStatus(NodeStatusEnum.STOP.getCode()); return; // expected cancel
  }
  throw e;
}
Defensive patterns

Strategy: try-catch

Validate before calling

if (context.getTaskStatus() == NodeStatusEnum.STOP.getCode()) {
    // skip node execution proactively
    return;
}

Type guard

static boolean isCancelled(WorkflowContext ctx) {
    return ctx != null && NodeStatusEnum.STOP.getCode().equals(ctx.getTaskStatus());
}

Try / catch

try {
    processor.execute(graph, node, context);
} catch (BizException e) {
    if (ErrorCode.WORKFLOW_RUN_CANCEL.getCode().equals(e.getCode())) {
        log.info("Workflow {} cancelled by user", context.getRequestId());
        return;
    }
    throw e;
}

Prevention

When it happens

Trigger: A user pressed stop/cancel on a running workflow (task status set to STOP in the context), and the next node's execute() calls preCheck() before running.

Common situations: Long-running workflow executions cancelled from the Studio/Admin UI; concurrent cancel requests racing node execution.

Understand the failure class

Background: "Invalid state transition" errors: "status must be X, actually Y", "already rejected/charging/uninstalled", "cannot ... while running" — what they mean when a library rejects your call — this error's family across 31 libraries.

Related errors


AI-assisted analysis of alibaba/spring-ai-alibaba@f82da0b50f (2026-09-09). Data as JSON: /api/errors/07cf595cbd36f465. Report an issue: GitHub.