Add compression mechanism to subagent (#12506)

This commit is contained in:
Silvio Junior
2025-11-05 16:15:28 -05:00
committed by GitHub
parent c951f9fdcd
commit 1d2f90c7e7
2 changed files with 280 additions and 5 deletions
+35 -1
View File
@@ -18,7 +18,8 @@ import type {
} from '@google/genai';
import { executeToolCall } from '../core/nonInteractiveToolExecutor.js';
import { ToolRegistry } from '../tools/tool-registry.js';
import type { ToolCallRequestInfo } from '../core/turn.js';
import { type ToolCallRequestInfo, CompressionStatus } from '../core/turn.js';
import { ChatCompressionService } from '../services/chatCompressionService.js';
import { getDirectoryContextString } from '../utils/environmentContext.js';
import {
GLOB_TOOL_NAME,
@@ -84,6 +85,8 @@ export class AgentExecutor<TOutput extends z.ZodTypeAny> {
private readonly toolRegistry: ToolRegistry;
private readonly runtimeContext: Config;
private readonly onActivity?: ActivityCallback;
private readonly compressionService: ChatCompressionService;
private hasFailedCompressionAttempt = false;
/**
* Creates and validates a new `AgentExecutor` instance.
@@ -159,6 +162,7 @@ export class AgentExecutor<TOutput extends z.ZodTypeAny> {
this.runtimeContext = runtimeContext;
this.toolRegistry = toolRegistry;
this.onActivity = onActivity;
this.compressionService = new ChatCompressionService();
const randomIdPart = Math.random().toString(36).slice(2, 8);
// parentPromptId will be undefined if this agent is invoked directly
@@ -184,6 +188,8 @@ export class AgentExecutor<TOutput extends z.ZodTypeAny> {
): Promise<AgentTurnResult> {
const promptId = `${this.agentId}#${turnCounter}`;
await this.tryCompressChat(chat, promptId);
const { functionCalls } = await promptIdContext.run(promptId, async () =>
this.callModel(chat, currentMessage, tools, combinedSignal, promptId),
);
@@ -548,6 +554,34 @@ export class AgentExecutor<TOutput extends z.ZodTypeAny> {
}
}
private async tryCompressChat(
chat: GeminiChat,
prompt_id: string,
): Promise<void> {
const model = this.definition.modelConfig.model;
const { newHistory, info } = await this.compressionService.compress(
chat,
prompt_id,
false,
model,
this.runtimeContext,
this.hasFailedCompressionAttempt,
);
if (
info.compressionStatus ===
CompressionStatus.COMPRESSION_FAILED_INFLATED_TOKEN_COUNT
) {
this.hasFailedCompressionAttempt = true;
} else if (info.compressionStatus === CompressionStatus.COMPRESSED) {
if (newHistory) {
chat.setHistory(newHistory);
this.hasFailedCompressionAttempt = false;
}
}
}
/**
* Calls the generative model with the current context and tools.
*