{"record":{"id":"4fcf0b61b5951665","repo":"flowable/flowable-engine","slug":"can-only-unacquire-bpmn-or-cmmn-external-job-job","errorCode":null,"errorMessage":"Can only unacquire BPMN or CMMN external job. Job with id '${jobId}' is from scope '${scopeType}'","messagePattern":"Can only unacquire BPMN or CMMN external job\\. Job with id '(.+?)' is from scope '(.+?)'","errorType":"validation","errorClass":"FlowableIllegalArgumentException","httpStatus":null,"severity":"error","filePath":"modules/flowable-external-job-rest/src/main/java/org/flowable/external/job/rest/service/api/acquire/ExternalWorkerUnacquireJobResource.java","lineNumber":109,"sourceCode":"                managementService.unacquireExternalWorkerJob(jobId, workerId);\n                \n            } else {\n                throw new FlowableException(\"Cannot unacquire BPMN job. There is no BPMN engine available\");\n            }\n        } else if (ScopeTypes.CMMN.equals(job.getScopeType())) {\n            if (cmmnManagementService != null) {\n                if (restApiInterceptor != null) {\n                    restApiInterceptor.unacquireExternalWorkerJob(job, request);\n                }\n\n                cmmnManagementService.unacquireExternalWorkerJob(jobId, workerId);\n                \n            } else {\n                throw new FlowableException(\"Cannot unacquire CMMN job. There is no CMMN engine available\");\n            }\n            \n        } else {\n            throw new FlowableIllegalArgumentException(\n                    \"Can only unacquire BPMN or CMMN external job. Job with id '\" + jobId + \"' is from scope '\" + job.getScopeType() + \"'\");\n        }\n\n        return ResponseEntity.noContent().build();\n    }\n    \n    protected void unaquireExternalWorkerJobs(String workerId, String tenantId) {\n        if (managementService != null) {\n            if (StringUtils.isNotEmpty(tenantId)) {\n                managementService.unacquireAllExternalWorkerJobsForWorker(workerId, tenantId);\n            } else {\n                managementService.unacquireAllExternalWorkerJobsForWorker(workerId);\n            }\n            \n        } else if (cmmnManagementService != null) {\n            if (StringUtils.isNotEmpty(tenantId)) {\n                cmmnManagementService.unacquireAllExternalWorkerJobsForWorker(workerId, tenantId);\n            } else {","sourceCodeStart":91,"sourceCodeEnd":127,"githubUrl":"https://github.com/flowable/flowable-engine/blob/d6d39ce1c69ff244f2d9dc6af756a9b95e865586/modules/flowable-external-job-rest/src/main/java/org/flowable/external/job/rest/service/api/acquire/ExternalWorkerUnacquireJobResource.java#L91-L127","documentation":"FlowableIllegalArgumentException thrown by unaquireJob when the job's scopeType is neither BPMN nor CMMN. Only external worker jobs tied to a process instance or case instance can be unacquired through this endpoint. The message includes the offending jobId and actual scope value.","triggerScenarios":"POST /external-worker-job/unacquire/jobs/{jobId} where the resolved job's scopeType is null or an unsupported value (e.g. a standalone/async external job without scope, or a custom scope type).","commonSituations":"Jobs created outside a process/case context; upgrading Flowable versions where scope handling changed; pointing the client at a job id from a different subsystem.","solutions":["Only unacquire jobs that were acquired through the external worker acquisition API for BPMN/CMMN scopes.","Check the job's SCOPE_TYPE_ column in ACT_RU_EXTERNAL_JOB to see what scope it carries.","If the job should be scoped, fix the model so the external job is created inside a process/case.","Use the correct endpoint or engine API for standalone jobs if that is the intent."],"exampleFix":"// before: attempting unacquire of a standalone job id\nDELETE-style call with jobId of a scopeless external job\n// after\nacquire and complete/unacquire only jobs returned by the external worker acquire endpoint","handlingStrategy":"validation","validationCode":"String scope = job.getScopeType();\nif (!\"bpmn\".equals(scope) && !\"cmmn\".equals(scope)) { throw new IllegalArgumentException(\"Unsupported scope: \" + scope); }","typeGuard":"boolean isBpmnOrCmmn(ExternalWorkerJob job) { return ScopeTypes.BPMN.equals(job.getScopeType()) || ScopeTypes.CMMN.equals(job.getScopeType()); }","tryCatchPattern":"try { unaquireJob(jobId, request); } catch (FlowableIllegalArgumentException e) { if (e.getMessage().contains(\"Can only unacquire BPMN or CMMN\")) { useCorrectEndpointForJob(); } else { throw e; } }","preventionTips":["Only unacquire jobs obtained via the external worker acquire API","Check scope type before calling","Avoid pointing clients at standalone job ids"],"tags":["validation","scope","external-worker","rest-api"],"backgroundTag":"invalid-argument-value","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"}