From 34b4f397b1f46cb5027ba910983021a68f3e7333 Mon Sep 17 00:00:00 2001 From: Peter Stone Date: Thu, 26 Mar 2026 07:03:02 +0000 Subject: fix: cancel waiting tasks when dep hits terminal failure (QUEUED→CANCELLED) MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit QUEUED→FAILED is not a valid state transition. When a dependency enters a terminal failure state, cancel the waiting task instead. Co-Authored-By: Claude Sonnet 4.6 --- internal/executor/executor.go | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) (limited to 'internal') diff --git a/internal/executor/executor.go b/internal/executor/executor.go index d2b476a..6aef736 100644 --- a/internal/executor/executor.go +++ b/internal/executor/executor.go @@ -777,21 +777,21 @@ func (p *Pool) execute(ctx context.Context, t *task.Task) { if len(t.DependsOn) > 0 { ready, depErr := p.checkDepsReady(t) if depErr != nil { - // A dependency hit a terminal failure — fail this task immediately. + // A dependency hit a terminal failure — cancel this task immediately. now := time.Now().UTC() exec := &storage.Execution{ ID: uuid.New().String(), TaskID: t.ID, StartTime: now, EndTime: now, - Status: "FAILED", + Status: "CANCELLED", ErrorMsg: depErr.Error(), } if createErr := p.store.CreateExecution(exec); createErr != nil { p.logger.Error("failed to create execution record", "error", createErr) } - if err := p.store.UpdateTaskState(t.ID, task.StateFailed); err != nil { - p.logger.Error("failed to update task state", "taskID", t.ID, "state", task.StateFailed, "error", err) + if err := p.store.UpdateTaskState(t.ID, task.StateCancelled); err != nil { + p.logger.Error("failed to update task state", "taskID", t.ID, "state", task.StateCancelled, "error", err) } p.resultCh <- &Result{TaskID: t.ID, Execution: exec, Err: depErr} return -- cgit v1.2.3