Compare commits

...
Author SHA1 Message Date
Sonarly Claude Code dd265a5f0f Workflow error handler fails when workflow run record is already deleted
https://sonarly.com/issue/4404?type=bug

The catch block in RunWorkflowJob.handle() unconditionally calls endWorkflowRun() which requires the workflow run to exist, causing a cascading "Workflow run not found" error when the run record was deleted between job enqueue and execution.

Fix: When a workflow run is deleted (soft-deleted by user action or hard-deleted by the cleanup cron) while a job is still queued, the worker picks up the job and calls `getWorkflowRunOrFail()` which throws `WORKFLOW_RUN_NOT_FOUND`. The catch block then tries to call `endWorkflowRun()` to mark the run as failed, but `endWorkflowRun()` also calls `getWorkflowRunOrFail()` — causing the same error to cascade.

**Fix:** Added an early return in the catch blocks of both `RunWorkflowJob` and `ResumeDelayedWorkflowJob` when the error is `WORKFLOW_RUN_NOT_FOUND`. If the workflow run doesn't exist, there's nothing to mark as failed — the job should exit silently. This matches the team's existing pattern of early returns for expected workflow states (e.g., returning when status isn't ENQUEUED/NOT_STARTED in `startWorkflowExecution`).
2026-03-10 10:03:44 +00:00
2 changed files with 14 additions and 0 deletions
@@ -94,6 +94,13 @@ export class ResumeDelayedWorkflowJob {
},
);
} catch (error) {
if (
error instanceof WorkflowRunException &&
error.code === WorkflowRunExceptionCode.WORKFLOW_RUN_NOT_FOUND
) {
return;
}
await this.workflowRunWorkspaceService.endWorkflowRun({
workflowRunId,
workspaceId,
@@ -56,6 +56,13 @@ export class RunWorkflowJob {
});
}
} catch (error) {
if (
error instanceof WorkflowRunException &&
error.code === WorkflowRunExceptionCode.WORKFLOW_RUN_NOT_FOUND
) {
return;
}
await this.workflowRunWorkspaceService.endWorkflowRun({
workspaceId,
workflowRunId,