flowable/flowable-engine · error · FlowableIllegalArgumentException
A process instance id is required, but the provided id
Error message
A process instance id is required, but the provided id '${processInstanceId}' points to a child execution of process instance '${processInstance.getProcessInstanceId()}'. Please invoke the ${class simple name} with a root execution id. What it means
Thrown when the supplied id belongs to a child execution rather than the root process instance execution. Business status lives on the root execution, so the command rejects child execution ids and suggests using the root id.
Solutions
- Use execution.getProcessInstanceId() (or task.getProcessInstanceId()) as the id argument.
- Confirm via RuntimeService.createProcessInstanceQuery() that the id is a process instance.
- Refactor delegates to always resolve the root id before calling the API.
Example fix
// before runtimeService.setProcessInstanceBusinessStatus(execution.getId(), status); // after runtimeService.setProcessInstanceBusinessStatus(execution.getProcessInstanceId(), status);
Defensive patterns
Strategy: validation
Validate before calling
ProcessInstance pi = runtimeService.createProcessInstanceQuery()
.processInstanceId(candidateId).singleResult();
if (pi == null || !candidateId.equals(pi.getId())) {
throw new IllegalArgumentException("must pass a root process instance id");
} Try / catch
try {
runtimeService.setProcessInstanceBusinessStatus(id, status);
} catch (FlowableIllegalArgumentException e) {
if (e.getMessage().contains("child execution")) {
String rootId = execution.getProcessInstanceId();
runtimeService.setProcessInstanceBusinessStatus(rootId, status);
}
} Prevention
- Prefer execution.getProcessInstanceId() over execution.getId() in delegates/listeners.
- Remember scope executions of sub-processes are not process instances.
- Keep helper methods that resolve the root id once and reuse it.
When it happens
Trigger: Passing Task.getExecutionId() or DelegateExecution.getId() (a child scope execution) to setProcessInstanceBusinessStatus instead of the process instance id.
Common situations: Code inside task listeners or JavaDelegates that has an Execution/Task at hand and mistakes the execution id for the process instance id, common with embedded sub-processes and call activities.
Understand the failure class
Background: "Must be a positive integer", "Invalid value", "Unsupported": the invalid-argument-value error family, when a library rejects the value you pass — this error's family across 35 libraries.
Related errors
- A process instance id is required, but the provided id
- ProcessInstanceId cannot be null.
- ProcessInstanceId cannot be null.
- processInstanceId is null
- processInstanceId is null
AI-assisted analysis of flowable/flowable-engine@d6d39ce1c6 (2026-09-11).
Data as JSON: /api/errors/df71144f0d43c069.
Report an issue: GitHub.
Appendix: source
Thrown at modules/flowable-engine/src/main/java/org/flowable/engine/impl/cmd/SetProcessInstanceBusinessStatusCmd.java:60
throw new FlowableIllegalArgumentException("The process instance id is mandatory, but '" + processInstanceId + "' has been provided.");
}
if (businessStatus == null) {
throw new FlowableIllegalArgumentException("The business status is mandatory, but 'null' has been provided.");
}
this.processInstanceId = processInstanceId;
this.businessStatus = businessStatus;
}
@Override
public Void execute(CommandContext commandContext) {
ExecutionEntityManager executionManager = CommandContextUtil.getExecutionEntityManager(commandContext);
ExecutionEntity processInstance = executionManager.findById(processInstanceId);
if (processInstance == null) {
throw new FlowableObjectNotFoundException("No process instance found for id = '" + processInstanceId + "'.", ProcessInstance.class);
} else if (!processInstance.isProcessInstanceType()) {
throw new FlowableIllegalArgumentException("A process instance id is required, but the provided id " + "'" + processInstanceId + "' " + "points to a child execution of process instance " + "'"
+ processInstance.getProcessInstanceId() + "'. " + "Please invoke the " + getClass().getSimpleName() + " with a root execution id.");
}
executionManager.updateProcessInstanceBusinessStatus(processInstance, businessStatus);
return null;
}
}
View on GitHub (pinned to d6d39ce1c6)