flowable/flowable-engine · error · FlowableIllegalArgumentException

Case definition ids is null

Error message

Case definition ids is null

What it means

HistoricCaseInstanceQueryImpl.caseDefinitionIds() requires a non-null Set of case definition ids. A null set cannot be translated into an SQL IN clause, so Flowable throws FlowableIllegalArgumentException immediately. Fail-fast validation protects the query execution phase.

Solutions

  1. Build the id set defensively and only call caseDefinitionIds when it is non-null
  2. Pass an empty set or omit the filter if no ids were selected
  3. Fall back to caseDefinitionId when there is exactly one id
  4. Catch FlowableIllegalArgumentException and surface a validation message

Example fix

// before
query.caseDefinitionIds(idsByIdentifier.get(tenant)); // may be null
// after
Set<String> ids = idsByIdentifier.get(tenant);
if (ids != null) {
    query.caseDefinitionIds(ids);
}
Defensive patterns

Strategy: validation

Validate before calling

if (caseDefinitionIds != null && !caseDefinitionIds.isEmpty()) {
    query.caseDefinitionIds(caseDefinitionIds);
}

Type guard

boolean validIdSet = ids != null;

Try / catch

try {
    query.caseDefinitionIds(ids);
} catch (FlowableIllegalArgumentException e) {
    throw new BadRequestException("caseDefinitionIds must not be null", e);
}

Prevention

When it happens

Trigger: Calling caseDefinitionIds(null), or passing a set built from an upstream source that returned null (e.g. Map.get or an unmarshalled payload field).

Common situations: Batch filters assembled from config or request bodies where the ids array is missing; code refactors replacing caseDefinitionId with the plural variant without a null guard.

Related errors


AI-assisted analysis of flowable/flowable-engine@d6d39ce1c6 (2026-09-11). Data as JSON: /api/errors/295c19bcdf357268. Report an issue: GitHub.

Appendix: source

Thrown at modules/flowable-cmmn-engine/src/main/java/org/flowable/cmmn/engine/impl/history/HistoricCaseInstanceQueryImpl.java:171

    }

    @Override
    public HistoricCaseInstanceQueryImpl caseDefinitionId(String caseDefinitionId) {
        if (caseDefinitionId == null) {
            throw new FlowableIllegalArgumentException("Case definition id is null");
        }
        if (inOrStatement) {
            this.currentOrQueryObject.caseDefinitionId = caseDefinitionId;
        } else {
            this.caseDefinitionId = caseDefinitionId;
        }
        return this;
    }

    @Override
    public HistoricCaseInstanceQuery caseDefinitionIds(Set<String> caseDefinitionIds) {
        if (caseDefinitionIds == null) {
            throw new FlowableIllegalArgumentException("Case definition ids is null");
        }
        if (inOrStatement) {
            this.currentOrQueryObject.caseDefinitionIds = caseDefinitionIds;
        } else {
            this.caseDefinitionIds = caseDefinitionIds;
        }
        return this;
    }

    @Override
    public HistoricCaseInstanceQueryImpl caseDefinitionKey(String caseDefinitionKey) {
        if (caseDefinitionKey == null) {
            throw new FlowableIllegalArgumentException("Case definition key is null");
        }
        if (inOrStatement) {
            this.currentOrQueryObject.caseDefinitionKey = caseDefinitionKey;
        } else {
            this.caseDefinitionKey = caseDefinitionKey;

View on GitHub (pinned to d6d39ce1c6)