flowable/flowable-engine · error · IllegalStateException
Provided process definition must have a deployment id.
Error message
Provided process definition must have a deployment id.
What it means
getPersistedInstanceOfProcessDefinition requires the given process definition entity to already be attached to a deployment, because it looks the definition up by deploymentId + key. If deploymentId is null or empty it fails fast with this IllegalStateException rather than issuing a meaningless query.
Source
Thrown at modules/flowable-engine/src/main/java/org/flowable/engine/impl/bpmn/deployer/BpmnDeploymentHelper.java:158
ProcessDefinitionEntity existingDefinition = null;
if (tenantId != null && !tenantId.equals(ProcessEngineConfiguration.NO_TENANT_ID)) {
existingDefinition = processDefinitionManager.findLatestDerivedProcessDefinitionByKeyAndTenantId(key, tenantId);
} else {
existingDefinition = processDefinitionManager.findLatestDerivedProcessDefinitionByKey(key);
}
return existingDefinition;
}
/**
* Gets the persisted version of the already-deployed process definition. Note that this is different from {@link #getMostRecentVersionOfProcessDefinition} as it looks specifically for a process
* definition that is already persisted and attached to a particular deployment, rather than the latest version across all deployments.
*/
public ProcessDefinitionEntity getPersistedInstanceOfProcessDefinition(ProcessDefinitionEntity processDefinition) {
String deploymentId = processDefinition.getDeploymentId();
if (StringUtils.isEmpty(processDefinition.getDeploymentId())) {
throw new IllegalStateException("Provided process definition must have a deployment id.");
}
ProcessDefinitionEntityManager processDefinitionManager = CommandContextUtil.getProcessEngineConfiguration().getProcessDefinitionEntityManager();
ProcessDefinitionEntity persistedProcessDefinition = null;
if (processDefinition.getTenantId() == null || ProcessEngineConfiguration.NO_TENANT_ID.equals(processDefinition.getTenantId())) {
persistedProcessDefinition = processDefinitionManager.findProcessDefinitionByDeploymentAndKey(deploymentId, processDefinition.getKey());
} else {
persistedProcessDefinition = processDefinitionManager.findProcessDefinitionByDeploymentAndKeyAndTenantId(deploymentId, processDefinition.getKey(), processDefinition.getTenantId());
}
return persistedProcessDefinition;
}
/**
* Updates all timers and events for the process definition. The undeploy half iterates the previous
* process definition's top-level start events; each behavior either does its own per-start-event work
* (e.g. the EventRegistry "manual" re-point) or registers an obsolete event subscription / timer job
* handler type with the context. After the undeploy iteration the deployer issues one mass-delete perView on GitHub (pinned to d6d39ce1c6)
Solutions
- Only call this method after the definition has been persisted and its deploymentId set
- If you need the latest definition regardless of deployment, use getMostRecentVersionOfProcessDefinition instead
- Persist the deployment (or let the standard Persister/Deployer pipeline run) before invoking this helper
- Guard custom code with a null/empty deploymentId check and skip or reroute accordingly
Example fix
// before
helper.getPersistedInstanceOfProcessDefinition(unsavedDefinition);
// after
if (StringUtils.isNotEmpty(unsavedDefinition.getDeploymentId())) {
helper.getPersistedInstanceOfProcessDefinition(unsavedDefinition);
} else {
helper.getMostRecentVersionOfProcessDefinition(unsavedDefinition);
} Defensive patterns
Strategy: validation
Validate before calling
if (processDefinition.getDeploymentId() == null || processDefinition.getDeploymentId().isEmpty()) {
// use latest-version lookup instead
return bpmnDeploymentHelper.getMostRecentVersionOfProcessDefinition(processDefinition);
} Prevention
- Only call getPersistedInstanceOfProcessDefinition with definitions already persisted
- Prefer getMostRecentVersionOfProcessDefinition when deployment linkage is unknown
- Keep custom deployer code inside the standard lifecycle phases
When it happens
Trigger: Calling BpmnDeploymentHelper.getPersistedInstanceOfProcessDefinition with a ProcessDefinitionEntity that has not yet been persisted/assigned a deploymentId — e.g. during deployment before the entity is saved, or a programmatically built definition.
Common situations: Custom deployers or extension code invoking the helper with an in-memory (unsaved) definition; calling it in the wrong deployment lifecycle phase; mixing up getMostRecentVersionOfProcessDefinition with getPersistedInstanceOfProcessDefinition.
Understand the failure class
Background: "missing required argument" and "the following required arguments were not provided": what required-argument errors mean and how to fix them — this error's family across 20 libraries.
Related errors
- Provided process definition must have both key and resource
- The deployment contains process definitions with the same ke
- Provided process definition must have its resource name set.
- No deployed process definition found for key '{processDefini
- No process definition found for id '${processDefinitionId}'
AI-assisted analysis of flowable/flowable-engine@d6d39ce1c6 (2026-09-11).
Data as JSON: /api/errors/973c818701502de3.
Report an issue: GitHub.