From 0fa5e3488836ddecd101c5a6d591ef6cf72fe5b4 Mon Sep 17 00:00:00 2001 From: kiwina Date: Mon, 2 Jun 2025 14:37:19 +0800 Subject: [PATCH 1/4] fix: auto patch for api_provider_clients --- src/api/index.ts | 5 +++++ src/api/providers/base-provider.ts | 21 +++++++++++++++++++++ src/core/task/Task.ts | 20 ++++++++++++++++++++ 3 files changed, 46 insertions(+) diff --git a/src/api/index.ts b/src/api/index.ts index 8b09bf4cf9..e224be0525 100644 --- a/src/api/index.ts +++ b/src/api/index.ts @@ -56,6 +56,11 @@ export interface ApiHandler { * @returns A promise resolving to the token count */ countTokens(content: Array): Promise + + /** + * Optional method to dispose of any resources held by the API handler. + */ + dispose?: () => void } export function buildApiHandler(configuration: ProviderSettings): ApiHandler { diff --git a/src/api/providers/base-provider.ts b/src/api/providers/base-provider.ts index 1abbf5f558..abbc9923e1 100644 --- a/src/api/providers/base-provider.ts +++ b/src/api/providers/base-provider.ts @@ -10,6 +10,8 @@ import { countTokens } from "../../utils/countTokens" * Base class for API providers that implements common functionality. */ export abstract class BaseProvider implements ApiHandler { + protected client: any // Added protected client field + abstract createMessage( systemPrompt: string, messages: Anthropic.Messages.MessageParam[], @@ -32,4 +34,23 @@ export abstract class BaseProvider implements ApiHandler { return countTokens(content, { useWorker: true }) } + + /** + * Disposes of any resources held by the provider. + * Attempts common disposal methods on the client if it exists. + */ + public dispose(): void { + if (this.client) { + // Try common disposal methods that SDKs might have + if (typeof (this.client as any).close === "function") { + ;(this.client as any).close() + } else if (typeof (this.client as any).destroy === "function") { + ;(this.client as any).destroy() + } else if (typeof (this.client as any).dispose === "function") { + ;(this.client as any).dispose() + } + // Clear the reference + this.client = undefined + } + } } diff --git a/src/core/task/Task.ts b/src/core/task/Task.ts index 5683c2d9b2..515490f90d 100644 --- a/src/core/task/Task.ts +++ b/src/core/task/Task.ts @@ -1001,6 +1001,7 @@ export class Task extends EventEmitter { this.browserSession.closeBrowser() this.rooIgnoreController?.dispose() this.fileContextTracker.dispose() + this.api?.dispose?.() // Added this line // If we're not streaming then `abortStream` (which reverts the diff // view changes) won't be called, so we need to revert the changes here. @@ -1012,6 +1013,25 @@ export class Task extends EventEmitter { await this.saveClineMessages() } + // Added new dispose method as per leak report suggestion + public dispose(): void { + console.log(`[subtasks] disposing task ${this.taskId}.${this.instanceId}`) + this.abortTask(true) // Call abortTask to ensure all resources are released + + // Explicitly call dispose on the api handler again, in case abortTask didn't catch it + // or if dispose is called directly without abortTask. + this.api?.dispose?.() + + // Clear any other task-specific resources if they weren't handled by abortTask + if (this.pauseInterval) { + clearInterval(this.pauseInterval) + this.pauseInterval = undefined + } + // Ensure other disposables are handled if not already by abortTask + // this.rooIgnoreController?.dispose(); // Already called in abortTask + // this.fileContextTracker.dispose(); // Already called in abortTask + } + // Used when a sub-task is launched and the parent task is waiting for it to // finish. // TBD: The 1s should be added to the settings, also should add a timeout to From 5cea8441964c864eaf7ab9e53e900f9ccd5ed367 Mon Sep 17 00:00:00 2001 From: kiwina Date: Mon, 2 Jun 2025 14:47:29 +0800 Subject: [PATCH 2/4] fix: auto patch for api_provider_clients --- src/api/providers/base-provider.ts | 22 ++++++++++++---------- 1 file changed, 12 insertions(+), 10 deletions(-) diff --git a/src/api/providers/base-provider.ts b/src/api/providers/base-provider.ts index abbc9923e1..6816477719 100644 --- a/src/api/providers/base-provider.ts +++ b/src/api/providers/base-provider.ts @@ -10,7 +10,7 @@ import { countTokens } from "../../utils/countTokens" * Base class for API providers that implements common functionality. */ export abstract class BaseProvider implements ApiHandler { - protected client: any // Added protected client field + // constructor remains empty, no new properties added here abstract createMessage( systemPrompt: string, @@ -40,17 +40,19 @@ export abstract class BaseProvider implements ApiHandler { * Attempts common disposal methods on the client if it exists. */ public dispose(): void { - if (this.client) { + // Use reflection to find any property named 'client' on the instance + const clientProperty = (this as any).client + if (clientProperty) { // Try common disposal methods that SDKs might have - if (typeof (this.client as any).close === "function") { - ;(this.client as any).close() - } else if (typeof (this.client as any).destroy === "function") { - ;(this.client as any).destroy() - } else if (typeof (this.client as any).dispose === "function") { - ;(this.client as any).dispose() + if (typeof clientProperty.close === "function") { + clientProperty.close() + } else if (typeof clientProperty.destroy === "function") { + clientProperty.destroy() + } else if (typeof clientProperty.dispose === "function") { + clientProperty.dispose() } - // Clear the reference - this.client = undefined + // Clear the reference on the instance + ;(this as any).client = undefined } } } From 8cb55444ee619fe5549e3649c6a4026a5c0daa42 Mon Sep 17 00:00:00 2001 From: kiwina Date: Mon, 2 Jun 2025 14:58:14 +0800 Subject: [PATCH 3/4] fix: auto patch for api_provider_clients --- src/api/providers/vscode-lm.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/api/providers/vscode-lm.ts b/src/api/providers/vscode-lm.ts index 6474371bee..847f15f46b 100644 --- a/src/api/providers/vscode-lm.ts +++ b/src/api/providers/vscode-lm.ts @@ -164,7 +164,7 @@ export class VsCodeLmHandler extends BaseProvider implements SingleCompletionHan * converts the messages to VS Code LM format, and streams the response chunks. * Tool calls handling is currently a work in progress. */ - dispose(): void { + override dispose(): void { if (this.disposable) { this.disposable.dispose() } From 899dc78c9bf91015b8567941ff734da783e2bd3f Mon Sep 17 00:00:00 2001 From: kiwina Date: Mon, 2 Jun 2025 15:09:01 +0800 Subject: [PATCH 4/4] fix: auto patch for bedrock_699 --- src/api/providers/bedrock.ts | 10 ++++++++++ 1 file changed, 10 insertions(+) diff --git a/src/api/providers/bedrock.ts b/src/api/providers/bedrock.ts index 0e335755ec..f3c62e8402 100644 --- a/src/api/providers/bedrock.ts +++ b/src/api/providers/bedrock.ts @@ -976,4 +976,14 @@ Suggestions: return `Bedrock completion error: ${errorMessage}` } } + + override dispose(): void { + // Clear custom cache specific to this handler + this.previousCachePointPlacements = {} + logger.debug("AwsBedrockHandler: Cleared previousCachePointPlacements.", { ctx: "bedrock" }) + + // Call base class dispose for any generic cleanup (like the SDK client) + // The base dispose method handles client disposal reflectively. + super.dispose() + } }