From f126b34effd92ba7412f35e9a60b08cfd5425472 Mon Sep 17 00:00:00 2001 From: Daniel Sauer Date: Sat, 17 Jan 2026 23:46:52 +0100 Subject: [PATCH] fix(acp): Fix memory leak in session map and event streams Add cleanup mechanism for ACP session map and event streams to prevent unbounded growth. Implements proper session lifecycle management. --- packages/opencode/src/acp/agent.ts | 34 ++++++++++++++++++++++++++++ packages/opencode/src/acp/session.ts | 8 +++++++ 2 files changed, 42 insertions(+) diff --git a/packages/opencode/src/acp/agent.ts b/packages/opencode/src/acp/agent.ts index 9512406b3d47..2c5464d11546 100644 --- a/packages/opencode/src/acp/agent.ts +++ b/packages/opencode/src/acp/agent.ts @@ -259,6 +259,12 @@ export namespace ACP { return } + case "session.deleted": { + const sessionId = event.properties.info.id + this.closeSession(sessionId) + return + } + case "message.part.updated": { log.info("message part updated", { event: event.properties }) const props = event.properties @@ -1432,6 +1438,34 @@ export namespace ACP { { throwOnError: true }, ) } + + /** + * Dispose of all session resources including event streams and session map entries. + * This should be called when the agent is being destroyed to prevent memory leaks. + */ + async dispose() { + log.info("disposing agent", { sessionCount: this.sessionManager["sessions"].size }) + + // Abort global event stream + this.eventAbort.abort() + + // Clear all sessions from the manager + this.sessionManager.clear() + } + + /** + * Close a specific session and clean up its resources. + * This should be called when a session is explicitly closed/ended. + */ + closeSession(sessionId: string) { + log.info("closing session", { sessionId }) + + // Remove from session manager + this.sessionManager.delete(sessionId) + + // Clean up permission queue if present + this.permissionQueues.delete(sessionId) + } } function toToolKind(toolName: string): ToolKind { diff --git a/packages/opencode/src/acp/session.ts b/packages/opencode/src/acp/session.ts index 18aa42313017..5159989223cf 100644 --- a/packages/opencode/src/acp/session.ts +++ b/packages/opencode/src/acp/session.ts @@ -13,6 +13,14 @@ export class ACPSessionManager { this.sdk = sdk } + delete(sessionId: string): boolean { + return this.sessions.delete(sessionId) + } + + clear(): void { + this.sessions.clear() + } + tryGet(sessionId: string): ACPSessionState | undefined { return this.sessions.get(sessionId) }