Activiti/Activiti · error · ActivitiIllegalArgumentException
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 ${getClass().getSimpleName()} with a root execution id. What it means
The provided id exists but points to a child execution (a concurrent branch or scope) rather than the root process instance execution — ExecutionEntity.isProcessInstanceType() returned false. Activiti requires a root execution id for version switching, so it throws ActivitiIllegalArgumentException and tells you the parent process instance id to use instead.
Solutions
- Resolve the root id: execution.getProcessInstanceId() gives the process instance id — use that
- If you have an ExecutionEntity, check isProcessInstanceType() before using its id
- Get ids from runtimeService.createProcessInstanceQuery() instead of createExecutionQuery() when you need instances
Example fix
// before runtimeService.setProcessDefinitionVersion(execution.getId(), version); // child execution // after runtimeService.setProcessDefinitionVersion(execution.getProcessInstanceId(), version);
Defensive patterns
Strategy: type-guard
Validate before calling
if (executionEntity != null && !executionEntity.isProcessInstanceType()) {
instanceId = executionEntity.getProcessInstanceId();
} Type guard
String toProcessInstanceId(ExecutionEntity e) {
return (e != null && e.isProcessInstanceType()) ? e.getId() : e.getProcessInstanceId();
} Try / catch
try {
runtimeService.setProcessDefinitionVersion(executionId, version);
} catch (ActivitiIllegalArgumentException e) {
log.error("Need root execution id: {}", e.getMessage());
} Prevention
- Distinguish Execution.getId() from ProcessInstance.getId() in your domain model
- In delegates, always use getProcessInstanceId() for instance-level operations
- Never feed execution-query results into instance-level APIs unchecked
When it happens
Trigger: Passing an Execution.getId() (from runtimeService.createExecutionQuery() or a receive-task/message correlation) into setProcessDefinitionVersion instead of the ProcessInstance.getId().
Common situations: Code that holds only an ExecutionEntity (e.g. inside a delegate or event listener) and uses its id directly; message boundary events on embedded sub-processes returning child execution ids.
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
- Could not find a scope execution for compensation boundary…
- No execution found for sub process of boundary cancel event
- Programmatic error: no parent scope execution found for…
- Programmatic error: no parent scope execution found for…
AI-assisted analysis of Activiti/Activiti@56435b1a97 (2026-09-09).
Data as JSON: /api/errors/07f35cde544ab5d2.
Report an issue: GitHub.
Appendix: source
Thrown at activiti-core/activiti-engine/src/main/java/org/activiti/engine/impl/cmd/SetProcessDefinitionVersionCmd.java:93
"' has been provided."
);
}
this.processInstanceId = processInstanceId;
this.processDefinitionVersion = processDefinitionVersion;
}
public Void execute(CommandContext commandContext) {
// check that the new process definition is just another version of the same
// process definition that the process instance is using
ExecutionEntityManager executionManager = commandContext.getExecutionEntityManager();
ExecutionEntity processInstance = executionManager.findById(processInstanceId);
if (processInstance == null) {
throw new ActivitiObjectNotFoundException(
"No process instance found for id = '" + processInstanceId + "'.",
ProcessInstance.class
);
} else if (!processInstance.isProcessInstanceType()) {
throw new ActivitiIllegalArgumentException(
"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."
);
}
DeploymentManager deploymentCache = commandContext.getProcessEngineConfiguration().getDeploymentManager();
ProcessDefinition currentProcessDefinition = deploymentCache.findDeployedProcessDefinitionById(
processInstance.getProcessDefinitionId()
);View on GitHub (pinned to 56435b1a97)