From 76e0e71fdab9c95df82c271489d827fbbb346e2d Mon Sep 17 00:00:00 2001 From: cte Date: Fri, 9 Jan 2026 13:15:52 -0800 Subject: [PATCH] Untested fix for cli task resumption --- src/core/task/Task.ts | 36 ++++++++++++++++++++++++++++++++++-- 1 file changed, 34 insertions(+), 2 deletions(-) diff --git a/src/core/task/Task.ts b/src/core/task/Task.ts index d3239983af..7ee4b007f5 100644 --- a/src/core/task/Task.ts +++ b/src/core/task/Task.ts @@ -1871,6 +1871,16 @@ export class Task extends EventEmitter implements TaskLike { } private async resumeTaskFromHistory() { + // Reset abort and streaming state to ensure clean continuation. + // This matches the behavior in resumeAfterDelegation() and prevents + // corrupted state from a previous cancellation. + this.abort = false + this.abandoned = false + this.abortReason = undefined + this.didFinishAbortingStream = false + this.isStreaming = false + this.isWaitingForFirstChunk = false + if (this.enableBridge) { try { await BridgeOrchestrator.subscribeToTask(this) @@ -1971,7 +1981,22 @@ export class Task extends EventEmitter implements TaskLike { this.isInitialized = true - const { response, text, images } = await this.ask(askType) // Calls `postStateToWebview`. + let response: ClineAskResponse + let text: string | undefined + let images: string[] | undefined + + try { + const result = await this.ask(askType) // Calls `postStateToWebview`. + response = result.response + text = result.text + images = result.images + } catch (error) { + // Handle abort gracefully - if task was aborted during the ask, don't throw + if (this.abort) { + return + } + throw error + } let responseText: string | undefined let responseImages: string[] | undefined @@ -2156,7 +2181,14 @@ export class Task extends EventEmitter implements TaskLike { await this.overwriteApiConversationHistory(modifiedApiConversationHistory) // Task resuming from history item. - await this.initiateTaskLoop(newUserContent) + await this.initiateTaskLoop(newUserContent).catch((error) => { + // Swallow loop rejection when the task was intentionally abandoned/aborted + // during delegation or user cancellation to prevent unhandled rejections. + if (this.abandoned === true || this.abortReason === "user_cancelled") { + return + } + throw error + }) } /**