@machina.ai/cell-cli 1.64.0-rc2 → 1.66.0-rc1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/index.js +14 -9
- package/dist/index.js.map +1 -1
- package/dist/package.json +4 -4
- package/dist/src/acp/acpSession.js +9 -13
- package/dist/src/acp/acpSession.js.map +1 -1
- package/dist/src/acp/acpSession.test.js +88 -0
- package/dist/src/acp/acpSession.test.js.map +1 -1
- package/dist/src/commands/mcp/add.js +14 -6
- package/dist/src/commands/mcp/add.js.map +1 -1
- package/dist/src/commands/mcp/add.test.js +61 -0
- package/dist/src/commands/mcp/add.test.js.map +1 -1
- package/dist/src/commands/mcp/remove.js +14 -1
- package/dist/src/commands/mcp/remove.js.map +1 -1
- package/dist/src/commands/mcp/remove.test.js +63 -0
- package/dist/src/commands/mcp/remove.test.js.map +1 -1
- package/dist/src/config/config.js +12 -0
- package/dist/src/config/config.js.map +1 -1
- package/dist/src/config/config.test.js +17 -0
- package/dist/src/config/config.test.js.map +1 -1
- package/dist/src/config/envDefaults.d.ts +20 -0
- package/dist/src/config/envDefaults.js +29 -0
- package/dist/src/config/envDefaults.js.map +1 -0
- package/dist/src/config/envDefaults.test.d.ts +6 -0
- package/dist/src/config/envDefaults.test.js +23 -0
- package/dist/src/config/envDefaults.test.js.map +1 -0
- package/dist/src/config/extension-manager.js +13 -4
- package/dist/src/config/extension-manager.js.map +1 -1
- package/dist/src/config/extension.test.js +117 -0
- package/dist/src/config/extension.test.js.map +1 -1
- package/dist/src/config/extensions/github.test.js +34 -0
- package/dist/src/config/extensions/github.test.js.map +1 -1
- package/dist/src/config/extensions/github_fetch.js +110 -18
- package/dist/src/config/extensions/github_fetch.js.map +1 -1
- package/dist/src/config/extensions/github_fetch.test.js +251 -36
- package/dist/src/config/extensions/github_fetch.test.js.map +1 -1
- package/dist/src/config/settings.d.ts +1 -0
- package/dist/src/config/settings.js +148 -58
- package/dist/src/config/settings.js.map +1 -1
- package/dist/src/config/settings.test.js +300 -0
- package/dist/src/config/settings.test.js.map +1 -1
- package/dist/src/config/settingsSchema.d.ts +1 -1
- package/dist/src/config/settingsSchema.js +6 -1
- package/dist/src/config/settingsSchema.js.map +1 -1
- package/dist/src/gemini.test.js +69 -0
- package/dist/src/gemini.test.js.map +1 -1
- package/dist/src/generated/git-commit.d.ts +2 -2
- package/dist/src/generated/git-commit.js +2 -2
- package/dist/src/interactiveCli.js +8 -3
- package/dist/src/interactiveCli.js.map +1 -1
- package/dist/src/services/CommandService.js +1 -1
- package/dist/src/services/CommandService.js.map +1 -1
- package/dist/src/services/CommandService.test.js +18 -1
- package/dist/src/services/CommandService.test.js.map +1 -1
- package/dist/src/services/SlashCommandConflictHandler.d.ts +1 -0
- package/dist/src/services/SlashCommandConflictHandler.js +18 -2
- package/dist/src/services/SlashCommandConflictHandler.js.map +1 -1
- package/dist/src/services/SlashCommandConflictHandler.test.js +85 -8
- package/dist/src/services/SlashCommandConflictHandler.test.js.map +1 -1
- package/dist/src/ui/AppContainer.js +254 -12
- package/dist/src/ui/AppContainer.js.map +1 -1
- package/dist/src/ui/AppContainer.test.js +362 -6
- package/dist/src/ui/AppContainer.test.js.map +1 -1
- package/dist/src/ui/auth/AuthDialog.js +21 -5
- package/dist/src/ui/auth/AuthDialog.js.map +1 -1
- package/dist/src/ui/auth/AuthDialog.test.js +83 -0
- package/dist/src/ui/auth/AuthDialog.test.js.map +1 -1
- package/dist/src/ui/auth/useAuth.js +7 -1
- package/dist/src/ui/auth/useAuth.js.map +1 -1
- package/dist/src/ui/auth/useAuth.test.js +9 -0
- package/dist/src/ui/auth/useAuth.test.js.map +1 -1
- package/dist/src/ui/commands/marketplaceCommand.js +92 -4
- package/dist/src/ui/commands/marketplaceCommand.js.map +1 -1
- package/dist/src/ui/commands/marketplaceCommand.test.js +98 -1
- package/dist/src/ui/commands/marketplaceCommand.test.js.map +1 -1
- package/dist/src/ui/components/AsciiArt.d.ts +6 -6
- package/dist/src/ui/components/AsciiArt.js +6 -6
- package/dist/src/ui/components/CliSpinner.d.ts +3 -2
- package/dist/src/ui/components/CliSpinner.js +27 -3
- package/dist/src/ui/components/CliSpinner.js.map +1 -1
- package/dist/src/ui/components/CliSpinner.test.js +42 -3
- package/dist/src/ui/components/CliSpinner.test.js.map +1 -1
- package/dist/src/ui/components/Composer.js +3 -3
- package/dist/src/ui/components/Composer.js.map +1 -1
- package/dist/src/ui/components/Composer.test.js +39 -1
- package/dist/src/ui/components/Composer.test.js.map +1 -1
- package/dist/src/ui/components/DetailedMessagesDisplay.js +5 -1
- package/dist/src/ui/components/DetailedMessagesDisplay.js.map +1 -1
- package/dist/src/ui/components/DetailedMessagesDisplay.test.js +19 -1
- package/dist/src/ui/components/DetailedMessagesDisplay.test.js.map +1 -1
- package/dist/src/ui/components/Footer.js +1 -1
- package/dist/src/ui/components/Footer.js.map +1 -1
- package/dist/src/ui/components/GeminiRespondingSpinner.d.ts +1 -1
- package/dist/src/ui/components/GeminiRespondingSpinner.js +9 -2
- package/dist/src/ui/components/GeminiRespondingSpinner.js.map +1 -1
- package/dist/src/ui/components/GeminiSpinner.d.ts +1 -1
- package/dist/src/ui/components/GeminiSpinner.js +18 -7
- package/dist/src/ui/components/GeminiSpinner.js.map +1 -1
- package/dist/src/ui/components/HistoryItemDisplay.js +5 -2
- package/dist/src/ui/components/HistoryItemDisplay.js.map +1 -1
- package/dist/src/ui/components/HistoryItemDisplay.test.js +21 -0
- package/dist/src/ui/components/HistoryItemDisplay.test.js.map +1 -1
- package/dist/src/ui/components/LoadingIndicator.d.ts +1 -1
- package/dist/src/ui/components/LoadingIndicator.js +4 -2
- package/dist/src/ui/components/LoadingIndicator.js.map +1 -1
- package/dist/src/ui/components/MainContent.js +47 -9
- package/dist/src/ui/components/MainContent.js.map +1 -1
- package/dist/src/ui/components/MainContent.test.js +87 -1
- package/dist/src/ui/components/MainContent.test.js.map +1 -1
- package/dist/src/ui/components/MemoryUsageDisplay.js +8 -4
- package/dist/src/ui/components/MemoryUsageDisplay.js.map +1 -1
- package/dist/src/ui/components/ModelDialog.js +30 -16
- package/dist/src/ui/components/ModelDialog.js.map +1 -1
- package/dist/src/ui/components/ModelDialog.test.js +32 -24
- package/dist/src/ui/components/ModelDialog.test.js.map +1 -1
- package/dist/src/ui/components/StatusRow.d.ts +7 -6
- package/dist/src/ui/components/StatusRow.js +24 -10
- package/dist/src/ui/components/StatusRow.js.map +1 -1
- package/dist/src/ui/components/ValidationDialog.js +13 -6
- package/dist/src/ui/components/ValidationDialog.js.map +1 -1
- package/dist/src/ui/components/ValidationDialog.test.js +40 -0
- package/dist/src/ui/components/ValidationDialog.test.js.map +1 -1
- package/dist/src/ui/components/messages/DenseToolMessage.js +17 -12
- package/dist/src/ui/components/messages/DenseToolMessage.js.map +1 -1
- package/dist/src/ui/components/messages/DenseToolMessage.test.js +71 -0
- package/dist/src/ui/components/messages/DenseToolMessage.test.js.map +1 -1
- package/dist/src/ui/components/messages/ToolResultDisplay.js +14 -11
- package/dist/src/ui/components/messages/ToolResultDisplay.js.map +1 -1
- package/dist/src/ui/components/messages/ToolResultDisplay.test.js +32 -0
- package/dist/src/ui/components/messages/ToolResultDisplay.test.js.map +1 -1
- package/dist/src/ui/components/shared/MaxSizedBox.js +8 -2
- package/dist/src/ui/components/shared/MaxSizedBox.js.map +1 -1
- package/dist/src/ui/components/shared/MaxSizedBox.test.js +23 -1
- package/dist/src/ui/components/shared/MaxSizedBox.test.js.map +1 -1
- package/dist/src/ui/contexts/ToolActionsContext.js +7 -1
- package/dist/src/ui/contexts/ToolActionsContext.js.map +1 -1
- package/dist/src/ui/contexts/ToolActionsContext.test.js +54 -1
- package/dist/src/ui/contexts/ToolActionsContext.test.js.map +1 -1
- package/dist/src/ui/hooks/atCommandProcessor.d.ts +2 -1
- package/dist/src/ui/hooks/atCommandProcessor.js +15 -15
- package/dist/src/ui/hooks/atCommandProcessor.js.map +1 -1
- package/dist/src/ui/hooks/useAgentStream.d.ts +9 -2
- package/dist/src/ui/hooks/useAgentStream.js +173 -8
- package/dist/src/ui/hooks/useAgentStream.js.map +1 -1
- package/dist/src/ui/hooks/useAgentStream.test.js +104 -1
- package/dist/src/ui/hooks/useAgentStream.test.js.map +1 -1
- package/dist/src/ui/hooks/useGeminiStream.d.ts +1 -1
- package/dist/src/ui/hooks/useGeminiStream.js +174 -59
- package/dist/src/ui/hooks/useGeminiStream.js.map +1 -1
- package/dist/src/ui/hooks/useGeminiStream.test.js +230 -3
- package/dist/src/ui/hooks/useGeminiStream.test.js.map +1 -1
- package/dist/src/ui/hooks/useLoadingIndicator.d.ts +2 -1
- package/dist/src/ui/hooks/useLoadingIndicator.js +3 -3
- package/dist/src/ui/hooks/useLoadingIndicator.js.map +1 -1
- package/dist/src/ui/hooks/useLoadingIndicator.test.js +23 -4
- package/dist/src/ui/hooks/useLoadingIndicator.test.js.map +1 -1
- package/dist/src/ui/hooks/useReverseSearchCompletion.js +10 -6
- package/dist/src/ui/hooks/useReverseSearchCompletion.js.map +1 -1
- package/dist/src/ui/hooks/useReverseSearchCompletion.test.js +49 -0
- package/dist/src/ui/hooks/useReverseSearchCompletion.test.js.map +1 -1
- package/dist/src/ui/key/keyBindings.js +19 -6
- package/dist/src/ui/key/keyBindings.js.map +1 -1
- package/dist/src/ui/key/keyBindings.test.js +106 -0
- package/dist/src/ui/key/keyBindings.test.js.map +1 -1
- package/dist/src/ui/utils/formatters.d.ts +2 -0
- package/dist/src/ui/utils/formatters.js +13 -5
- package/dist/src/ui/utils/formatters.js.map +1 -1
- package/dist/src/ui/utils/formatters.test.js +18 -0
- package/dist/src/ui/utils/formatters.test.js.map +1 -1
- package/dist/src/utils/activityLogger.js +109 -33
- package/dist/src/utils/activityLogger.js.map +1 -1
- package/dist/src/utils/activityLogger.test.js +441 -0
- package/dist/src/utils/activityLogger.test.js.map +1 -1
- package/dist/src/utils/handleAutoUpdate.d.ts +4 -1
- package/dist/src/utils/handleAutoUpdate.js +45 -3
- package/dist/src/utils/handleAutoUpdate.js.map +1 -1
- package/dist/src/utils/handleAutoUpdate.test.js +280 -2
- package/dist/src/utils/handleAutoUpdate.test.js.map +1 -1
- package/dist/src/utils/nodeVersion.d.ts +11 -0
- package/dist/src/utils/nodeVersion.js +42 -0
- package/dist/src/utils/nodeVersion.js.map +1 -0
- package/dist/src/utils/nodeVersion.test.d.ts +6 -0
- package/dist/src/utils/nodeVersion.test.js +35 -0
- package/dist/src/utils/nodeVersion.test.js.map +1 -0
- package/dist/src/utils/processUtils.d.ts +23 -0
- package/dist/src/utils/processUtils.js +72 -0
- package/dist/src/utils/processUtils.js.map +1 -1
- package/dist/src/utils/processUtils.test.js +95 -1
- package/dist/src/utils/processUtils.test.js.map +1 -1
- package/dist/src/utils/relaunch.js +8 -6
- package/dist/src/utils/relaunch.js.map +1 -1
- package/dist/src/utils/relaunch.test.js +107 -1
- package/dist/src/utils/relaunch.test.js.map +1 -1
- package/dist/tsconfig.tsbuildinfo +1 -1
- package/package.json +4 -4
|
@@ -12,7 +12,7 @@ import { useGeminiStream } from './useGeminiStream.js';
|
|
|
12
12
|
import { useKeypress } from './useKeypress.js';
|
|
13
13
|
import * as atCommandProcessor from './atCommandProcessor.js';
|
|
14
14
|
import { useToolScheduler, } from './useToolScheduler.js';
|
|
15
|
-
import { CoreToolCallStatus, ApprovalMode, DEFAULT_GEMINI_FLASH_MODEL, AuthType, GeminiEventType as ServerGeminiEventType, uiTelemetryService, ToolErrorType, ToolConfirmationOutcome, MessageBusType, tokenLimit, debugLogger, coreEvents, CoreEvent, SHELL_TOOL_NAME, MCPDiscoveryState, GeminiCliOperation, getPlanModeExitMessage, UPDATE_TOPIC_TOOL_NAME, TRUE_EMPTY_RESPONSE_MESSAGE, } from '@google/gemini-cli-core';
|
|
15
|
+
import { CoreToolCallStatus, ApprovalMode, DEFAULT_GEMINI_FLASH_MODEL, AuthType, GeminiEventType as ServerGeminiEventType, uiTelemetryService, ToolErrorType, ToolConfirmationOutcome, MessageBusType, tokenLimit, debugLogger, coreEvents, CoreEvent, SHELL_TOOL_NAME, MCPDiscoveryState, GeminiCliOperation, getPlanModeExitMessage, UPDATE_TOPIC_TOOL_NAME, TRUE_EMPTY_RESPONSE_MESSAGE, Kind, } from '@google/gemini-cli-core';
|
|
16
16
|
import { MessageType, StreamingState } from '../types.js';
|
|
17
17
|
import { findLastSafeSplitPoint } from '../utils/markdownUtilities.js';
|
|
18
18
|
import { theme } from '../semantic-colors.js';
|
|
@@ -1732,7 +1732,7 @@ describe('useGeminiStream', () => {
|
|
|
1732
1732
|
expect(result.current.retryStatus).toEqual(retryPayload);
|
|
1733
1733
|
// Cancel to make isResponding false
|
|
1734
1734
|
await act(async () => {
|
|
1735
|
-
result.current.cancelOngoingRequest();
|
|
1735
|
+
await result.current.cancelOngoingRequest();
|
|
1736
1736
|
});
|
|
1737
1737
|
expect(result.current.retryStatus).toBeNull();
|
|
1738
1738
|
});
|
|
@@ -1767,7 +1767,7 @@ describe('useGeminiStream', () => {
|
|
|
1767
1767
|
});
|
|
1768
1768
|
expect(result.current.retryStatus).toEqual(retryPayload);
|
|
1769
1769
|
await act(async () => {
|
|
1770
|
-
result.current.cancelOngoingRequest();
|
|
1770
|
+
await result.current.cancelOngoingRequest();
|
|
1771
1771
|
});
|
|
1772
1772
|
await waitFor(() => {
|
|
1773
1773
|
expect(result.current.retryStatus).toBeNull();
|
|
@@ -3223,6 +3223,133 @@ describe('useGeminiStream', () => {
|
|
|
3223
3223
|
});
|
|
3224
3224
|
});
|
|
3225
3225
|
});
|
|
3226
|
+
describe('Grouped Tool Calls', () => {
|
|
3227
|
+
const createToolCall = (callId, { status = CoreToolCallStatus.Success, kind = Kind.Agent, groupId, } = {}) => ({
|
|
3228
|
+
request: {
|
|
3229
|
+
callId,
|
|
3230
|
+
name: `tool-${callId}`,
|
|
3231
|
+
args: {},
|
|
3232
|
+
isClientInitiated: false,
|
|
3233
|
+
prompt_id: 'prompt-id-1',
|
|
3234
|
+
groupId,
|
|
3235
|
+
},
|
|
3236
|
+
status,
|
|
3237
|
+
responseSubmittedToGemini: false,
|
|
3238
|
+
response: {
|
|
3239
|
+
callId,
|
|
3240
|
+
responseParts: [],
|
|
3241
|
+
resultDisplay: `result of ${callId}`,
|
|
3242
|
+
error: undefined,
|
|
3243
|
+
errorType: undefined,
|
|
3244
|
+
},
|
|
3245
|
+
tool: {
|
|
3246
|
+
name: `tool-${callId}`,
|
|
3247
|
+
displayName: `tool-${callId}`,
|
|
3248
|
+
description: `description of ${callId}`,
|
|
3249
|
+
kind,
|
|
3250
|
+
build: vi.fn(),
|
|
3251
|
+
},
|
|
3252
|
+
invocation: {
|
|
3253
|
+
getDescription: () => `Mock description of ${callId}`,
|
|
3254
|
+
},
|
|
3255
|
+
});
|
|
3256
|
+
const setToolCalls = (toolCalls) => {
|
|
3257
|
+
mockUseToolScheduler.mockReturnValue([
|
|
3258
|
+
toolCalls,
|
|
3259
|
+
mockScheduleToolCalls,
|
|
3260
|
+
mockMarkToolsAsSubmitted,
|
|
3261
|
+
vi.fn(),
|
|
3262
|
+
mockCancelAllToolCalls,
|
|
3263
|
+
0,
|
|
3264
|
+
]);
|
|
3265
|
+
};
|
|
3266
|
+
const renderWithToolCalls = async (toolCalls) => {
|
|
3267
|
+
setToolCalls(toolCalls);
|
|
3268
|
+
return renderHookWithProviders(() => useGeminiStream(mockConfig.getGeminiClient(), [], mockAddItem, mockConfig, mockLoadedSettings, mockOnDebugMessage, mockHandleSlashCommand, false, () => 'vscode', () => { }, () => Promise.resolve(), false, () => { }, () => { }, () => { }, 80, 24));
|
|
3269
|
+
};
|
|
3270
|
+
// The call IDs of every tool group pushed to history. `useStateAndRef` is
|
|
3271
|
+
// mocked in this file, so the effect that pushes finished tools starts from
|
|
3272
|
+
// scratch on every render. The assertions below therefore check which
|
|
3273
|
+
// groups were pushed rather than how many times `addItem` was called.
|
|
3274
|
+
const getPushedGroups = () => mockAddItem.mock.calls
|
|
3275
|
+
.map(([item]) => item)
|
|
3276
|
+
.filter((item) => item.type === 'tool_group')
|
|
3277
|
+
.map((item) => item.tools.map((tool) => tool.callId));
|
|
3278
|
+
it('should hold back a group until every call in it has finished', async () => {
|
|
3279
|
+
const { rerender } = await renderWithToolCalls([
|
|
3280
|
+
createToolCall('agent-1', { groupId: 'agent-1' }),
|
|
3281
|
+
createToolCall('agent-2', {
|
|
3282
|
+
status: CoreToolCallStatus.Executing,
|
|
3283
|
+
groupId: 'agent-1',
|
|
3284
|
+
}),
|
|
3285
|
+
]);
|
|
3286
|
+
expect(getPushedGroups()).toEqual([]);
|
|
3287
|
+
setToolCalls([
|
|
3288
|
+
createToolCall('agent-1', { groupId: 'agent-1' }),
|
|
3289
|
+
createToolCall('agent-2', { groupId: 'agent-1' }),
|
|
3290
|
+
]);
|
|
3291
|
+
rerender();
|
|
3292
|
+
expect(getPushedGroups()).toContainEqual(['agent-1', 'agent-2']);
|
|
3293
|
+
});
|
|
3294
|
+
it('should treat failed and cancelled calls as finished', async () => {
|
|
3295
|
+
await renderWithToolCalls([
|
|
3296
|
+
createToolCall('agent-1', { groupId: 'agent-1' }),
|
|
3297
|
+
createToolCall('agent-2', {
|
|
3298
|
+
status: CoreToolCallStatus.Error,
|
|
3299
|
+
groupId: 'agent-1',
|
|
3300
|
+
}),
|
|
3301
|
+
createToolCall('agent-3', {
|
|
3302
|
+
status: CoreToolCallStatus.Cancelled,
|
|
3303
|
+
groupId: 'agent-1',
|
|
3304
|
+
}),
|
|
3305
|
+
]);
|
|
3306
|
+
expect(getPushedGroups()).toContainEqual([
|
|
3307
|
+
'agent-1',
|
|
3308
|
+
'agent-2',
|
|
3309
|
+
'agent-3',
|
|
3310
|
+
]);
|
|
3311
|
+
});
|
|
3312
|
+
it('should group by group ID rather than by tool kind', async () => {
|
|
3313
|
+
const { rerender } = await renderWithToolCalls([
|
|
3314
|
+
createToolCall('read-1', { kind: Kind.Read, groupId: 'read-1' }),
|
|
3315
|
+
createToolCall('read-2', {
|
|
3316
|
+
kind: Kind.Read,
|
|
3317
|
+
status: CoreToolCallStatus.Executing,
|
|
3318
|
+
groupId: 'read-1',
|
|
3319
|
+
}),
|
|
3320
|
+
]);
|
|
3321
|
+
expect(getPushedGroups()).toEqual([]);
|
|
3322
|
+
setToolCalls([
|
|
3323
|
+
createToolCall('read-1', { kind: Kind.Read, groupId: 'read-1' }),
|
|
3324
|
+
createToolCall('read-2', { kind: Kind.Read, groupId: 'read-1' }),
|
|
3325
|
+
]);
|
|
3326
|
+
rerender();
|
|
3327
|
+
expect(getPushedGroups()).toContainEqual(['read-1', 'read-2']);
|
|
3328
|
+
});
|
|
3329
|
+
it('should push calls without a group ID individually, whatever their kind', async () => {
|
|
3330
|
+
await renderWithToolCalls([
|
|
3331
|
+
createToolCall('agent-1'),
|
|
3332
|
+
createToolCall('agent-2'),
|
|
3333
|
+
]);
|
|
3334
|
+
const groups = getPushedGroups();
|
|
3335
|
+
expect(groups).toContainEqual(['agent-1']);
|
|
3336
|
+
expect(groups).toContainEqual(['agent-2']);
|
|
3337
|
+
expect(groups).not.toContainEqual(['agent-1', 'agent-2']);
|
|
3338
|
+
});
|
|
3339
|
+
it('should push finished calls ahead of a group that is still running', async () => {
|
|
3340
|
+
await renderWithToolCalls([
|
|
3341
|
+
createToolCall('read-1', { kind: Kind.Read }),
|
|
3342
|
+
createToolCall('agent-1', { groupId: 'agent-1' }),
|
|
3343
|
+
createToolCall('agent-2', {
|
|
3344
|
+
status: CoreToolCallStatus.Executing,
|
|
3345
|
+
groupId: 'agent-1',
|
|
3346
|
+
}),
|
|
3347
|
+
]);
|
|
3348
|
+
const groups = getPushedGroups();
|
|
3349
|
+
expect(groups).toContainEqual(['read-1']);
|
|
3350
|
+
expect(groups.flat()).not.toContain('agent-1');
|
|
3351
|
+
});
|
|
3352
|
+
});
|
|
3226
3353
|
describe('Stream Splitting', () => {
|
|
3227
3354
|
it('should not add empty history item when splitting message results in empty or whitespace-only beforeText', async () => {
|
|
3228
3355
|
// Mock split point to always be 0, causing beforeText to be empty
|
|
@@ -3291,5 +3418,105 @@ describe('useGeminiStream', () => {
|
|
|
3291
3418
|
});
|
|
3292
3419
|
expect(spanMetadata.input).toBe('telemetry test query');
|
|
3293
3420
|
});
|
|
3421
|
+
describe('cancelOngoingRequest session log harmonization & timeout bound', () => {
|
|
3422
|
+
it('immediately synthesizes and records filler functionResponse via recordCompletedToolCalls when cancelling active tools', async () => {
|
|
3423
|
+
const executingToolCall = {
|
|
3424
|
+
request: {
|
|
3425
|
+
callId: 'call-abc',
|
|
3426
|
+
name: 'run_shell_command',
|
|
3427
|
+
args: { command: 'sleep 30' },
|
|
3428
|
+
isClientInitiated: false,
|
|
3429
|
+
prompt_id: 'prompt-1',
|
|
3430
|
+
},
|
|
3431
|
+
status: CoreToolCallStatus.Executing,
|
|
3432
|
+
tool: {
|
|
3433
|
+
name: 'run_shell_command',
|
|
3434
|
+
displayName: 'Shell',
|
|
3435
|
+
},
|
|
3436
|
+
invocation: {
|
|
3437
|
+
getDescription: () => 'sleep 30',
|
|
3438
|
+
},
|
|
3439
|
+
};
|
|
3440
|
+
const { result, client } = await renderTestHook([executingToolCall]);
|
|
3441
|
+
const mockRecordCompletedToolCalls = client.getChat().recordCompletedToolCalls;
|
|
3442
|
+
await act(async () => {
|
|
3443
|
+
await result.current.cancelOngoingRequest();
|
|
3444
|
+
});
|
|
3445
|
+
expect(mockCancelAllToolCalls).toHaveBeenCalledTimes(1);
|
|
3446
|
+
expect(mockRecordCompletedToolCalls).toHaveBeenCalledTimes(1);
|
|
3447
|
+
expect(mockRecordCompletedToolCalls).toHaveBeenCalledWith(expect.any(String), [
|
|
3448
|
+
expect.objectContaining({
|
|
3449
|
+
status: CoreToolCallStatus.Cancelled,
|
|
3450
|
+
request: executingToolCall.request,
|
|
3451
|
+
response: expect.objectContaining({
|
|
3452
|
+
callId: 'call-abc',
|
|
3453
|
+
responseParts: [
|
|
3454
|
+
{
|
|
3455
|
+
functionResponse: {
|
|
3456
|
+
id: 'call-abc',
|
|
3457
|
+
name: 'run_shell_command',
|
|
3458
|
+
response: {
|
|
3459
|
+
error: '[Operation Cancelled] Reason: User cancelled operation',
|
|
3460
|
+
},
|
|
3461
|
+
},
|
|
3462
|
+
},
|
|
3463
|
+
],
|
|
3464
|
+
}),
|
|
3465
|
+
}),
|
|
3466
|
+
]);
|
|
3467
|
+
});
|
|
3468
|
+
it('bounds waiting on an unresponsive tool schedule promise at 1000ms', async () => {
|
|
3469
|
+
vi.useFakeTimers();
|
|
3470
|
+
try {
|
|
3471
|
+
mockScheduleToolCalls.mockImplementation(() => new Promise(() => { }));
|
|
3472
|
+
mockSendMessageStream.mockReturnValue((async function* () {
|
|
3473
|
+
yield {
|
|
3474
|
+
type: ServerGeminiEventType.ToolCallRequest,
|
|
3475
|
+
value: {
|
|
3476
|
+
callId: 'call-hang',
|
|
3477
|
+
name: 'hanging_tool',
|
|
3478
|
+
args: {},
|
|
3479
|
+
isClientInitiated: false,
|
|
3480
|
+
prompt_id: 'prompt-hang',
|
|
3481
|
+
},
|
|
3482
|
+
};
|
|
3483
|
+
})());
|
|
3484
|
+
const { result, client } = await renderTestHook();
|
|
3485
|
+
const mockRecordCompletedToolCalls = client.getChat().recordCompletedToolCalls;
|
|
3486
|
+
act(() => {
|
|
3487
|
+
void result.current.submitQuery('run hanging tool');
|
|
3488
|
+
});
|
|
3489
|
+
await act(async () => {
|
|
3490
|
+
await vi.advanceTimersByTimeAsync(10);
|
|
3491
|
+
});
|
|
3492
|
+
expect(mockScheduleToolCalls).toHaveBeenCalledTimes(1);
|
|
3493
|
+
let cancelResolved = false;
|
|
3494
|
+
let cancelPromise;
|
|
3495
|
+
act(() => {
|
|
3496
|
+
cancelPromise = result.current.cancelOngoingRequest().then(() => {
|
|
3497
|
+
cancelResolved = true;
|
|
3498
|
+
});
|
|
3499
|
+
});
|
|
3500
|
+
expect(mockRecordCompletedToolCalls).toHaveBeenCalledWith(expect.any(String), [
|
|
3501
|
+
expect.objectContaining({
|
|
3502
|
+
status: CoreToolCallStatus.Cancelled,
|
|
3503
|
+
request: expect.objectContaining({
|
|
3504
|
+
callId: 'call-hang',
|
|
3505
|
+
name: 'hanging_tool',
|
|
3506
|
+
}),
|
|
3507
|
+
}),
|
|
3508
|
+
]);
|
|
3509
|
+
expect(cancelResolved).toBe(false);
|
|
3510
|
+
await act(async () => {
|
|
3511
|
+
await vi.advanceTimersByTimeAsync(1000);
|
|
3512
|
+
await cancelPromise;
|
|
3513
|
+
});
|
|
3514
|
+
expect(cancelResolved).toBe(true);
|
|
3515
|
+
}
|
|
3516
|
+
finally {
|
|
3517
|
+
vi.useRealTimers();
|
|
3518
|
+
}
|
|
3519
|
+
});
|
|
3520
|
+
});
|
|
3294
3521
|
});
|
|
3295
3522
|
//# sourceMappingURL=useGeminiStream.test.js.map
|