{"record":{"id":"aa488db0cb5ed80a","repo":"flowable/flowable-engine","slug":"cannot-migrate-historic-case-instances-not-enough","errorCode":null,"errorMessage":"Cannot migrate historic case instances, not enough information","messagePattern":"Cannot migrate historic case instances, not enough information","errorType":"exception","errorClass":"FlowableException","httpStatus":null,"severity":"error","filePath":"modules/flowable-cmmn-engine/src/main/java/org/flowable/cmmn/engine/impl/cmd/HistoricCaseInstanceMigrationBatchCmd.java","lineNumber":77,"sourceCode":"        }\n        this.caseDefinitionKey = caseDefinitionKey;\n        this.caseDefinitionVersion = caseDefinitionVersion;\n        this.caseDefinitionTenantId = caseDefinitionTenantId;\n        this.historicCaseInstanceMigrationDocument = historicCaseInstanceMigrationDocument;\n        this.cmmnEngineConfiguration = cmmnEngineConfiguration;\n    }\n\n    @Override\n    public Batch execute(CommandContext commandContext) {\n        CaseInstanceMigrationManager migrationManager = cmmnEngineConfiguration.getCaseInstanceMigrationManager();\n\n        if (caseDefinitionId != null) {\n            return migrationManager.batchMigrateHistoricCaseInstancesOfCaseDefinition(caseDefinitionId, historicCaseInstanceMigrationDocument, commandContext);\n        } else if (caseDefinitionKey != null && caseDefinitionVersion >= 0) {\n            return migrationManager.batchMigrateHistoricCaseInstancesOfCaseDefinition(caseDefinitionKey, caseDefinitionVersion, caseDefinitionTenantId, \n                    historicCaseInstanceMigrationDocument, commandContext);\n        } else {\n            throw new FlowableException(\"Cannot migrate historic case instances, not enough information\");\n        }\n    }\n}\n","sourceCodeStart":59,"sourceCodeEnd":81,"githubUrl":"https://github.com/flowable/flowable-engine/blob/d6d39ce1c69ff244f2d9dc6af756a9b95e865586/modules/flowable-cmmn-engine/src/main/java/org/flowable/cmmn/engine/impl/cmd/HistoricCaseInstanceMigrationBatchCmd.java#L59-L81","documentation":"HistoricCaseInstanceMigrationBatchCmd.execute() dispatches to the migration manager either by caseDefinitionId or by (key, version, tenantId). If none of those identifying fields are set, there is no way to select historic case instances, so execute() throws FlowableException('Cannot migrate historic case instances, not enough information'). This can only happen when an instance was created bypassing the validating constructors (e.g. deserialization or a default constructor path).","triggerScenarios":"Executing a HistoricCaseInstanceMigrationBatchCmd where caseDefinitionId == null AND (caseDefinitionKey == null OR caseDefinitionVersion < 0) — e.g. the object was built through a no-arg/reflective path or setters were never called; or caseDefinitionVersion left at its default (e.g. -1/0 sentinel below the >= 0 check).","commonSituations":"Constructing the command via reflection/serialization frameworks that skip constructor validation; copying a command object partially initialized; passing version 0 or -1 as 'latest' instead of a positive version number.","solutions":["Set caseDefinitionId (or the key/version/tenant triple with version >= 0) via the proper public constructor before executing the command.","If using key-based migration, ensure caseDefinitionVersion is a real deployed version number (>= 0); do not pass -1 as a 'latest' sentinel.","Avoid building this command reflectively or via a default-constructed instance; use HistoricCaseInstanceMigrationBuilder on the CmmnEngineConfiguration which populates fields correctly."],"exampleFix":"// before\nHistoricCaseInstanceMigrationBatchCmd cmd = new HistoricCaseInstanceMigrationBatchCmd();\ncmd.setMigrationDocument(doc); // no definition info set -> execute() throws\n\n// after\nHistoricCaseInstanceMigrationBatchCmd cmd = new HistoricCaseInstanceMigrationBatchCmd(\n    \"myCase\", 2, \"acme-tenant\", doc, cmmnEngineConfiguration); // fully identified","handlingStrategy":"validation","validationCode":"boolean canExecute = caseDefinitionId != null\n    || (caseDefinitionKey != null && caseDefinitionVersion >= 0 && tenantId != null);\nif (!canExecute)\n    throw new IllegalArgumentException(\"Provide definition id or (key, version >= 0, tenant) before executing batch migration\");","typeGuard":"boolean hasMigrationTarget(String id, String key, int version) {\n    return id != null || (key != null && version >= 0);\n}","tryCatchPattern":"try {\n    command.execute(commandContext);\n} catch (FlowableException e) {\n    if (e.getMessage().contains(\"not enough information\")) {\n        throw new ConfigurationException(\"Command built without definition id or key/version/tenant; use the public constructors\", e);\n    }\n    throw e;\n}","preventionTips":["Only build the command through its validating constructors or the migration builder API","Never pass -1 or 0 as a 'latest version' sentinel; query the actual latest version","Avoid reflective/deserialized construction that skips validation"],"tags":["flowable","cmmn","missing-required-argument","case-migration","command-execution"],"backgroundTag":"missing-required-argument","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"}