{"record":{"id":"bdd6801c90b674bc","repo":"flowable/flowable-engine","slug":"rootscopeids-is-null-or-empty-bdd680","errorCode":null,"errorMessage":"rootScopeIds is null or empty","messagePattern":"rootScopeIds is null or empty","errorType":"validation","errorClass":"FlowableIllegalArgumentException","httpStatus":null,"severity":"error","filePath":"modules/flowable-cmmn-engine/src/main/java/org/flowable/cmmn/engine/impl/runtime/CaseInstanceQueryImpl.java","lineNumber":386,"sourceCode":"    }\n\n    @Override\n    public CaseInstanceQuery caseInstanceRootScopeId(String rootScopeId) {\n        if (rootScopeId == null) {\n            throw new FlowableIllegalArgumentException(\"rootScopeId is null\");\n        }\n        if (inOrStatement) {\n            this.currentOrQueryObject.rootScopeId = rootScopeId;\n        } else {\n            this.rootScopeId = rootScopeId;\n        }\n        return this;\n    }\n\n    @Override\n    public CaseInstanceQuery caseInstanceRootScopeIds(Set<String> rootScopeIds) {\n        if (rootScopeIds == null || rootScopeIds.isEmpty()) {\n            throw new FlowableIllegalArgumentException(\"rootScopeIds is null or empty\");\n        }\n        if (inOrStatement) {\n            this.currentOrQueryObject.rootScopeIds = rootScopeIds;\n        } else {\n            this.rootScopeIds = rootScopeIds;\n        }\n        return this;\n    }\n\n    @Override\n    public CaseInstanceQuery caseInstanceParentScopeId(String parentScopeId) {\n        if (parentScopeId == null) {\n            throw new FlowableIllegalArgumentException(\"parentScopeId is null\");\n        }\n        if (inOrStatement) {\n            this.currentOrQueryObject.parentScopeId = parentScopeId;\n        } else {\n            this.parentScopeId = parentScopeId;","sourceCodeStart":368,"sourceCodeEnd":404,"githubUrl":"https://github.com/flowable/flowable-engine/blob/d6d39ce1c69ff244f2d9dc6af756a9b95e865586/modules/flowable-cmmn-engine/src/main/java/org/flowable/cmmn/engine/impl/runtime/CaseInstanceQueryImpl.java#L368-L404","documentation":"Flowable's CaseInstanceQueryImpl throws FlowableIllegalArgumentException when caseInstanceRootScopeIds(Set<String>) is called with a null or empty set. The query API requires at least one root scope id because an empty IN-clause would produce invalid or meaningless SQL against the case instance table. Throwing early gives immediate feedback instead of a broken query at execution time.","triggerScenarios":"Calling cmmnRuntimeService.createCaseInstanceQuery().caseInstanceRootScopeIds(null), or caseInstanceRootScopeIds(Collections.emptySet()) / a Set that was filtered down to zero elements, before executing the query.","commonSituations":"Building queries dynamically where root scope ids come from an upstream lookup (parent process/relation table) that returned nothing; passing an unfiltered collection variable; copying code from caseInstanceParentScopeIds and passing the wrong (empty) collection; unit tests with no seeded data.","solutions":["Ensure at least one root scope id is resolved before calling the method; skip the filter clause entirely when the set is empty instead of calling it","Guard the call: only invoke caseInstanceRootScopeIds when ids != null && !ids.isEmpty()","Check the upstream data source that produces the ids (parent case/process instance actually exists)","If the intent is 'all case instances', drop the root-scope criterion rather than passing an empty set"],"exampleFix":"// before\nquery.caseInstanceRootScopeIds(collectRootScopeIds()); // NPE/empty -> FlowableIllegalArgumentException\n// after\nSet<String> rootScopeIds = collectRootScopeIds();\nif (rootScopeIds != null && !rootScopeIds.isEmpty()) {\n    query.caseInstanceRootScopeIds(rootScopeIds);\n}","handlingStrategy":"validation","validationCode":"if (rootScopeIds == null || rootScopeIds.isEmpty()) {\n    throw new IllegalArgumentException(\"rootScopeIds must contain at least one id\");\n}\nquery.caseInstanceRootScopeIds(rootScopeIds);","typeGuard":"boolean hasRootScopeIds(Set<String> ids) {\n    return ids != null && !ids.isEmpty();\n}","tryCatchPattern":"try {\n    query.caseInstanceRootScopeIds(rootScopeIds);\n} catch (FlowableIllegalArgumentException e) {\n    log.warn(\"Invalid root scope ids for case instance query: {}\", e.getMessage());\n    // rebuild query without the root-scope criterion or fail the request with 400\n}","preventionTips":["Always null/empty-check collections before passing them to Flowable query filter methods","Skip adding filter criteria that have no value instead of passing null/empty","Centralize query building in a helper that applies only populated filters","Test query builders with empty upstream result sets"],"tags":["flowable","cmmn","query","null-check","validation"],"backgroundTag":"empty-required-field","analyzedSha":"d6d39ce1c69ff244f2d9dc6af756a9b95e865586","analyzedAt":"2026-09-11T06:41:19.413Z","contentChangedAt":"2026-09-11T06:41:19.413Z","schemaVersion":2},"datasetVersion":"2026-09-14T05:17:10.506Z"}