From 7c6140517e937fd7bb642ebf2d652ec1c4b8fe90 Mon Sep 17 00:00:00 2001 From: Mikael Hugo Date: Sat, 2 May 2026 21:48:35 +0200 Subject: [PATCH] fix(sf): surface escalation write failures back to the agent MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit When sf_task_complete's escalation payload was rejected (validation error) or silently dropped (feature flag off), the agent saw a clean "Completed task" response and assumed the issue was raised — but no carry-forward override was created, so the next executor saw nothing. Now the response text explicitly says: - "WARNING: escalation payload was REJECTED (); the next executor will NOT see your decision" — when buildEscalationArtifact throws - "note: escalation payload was DROPPED because phases.mid_execution_escalation is disabled" — when feature flag is off Task completion is still never blocked by escalation issues — additive, auditable, agent-actionable. Co-Authored-By: Claude Opus 4.7 (1M context) --- .../sf/tools/workflow-tool-executors.ts | 19 ++++++++++++++++--- 1 file changed, 16 insertions(+), 3 deletions(-) diff --git a/src/resources/extensions/sf/tools/workflow-tool-executors.ts b/src/resources/extensions/sf/tools/workflow-tool-executors.ts index e172b4082..f3f489561 100644 --- a/src/resources/extensions/sf/tools/workflow-tool-executors.ts +++ b/src/resources/extensions/sf/tools/workflow-tool-executors.ts @@ -313,6 +313,8 @@ export async function executeTaskComplete( // payload backwards-compatible for callers that always send it. let escalationPath: string | undefined; let escalationStatus: "pending" | "awaiting-review" | undefined; + let escalationError: string | undefined; + let escalationDisabled = false; if (params.escalation) { try { const { loadEffectiveSFPreferences } = await import( @@ -337,12 +339,19 @@ export async function executeTaskComplete( escalationStatus = params.escalation.continueWithDefault ? "awaiting-review" : "pending"; + } else { + // Feature flag is off — surface this so the agent knows the payload + // was dropped and can either turn the feature on or just make the + // decision themselves. + escalationDisabled = true; } } catch (err) { - // Escalation is additive — never block task completion if it fails. + // Escalation is additive — never block task completion if it fails, + // but DO tell the agent so they don't think the issue was recorded. + escalationError = err instanceof Error ? err.message : String(err); logError( "tool", - `sf_task_complete escalation write failed: ${err instanceof Error ? err.message : String(err)}`, + `sf_task_complete escalation write failed: ${escalationError}`, { tool: "sf_task_complete", op: "escalation" }, ); } @@ -351,7 +360,11 @@ export async function executeTaskComplete( const baseText = `Completed task ${result.taskId} (${result.sliceId}/${result.milestoneId})`; const escalationSuffix = escalationStatus ? ` — escalation ${escalationStatus} at ${escalationPath}` - : ""; + : escalationError + ? ` — WARNING: escalation payload was REJECTED (${escalationError}); the next executor will NOT see your decision. Either fix the payload and retry, or make the choice yourself and document it in the summary.` + : escalationDisabled + ? ` — note: escalation payload was DROPPED because phases.mid_execution_escalation is disabled; document the choice in the summary instead.` + : ""; return { content: [ {