{"record":{"id":"23be49103a30bcf7","repo":"flowable/flowable-engine","slug":"no-external-worker-job-found-for-id","errorCode":null,"errorMessage":"No External Worker job found for id: ","messagePattern":"No External Worker job found for id: ","errorType":"exception","errorClass":"FlowableObjectNotFoundException","httpStatus":null,"severity":"error","filePath":"modules/flowable-job-service/src/main/java/org/flowable/job/service/impl/cmd/AbstractExternalWorkerJobCmd.java","lineNumber":70,"sourceCode":"    }\n\n    protected abstract void runJobLogic(ExternalWorkerJobEntity externalWorkerJob, CommandContext commandContext);\n\n    protected ExternalWorkerJobEntity resolveJob() {\n        if (StringUtils.isEmpty(externalJobId)) {\n            throw new FlowableIllegalArgumentException(\"externalJobId must not be empty\");\n        }\n\n        if (StringUtils.isEmpty(workerId)) {\n            throw new FlowableIllegalArgumentException(\"workerId must not be empty\");\n        }\n\n        ExternalWorkerJobEntityManager externalWorkerJobEntityManager = jobServiceConfiguration.getExternalWorkerJobEntityManager();\n\n        ExternalWorkerJobEntity job = externalWorkerJobEntityManager.findById(externalJobId);\n\n        if (job == null) {\n            throw new FlowableObjectNotFoundException(\"No External Worker job found for id: \" + externalJobId, ExternalWorkerJobEntity.class);\n        }\n\n        if (!Objects.equals(workerId, job.getLockOwner())) {\n            throw new FlowableIllegalArgumentException(workerId + \" does not hold a lock on the requested job\");\n        }\n\n        return job;\n    }\n}\n","sourceCodeStart":52,"sourceCodeEnd":80,"githubUrl":"https://github.com/flowable/flowable-engine/blob/d6d39ce1c69ff244f2d9dc6af756a9b95e865586/modules/flowable-job-service/src/main/java/org/flowable/job/service/impl/cmd/AbstractExternalWorkerJobCmd.java#L52-L80","documentation":"Thrown by resolveJob() as a FlowableObjectNotFoundException when findById(externalJobId) returns no ExternalWorkerJobEntity. The job id was well-formed but no matching external worker job row exists anymore — typically because the job was already completed, deleted, or the id is wrong or from another database/tenant.","triggerScenarios":"Calling completeExternalWorkerJob/terminateExternalWorkerJob/failExternalWorkerJob with a job id that was deleted after completion; a stale job reference held across a long worker outage; typo'd or cross-environment job id; job removed by cleanup/history jobs in the meantime.","commonSituations":"Long-running worker holds an id while another worker instance completed the job; testing against one database and running against another; retry logic replaying completion for an already-processed job id.","solutions":["Treat this as an expected race: catch FlowableObjectNotFoundException and skip/ack the job as already handled","Verify the job id and database/tenant the command runs against match the acquisition","Check job retention: if jobs complete too fast, ensure your worker fetches fresh ids rather than caching them"],"exampleFix":"// before\nexternalWorkerJobCompletionBuilder.externalJobId(jobId).workerId(workerId).complete();\n// after\ntry {\n    externalWorkerJobCompletionBuilder.externalJobId(jobId).workerId(workerId).complete();\n} catch (FlowableObjectNotFoundException e) {\n    LOGGER.info(\"External worker job {} already gone, skipping\", jobId);\n}","handlingStrategy":"try-catch","validationCode":null,"typeGuard":null,"tryCatchPattern":"try {\n    completionBuilder.externalJobId(jobId).workerId(workerId).complete();\n} catch (FlowableObjectNotFoundException e) {\n    LOGGER.info(\"Job {} no longer exists (already completed/deleted), skipping\", jobId);\n}","preventionTips":["Do not cache external job ids across long processing delays","Catch FlowableObjectNotFoundException around completion and treat it as idempotent success","Ensure all workers point at the same database/tenant as the acquisition"],"tags":["not-found","flowable","external-worker-job"],"backgroundTag":"record-not-found","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"}