fix: properly use systemMessage for hooks in UI (#16250)

This commit is contained in:
Jack Wotherspoon
2026-01-09 15:47:14 -05:00
committed by GitHub
parent 9d187e041c
commit c7d17dda49
6 changed files with 88 additions and 19 deletions

View File

@@ -349,7 +349,7 @@ export async function runNonInteractive({
} else if (event.type === GeminiEventType.Error) {
throw event.value.error;
} else if (event.type === GeminiEventType.AgentExecutionStopped) {
const stopMessage = `Agent execution stopped: ${event.value.reason}`;
const stopMessage = `Agent execution stopped: ${event.value.systemMessage?.trim() || event.value.reason}`;
if (config.getOutputFormat() === OutputFormat.TEXT) {
process.stderr.write(`${stopMessage}\n`);
}
@@ -369,7 +369,7 @@ export async function runNonInteractive({
}
return;
} else if (event.type === GeminiEventType.AgentExecutionBlocked) {
const blockMessage = `Agent execution blocked: ${event.value.reason}`;
const blockMessage = `Agent execution blocked: ${event.value.systemMessage?.trim() || event.value.reason}`;
if (config.getOutputFormat() === OutputFormat.TEXT) {
process.stderr.write(`[WARNING] ${blockMessage}\n`);
}

View File

@@ -2800,7 +2800,38 @@ describe('useGeminiStream', () => {
});
describe('Agent Execution Events', () => {
it('should handle AgentExecutionStopped event', async () => {
it('should handle AgentExecutionStopped event with systemMessage', async () => {
mockSendMessageStream.mockReturnValue(
(async function* () {
yield {
type: ServerGeminiEventType.AgentExecutionStopped,
value: {
reason: 'hook-reason',
systemMessage: 'Custom stop message',
},
};
})(),
);
const { result } = renderTestHook();
await act(async () => {
await result.current.submitQuery('test stop');
});
await waitFor(() => {
expect(mockAddItem).toHaveBeenCalledWith(
{
type: MessageType.INFO,
text: 'Agent execution stopped: Custom stop message',
},
expect.any(Number),
);
expect(result.current.streamingState).toBe(StreamingState.Idle);
});
});
it('should handle AgentExecutionStopped event by falling back to reason when systemMessage is missing', async () => {
mockSendMessageStream.mockReturnValue(
(async function* () {
yield {
@@ -2828,7 +2859,37 @@ describe('useGeminiStream', () => {
});
});
it('should handle AgentExecutionBlocked event', async () => {
it('should handle AgentExecutionBlocked event with systemMessage', async () => {
mockSendMessageStream.mockReturnValue(
(async function* () {
yield {
type: ServerGeminiEventType.AgentExecutionBlocked,
value: {
reason: 'hook-reason',
systemMessage: 'Custom block message',
},
};
})(),
);
const { result } = renderTestHook();
await act(async () => {
await result.current.submitQuery('test block');
});
await waitFor(() => {
expect(mockAddItem).toHaveBeenCalledWith(
{
type: MessageType.WARNING,
text: 'Agent execution blocked: Custom block message',
},
expect.any(Number),
);
});
});
it('should handle AgentExecutionBlocked event by falling back to reason when systemMessage is missing', async () => {
mockSendMessageStream.mockReturnValue(
(async function* () {
yield {

View File

@@ -794,7 +794,7 @@ export const useGeminiStream = (
);
const handleAgentExecutionStoppedEvent = useCallback(
(reason: string, userMessageTimestamp: number) => {
(reason: string, userMessageTimestamp: number, systemMessage?: string) => {
if (pendingHistoryItemRef.current) {
addItem(pendingHistoryItemRef.current, userMessageTimestamp);
setPendingHistoryItem(null);
@@ -802,7 +802,7 @@ export const useGeminiStream = (
addItem(
{
type: MessageType.INFO,
text: `Agent execution stopped: ${reason}`,
text: `Agent execution stopped: ${systemMessage?.trim() || reason}`,
},
userMessageTimestamp,
);
@@ -812,7 +812,7 @@ export const useGeminiStream = (
);
const handleAgentExecutionBlockedEvent = useCallback(
(reason: string, userMessageTimestamp: number) => {
(reason: string, userMessageTimestamp: number, systemMessage?: string) => {
if (pendingHistoryItemRef.current) {
addItem(pendingHistoryItemRef.current, userMessageTimestamp);
setPendingHistoryItem(null);
@@ -820,7 +820,7 @@ export const useGeminiStream = (
addItem(
{
type: MessageType.WARNING,
text: `Agent execution blocked: ${reason}`,
text: `Agent execution blocked: ${systemMessage?.trim() || reason}`,
},
userMessageTimestamp,
);
@@ -861,12 +861,14 @@ export const useGeminiStream = (
handleAgentExecutionStoppedEvent(
event.value.reason,
userMessageTimestamp,
event.value.systemMessage,
);
break;
case ServerGeminiEventType.AgentExecutionBlocked:
handleAgentExecutionBlockedEvent(
event.value.reason,
userMessageTimestamp,
event.value.systemMessage,
);
break;
case ServerGeminiEventType.ChatCompressed: