{"record":{"id":"fec1ebe2978e661a","repo":"flowable/flowable-engine","slug":"the-process-instance-id-is-mandatory-but-pro","errorCode":null,"errorMessage":"The process instance id is mandatory, but '\" + processInstanceId + \"' has been provided.\"","messagePattern":"The process instance id is mandatory, but '\" \\+ processInstanceId \\+ \"' has been provided\\.\"","errorType":"validation","errorClass":"FlowableIllegalArgumentException","httpStatus":null,"severity":"error","filePath":"modules/flowable-engine/src/main/java/org/flowable/engine/impl/cmd/ProcessInstanceClaimCmd.java","lineNumber":45,"sourceCode":"import org.flowable.engine.impl.util.CommandContextUtil;\nimport org.flowable.engine.impl.util.IdentityLinkUtil;\nimport org.flowable.engine.runtime.ProcessInstance;\nimport org.flowable.identitylink.api.IdentityLinkType;\nimport org.flowable.identitylink.service.impl.persistence.entity.IdentityLinkEntity;\n\n/**\n * {@link Command} that claims an existing process instance.\n */\npublic class ProcessInstanceClaimCmd implements Command<Void>, Serializable {\n\n    private static final long serialVersionUID = 1L;\n\n    private final String processInstanceId;\n    private final String userId;\n\n    public ProcessInstanceClaimCmd(String processInstanceId, String userId) {\n        if (processInstanceId == null || processInstanceId.isEmpty()) {\n            throw new FlowableIllegalArgumentException(\"The process instance id is mandatory, but '\" + processInstanceId + \"' has been provided.\");\n        }\n\n        this.processInstanceId = processInstanceId;\n        this.userId = userId;\n    }\n\n    @Override\n    public Void execute(CommandContext commandContext) {\n        ExecutionEntityManager executionManager = CommandContextUtil.getExecutionEntityManager(commandContext);\n        ExecutionEntity processInstance = executionManager.findById(processInstanceId);\n        if (processInstance == null) {\n            throw new FlowableObjectNotFoundException(\"No process instance found for id = '\" + processInstanceId + \"'.\", ProcessInstance.class);\n\n        } else if (!processInstance.isProcessInstanceType()) {\n            throw new FlowableIllegalArgumentException(\"A process instance id is required, but the provided id \" + \"'\" + processInstanceId + \"' \" + \"points to a child execution of process instance \" + \"'\"\n                    + processInstance.getProcessInstanceId() + \"'. \" + \"Please invoke the \" + getClass().getSimpleName() + \" with a root execution id.\");\n        }\n","sourceCodeStart":27,"sourceCodeEnd":63,"githubUrl":"https://github.com/flowable/flowable-engine/blob/d6d39ce1c69ff244f2d9dc6af756a9b95e865586/modules/flowable-engine/src/main/java/org/flowable/engine/impl/cmd/ProcessInstanceClaimCmd.java#L27-L63","documentation":"The ProcessInstanceClaimCmd constructor validates its arguments eagerly: if processInstanceId is null or an empty string, it throws FlowableIllegalArgumentException before any command context exists. Claiming (attaching a userId identity link to) a process instance requires a real instance id.","triggerScenarios":"new ProcessInstanceClaimCmd(null, userId) or new ProcessInstanceClaimCmd(\"\", userId), typically executed via ManagementService/CommandRunner.","commonSituations":"Binding the processInstanceId from a request path/body that was empty; a null result from a previous lookup passed straight into the command; Spring bean wiring calling the command with an unresolved property.","solutions":["Validate processInstanceId with a null/empty check before constructing the command.","Fix the upstream source (REST handler, query result) that produced the blank id.","Catch FlowableIllegalArgumentException at the command-dispatch boundary and return a 400-level validation error.","Use a domain helper that refuses to build the command for blank ids, keeping the check in one place."],"exampleFix":"// before\nmanagementService.executeCommand(new ProcessInstanceClaimCmd(processInstanceId, userId));\n// after\nif (processInstanceId == null || processInstanceId.isEmpty()) {\n    throw new IllegalArgumentException(\"processInstanceId is required\");\n}\nmanagementService.executeCommand(new ProcessInstanceClaimCmd(processInstanceId, userId));","handlingStrategy":"validation","validationCode":"Objects.requireNonNull(processInstanceId, \"processInstanceId is required\");\nif (processInstanceId.isEmpty()) { throw new IllegalArgumentException(\"processInstanceId must not be empty\"); }","typeGuard":"boolean isValidInstanceId(String id) { return id != null && !id.isEmpty(); }","tryCatchPattern":"try {\n    managementService.executeCommand(new ProcessInstanceClaimCmd(pid, userId));\n} catch (FlowableIllegalArgumentException e) {\n    throw new BadRequestException(\"A non-empty processInstanceId is required\");\n}","preventionTips":["Validate ids in REST controllers with @NotBlank before building commands.","Never forward null results of prior queries into new commands.","Centralize id validation in a command factory.","Test command constructors with null and empty inputs."],"tags":["flowable","null-argument","empty-string","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-18T11:17:12.947Z"}