flowable/flowable-engine · error · FlowableIllegalArgumentException
caseInstanceId is null
Error message
caseInstanceId is null
What it means
HasCaseInstanceVariableCmd.execute throws FlowableIllegalArgumentException when caseInstanceId is null. The command first validates its required arguments, then checks the case instance exists, before testing whether the variable is present. A null id cannot be resolved to any case instance, so it is rejected immediately.
Source
Thrown at modules/flowable-cmmn-engine/src/main/java/org/flowable/cmmn/engine/impl/cmd/HasCaseInstanceVariableCmd.java:44
* @author Tijs Rademakers
*/
public class HasCaseInstanceVariableCmd implements Command<Boolean>, Serializable {
private static final long serialVersionUID = 1L;
protected String caseInstanceId;
protected String variableName;
protected boolean isLocal;
public HasCaseInstanceVariableCmd(String caseInstanceId, String variableName, boolean isLocal) {
this.caseInstanceId = caseInstanceId;
this.variableName = variableName;
this.isLocal = isLocal;
}
@Override
public Boolean execute(CommandContext commandContext) {
if (caseInstanceId == null) {
throw new FlowableIllegalArgumentException("caseInstanceId is null");
}
if (variableName == null) {
throw new FlowableIllegalArgumentException("variableName is null");
}
CaseInstanceEntity caseInstance = CommandContextUtil.getCaseInstanceEntityManager(commandContext).findById(caseInstanceId);
if (caseInstance == null) {
throw new FlowableObjectNotFoundException("case instance " + caseInstanceId + " doesn't exist", CaseInstance.class);
}
boolean hasVariable = false;
if (isLocal) {
hasVariable = caseInstance.hasVariableLocal(variableName);
} else {
hasVariable = caseInstance.hasVariable(variableName);
}View on GitHub (pinned to d6d39ce1c6)
Solutions
- Verify caseInstanceId is populated before the call; trace its source
- Resolve the id via a CaseInstanceQuery and handle the no-match case first
- Wrap the call in a null check or use an Optional around the id
Example fix
// before boolean has = cmmnRuntimeService.hasVariable(caseInstanceId, "approved"); // after boolean has = caseInstanceId != null && cmmnRuntimeService.hasVariable(caseInstanceId, "approved");
Defensive patterns
Strategy: validation
Validate before calling
if (caseInstanceId == null) {
throw new IllegalArgumentException("caseInstanceId is required for hasVariable");
} Type guard
boolean validId(String id) {
return id != null && !id.isEmpty();
} Try / catch
try {
return cmmnRuntimeService.hasVariable(caseInstanceId, variableName);
} catch (FlowableIllegalArgumentException e) {
log.warn("Invalid hasVariable arguments: {}", e.getMessage());
return false;
} Prevention
- Null-check ids resolved from previous engine calls
- Prefer query-then-act: fetch the CaseInstance, then check variables
- Log id provenance to catch unpopulated fields early
When it happens
Trigger: Calling cmmnRuntimeService.hasVariable(null, variableName) or hasVariableLocal(null, variableName), or building the command directly with a null caseInstanceId.
Common situations: Chained lookups where an earlier query returned null, passing an uninitialized field from a delegation class, or copy/paste code where the id variable was renamed but not initialized.
Related errors
- planItemInstanceId is null
- planItemInstanceId is null
- variableName is null
- planItemInstanceId is null
- caseInstanceId is null
AI-assisted analysis of flowable/flowable-engine@d6d39ce1c6 (2026-09-11).
Data as JSON: /api/errors/e0f22f66145144f1.
Report an issue: GitHub.