From f94c468118e40021577e5c126222751f51718ebc Mon Sep 17 00:00:00 2001 From: Your Name Date: Wed, 25 Mar 2026 17:55:11 +0000 Subject: [PATCH] testing --- packages/cli/src/config/config.ts | 1 + packages/cli/src/config/settingsSchema.ts | 10 +++++ packages/core/src/config/config.ts | 7 ++++ .../src/services/chatCompressionService.ts | 39 +++++++++++++------ 4 files changed, 45 insertions(+), 12 deletions(-) diff --git a/packages/cli/src/config/config.ts b/packages/cli/src/config/config.ts index d5e4851e97..813c28d391 100755 --- a/packages/cli/src/config/config.ts +++ b/packages/cli/src/config/config.ts @@ -882,6 +882,7 @@ export async function loadCliConfig( ideMode, disableLoopDetection: settings.model?.disableLoopDetection, compressionThreshold: settings.model?.compressionThreshold, + forceCompressionRetries: settings.model?.forceCompressionRetries, folderTrust, interactive, trustedFolder, diff --git a/packages/cli/src/config/settingsSchema.ts b/packages/cli/src/config/settingsSchema.ts index f1711f3b92..5dd1f2241c 100644 --- a/packages/cli/src/config/settingsSchema.ts +++ b/packages/cli/src/config/settingsSchema.ts @@ -970,6 +970,16 @@ const SETTINGS_SCHEMA = { showInDialog: true, unit: '%', }, + forceCompressionRetries: { + type: 'boolean', + label: 'Force Compression Retries', + category: 'Model', + requiresRestart: true, + default: false as boolean, + description: + 'If true, summarization will be retried even if a previous summarization attempt in the session failed. Useful for aggressive compression experiments.', + showInDialog: false, + }, disableLoopDetection: { type: 'boolean', label: 'Disable Loop Detection', diff --git a/packages/core/src/config/config.ts b/packages/core/src/config/config.ts index 5bac6d086c..c2589e0795 100644 --- a/packages/core/src/config/config.ts +++ b/packages/core/src/config/config.ts @@ -598,6 +598,7 @@ export interface ConfigParameters { importFormat?: 'tree' | 'flat'; discoveryMaxDirs?: number; compressionThreshold?: number; + forceCompressionRetries?: boolean; interactive?: boolean; trustedFolder?: boolean; useBackgroundColor?: boolean; @@ -792,6 +793,7 @@ export class Config implements McpContext, AgentLoopContext { private readonly importFormat: 'tree' | 'flat'; private readonly discoveryMaxDirs: number; private readonly compressionThreshold: number | undefined; + private readonly forceCompressionRetries: boolean; /** Public for testing only */ readonly interactive: boolean; private readonly ptyInfo: string; @@ -1086,6 +1088,7 @@ export class Config implements McpContext, AgentLoopContext { this.importFormat = params.importFormat ?? 'tree'; this.discoveryMaxDirs = params.discoveryMaxDirs ?? 200; this.compressionThreshold = params.compressionThreshold; + this.forceCompressionRetries = params.forceCompressionRetries ?? false; this.interactive = params.interactive ?? false; this.ptyInfo = params.ptyInfo ?? 'child_process'; this.trustedFolder = params.trustedFolder; @@ -2749,6 +2752,10 @@ export class Config implements McpContext, AgentLoopContext { return remoteThreshold; } + getForceCompressionRetries(): boolean { + return this.forceCompressionRetries; + } + async getUserCaching(): Promise { await this.ensureExperimentsLoaded(); diff --git a/packages/core/src/services/chatCompressionService.ts b/packages/core/src/services/chatCompressionService.ts index a1f9c12f2c..ce718f359e 100644 --- a/packages/core/src/services/chatCompressionService.ts +++ b/packages/core/src/services/chatCompressionService.ts @@ -266,7 +266,11 @@ export class ChatCompressionService { const threshold = (await config.getCompressionThreshold()) ?? DEFAULT_COMPRESSION_TOKEN_THRESHOLD; - if (originalTokenCount < threshold * tokenLimit(model)) { + const calculatedLimit = threshold * tokenLimit(model); + debugLogger.log( + `Checking compression limit: ${originalTokenCount} / ${calculatedLimit} (Threshold: ${threshold})`, + ); + if (originalTokenCount < calculatedLimit) { return { newHistory: null, info: { @@ -286,14 +290,22 @@ export class ChatCompressionService { ); // If summarization previously failed (and not forced), we only rely on truncation. - // We do NOT attempt to invoke the LLM for summarization again to avoid repeated failures/costs. - if (hasFailedCompressionAttempt && !force) { + // We do NOT attempt to invoke the LLM for summarization again to avoid repeated failures/costs, + // unless the 'forceCompressionRetries' config flag is set. + if ( + hasFailedCompressionAttempt && + !force && + !config.getForceCompressionRetries() + ) { const truncatedTokenCount = estimateTokenCountSync( truncatedHistory.flatMap((c) => c.parts || []), ); // If truncation reduced the size, we consider it a successful "compression" (truncation only). if (truncatedTokenCount < originalTokenCount) { + debugLogger.log( + `Compression previously failed but truncation succeeded. Reduced ${originalTokenCount} to ${truncatedTokenCount} tokens.`, + ); return { newHistory: truncatedHistory, info: { @@ -302,16 +314,19 @@ export class ChatCompressionService { compressionStatus: CompressionStatus.CONTENT_TRUNCATED, }, }; + } else { + debugLogger.log( + 'Compression previously failed and truncation did not reduce size. Bypassing summarization.', + ); + return { + newHistory: null, + info: { + originalTokenCount, + newTokenCount: originalTokenCount, + compressionStatus: CompressionStatus.NOOP, + }, + }; } - - return { - newHistory: null, - info: { - originalTokenCount, - newTokenCount: originalTokenCount, - compressionStatus: CompressionStatus.NOOP, - }, - }; } const splitPoint = findCompressSplitPoint(