feat(hooks): implement STOP_EXECUTION and enhance hook decision handling (#15685)

This commit is contained in:
Sandy Tao
2025-12-31 07:22:53 +08:00
committed by GitHub
parent 3ebe4e6a8f
commit 05049b5abf
10 changed files with 379 additions and 22 deletions
+38
View File
@@ -28,6 +28,7 @@ import {
CoreEvent,
createWorkingStdio,
recordToolCallInteractions,
ToolErrorType,
} from '@google/gemini-cli-core';
import type { Content, Part } from '@google/genai';
@@ -416,6 +417,43 @@ export async function runNonInteractive({
);
}
// Check if any tool requested to stop execution immediately
const stopExecutionTool = completedToolCalls.find(
(tc) => tc.response.errorType === ToolErrorType.STOP_EXECUTION,
);
if (stopExecutionTool && stopExecutionTool.response.error) {
const stopMessage = `Agent execution stopped: ${stopExecutionTool.response.error.message}`;
if (config.getOutputFormat() === OutputFormat.TEXT) {
process.stderr.write(`${stopMessage}\n`);
}
// Emit final result event for streaming JSON
if (streamFormatter) {
const metrics = uiTelemetryService.getMetrics();
const durationMs = Date.now() - startTime;
streamFormatter.emitEvent({
type: JsonStreamEventType.RESULT,
timestamp: new Date().toISOString(),
status: 'success',
stats: streamFormatter.convertToStreamStats(
metrics,
durationMs,
),
});
} else if (config.getOutputFormat() === OutputFormat.JSON) {
const formatter = new JsonFormatter();
const stats = uiTelemetryService.getMetrics();
textOutput.write(
formatter.format(config.getSessionId(), responseText, stats),
);
} else {
textOutput.ensureTrailingNewline(); // Ensure a final newline
}
return;
}
currentMessages = [{ role: 'user', parts: toolResponseParts }];
} else {
// Emit final result event for streaming JSON