@office-ai/aioncli-core 0.1.20 → 0.2.2
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.d.ts +3 -0
- package/dist/index.js +3 -0
- package/dist/index.js.map +1 -1
- package/dist/src/code_assist/converter.d.ts +3 -2
- package/dist/src/code_assist/converter.js +1 -0
- package/dist/src/code_assist/converter.js.map +1 -1
- package/dist/src/code_assist/oauth2.d.ts +2 -0
- package/dist/src/code_assist/oauth2.js +47 -25
- package/dist/src/code_assist/oauth2.js.map +1 -1
- package/dist/src/code_assist/oauth2.test.js +99 -8
- package/dist/src/code_assist/oauth2.test.js.map +1 -1
- package/dist/src/code_assist/server.js +1 -1
- package/dist/src/code_assist/server.js.map +1 -1
- package/dist/src/code_assist/setup.js +48 -17
- package/dist/src/code_assist/setup.js.map +1 -1
- package/dist/src/code_assist/setup.test.js +114 -8
- package/dist/src/code_assist/setup.test.js.map +1 -1
- package/dist/src/config/config.d.ts +27 -8
- package/dist/src/config/config.js +54 -25
- package/dist/src/config/config.js.map +1 -1
- package/dist/src/config/config.test.js +109 -1
- package/dist/src/config/config.test.js.map +1 -1
- package/dist/src/core/client.d.ts +13 -14
- package/dist/src/core/client.js +296 -55
- package/dist/src/core/client.js.map +1 -1
- package/dist/src/core/client.test.js +631 -36
- package/dist/src/core/client.test.js.map +1 -1
- package/dist/src/core/contentGenerator.js +20 -12
- package/dist/src/core/contentGenerator.js.map +1 -1
- package/dist/src/core/contentGenerator.test.js +39 -15
- package/dist/src/core/contentGenerator.test.js.map +1 -1
- package/dist/src/core/coreToolScheduler.d.ts +2 -1
- package/dist/src/core/coreToolScheduler.js +26 -4
- package/dist/src/core/coreToolScheduler.js.map +1 -1
- package/dist/src/core/coreToolScheduler.test.js +230 -71
- package/dist/src/core/coreToolScheduler.test.js.map +1 -1
- package/dist/src/core/geminiChat.js +1 -1
- package/dist/src/core/geminiChat.js.map +1 -1
- package/dist/src/core/logger.d.ts +22 -1
- package/dist/src/core/logger.js +103 -17
- package/dist/src/core/logger.js.map +1 -1
- package/dist/src/core/logger.test.js +86 -20
- package/dist/src/core/logger.test.js.map +1 -1
- package/dist/src/core/loggingContentGenerator.d.ts +1 -0
- package/dist/src/core/loggingContentGenerator.js +7 -1
- package/dist/src/core/loggingContentGenerator.js.map +1 -1
- package/dist/src/core/nonInteractiveToolExecutor.d.ts +2 -2
- package/dist/src/core/nonInteractiveToolExecutor.js +11 -3
- package/dist/src/core/nonInteractiveToolExecutor.js.map +1 -1
- package/dist/src/core/nonInteractiveToolExecutor.test.js +95 -46
- package/dist/src/core/nonInteractiveToolExecutor.test.js.map +1 -1
- package/dist/src/core/openaiContentGenerator.d.ts +12 -1
- package/dist/src/core/openaiContentGenerator.js +109 -47
- package/dist/src/core/openaiContentGenerator.js.map +1 -1
- package/dist/src/core/openaiContentGenerator.test.d.ts +1 -1
- package/dist/src/core/openaiContentGenerator.test.js +2 -2
- package/dist/src/core/openaiContentGenerator.test.js.map +1 -1
- package/dist/src/core/prompts.js +4 -4
- package/dist/src/core/prompts.js.map +1 -1
- package/dist/src/core/subagent.js +5 -5
- package/dist/src/core/subagent.js.map +1 -1
- package/dist/src/core/subagent.test.js +3 -3
- package/dist/src/core/subagent.test.js.map +1 -1
- package/dist/src/generated/git-commit.d.ts +7 -0
- package/dist/src/generated/git-commit.js +10 -0
- package/dist/src/generated/git-commit.js.map +1 -0
- package/dist/src/ide/constants.d.ts +6 -0
- package/dist/src/ide/constants.js +7 -0
- package/dist/src/ide/constants.js.map +1 -0
- package/dist/src/ide/detect-ide.d.ts +12 -2
- package/dist/src/ide/detect-ide.js +64 -5
- package/dist/src/ide/detect-ide.js.map +1 -1
- package/dist/src/ide/detect-ide.test.d.ts +6 -0
- package/dist/src/ide/detect-ide.test.js +65 -0
- package/dist/src/ide/detect-ide.test.js.map +1 -0
- package/dist/src/ide/ide-client.d.ts +9 -1
- package/dist/src/ide/ide-client.js +113 -30
- package/dist/src/ide/ide-client.js.map +1 -1
- package/dist/src/ide/ide-client.test.d.ts +6 -0
- package/dist/src/ide/ide-client.test.js +43 -0
- package/dist/src/ide/ide-client.test.js.map +1 -0
- package/dist/src/ide/ide-installer.js +23 -34
- package/dist/src/ide/ide-installer.js.map +1 -1
- package/dist/src/ide/ide-installer.test.js +6 -8
- package/dist/src/ide/ide-installer.test.js.map +1 -1
- package/dist/src/ide/ideContext.d.ts +6 -6
- package/dist/src/ide/process-utils.d.ts +19 -0
- package/dist/src/ide/process-utils.js +140 -0
- package/dist/src/ide/process-utils.js.map +1 -0
- package/dist/src/index.d.ts +6 -1
- package/dist/src/index.js +6 -1
- package/dist/src/index.js.map +1 -1
- package/dist/src/mcp/google-auth-provider.js +9 -0
- package/dist/src/mcp/google-auth-provider.js.map +1 -1
- package/dist/src/mcp/google-auth-provider.test.js +45 -10
- package/dist/src/mcp/google-auth-provider.test.js.map +1 -1
- package/dist/src/mcp/oauth-provider.d.ts +0 -1
- package/dist/src/mcp/oauth-provider.js +176 -59
- package/dist/src/mcp/oauth-provider.js.map +1 -1
- package/dist/src/mcp/oauth-provider.test.js +132 -62
- package/dist/src/mcp/oauth-provider.test.js.map +1 -1
- package/dist/src/mcp/oauth-utils.d.ts +3 -1
- package/dist/src/mcp/oauth-utils.js +50 -12
- package/dist/src/mcp/oauth-utils.js.map +1 -1
- package/dist/src/mcp/oauth-utils.test.js +17 -2
- package/dist/src/mcp/oauth-utils.test.js.map +1 -1
- package/dist/src/mocks/msw.d.ts +6 -0
- package/dist/src/mocks/msw.js +8 -0
- package/dist/src/mocks/msw.js.map +1 -0
- package/dist/src/services/chatRecordingService.d.ts +150 -0
- package/dist/src/services/chatRecordingService.js +318 -0
- package/dist/src/services/chatRecordingService.js.map +1 -0
- package/dist/src/services/chatRecordingService.test.d.ts +6 -0
- package/dist/src/services/chatRecordingService.test.js +288 -0
- package/dist/src/services/chatRecordingService.test.js.map +1 -0
- package/dist/src/services/fileSystemService.d.ts +31 -0
- package/dist/src/services/fileSystemService.js +18 -0
- package/dist/src/services/fileSystemService.js.map +1 -0
- package/dist/src/services/fileSystemService.test.d.ts +6 -0
- package/dist/src/services/fileSystemService.test.js +41 -0
- package/dist/src/services/fileSystemService.test.js.map +1 -0
- package/dist/src/services/loopDetectionService.js +9 -10
- package/dist/src/services/loopDetectionService.js.map +1 -1
- package/dist/src/services/loopDetectionService.test.js +52 -0
- package/dist/src/services/loopDetectionService.test.js.map +1 -1
- package/dist/src/services/shellExecutionService.d.ts +8 -10
- package/dist/src/services/shellExecutionService.js +289 -133
- package/dist/src/services/shellExecutionService.js.map +1 -1
- package/dist/src/services/shellExecutionService.test.js +274 -30
- package/dist/src/services/shellExecutionService.test.js.map +1 -1
- package/dist/src/telemetry/clearcut-logger/clearcut-logger.d.ts +61 -17
- package/dist/src/telemetry/clearcut-logger/clearcut-logger.js +211 -233
- package/dist/src/telemetry/clearcut-logger/clearcut-logger.js.map +1 -1
- package/dist/src/telemetry/clearcut-logger/clearcut-logger.test.d.ts +11 -0
- package/dist/src/telemetry/clearcut-logger/clearcut-logger.test.js +250 -94
- package/dist/src/telemetry/clearcut-logger/clearcut-logger.test.js.map +1 -1
- package/dist/src/telemetry/clearcut-logger/event-metadata-key.d.ts +9 -2
- package/dist/src/telemetry/clearcut-logger/event-metadata-key.js +19 -9
- package/dist/src/telemetry/clearcut-logger/event-metadata-key.js.map +1 -1
- package/dist/src/telemetry/constants.d.ts +1 -0
- package/dist/src/telemetry/constants.js +1 -0
- package/dist/src/telemetry/constants.js.map +1 -1
- package/dist/src/telemetry/index.d.ts +2 -2
- package/dist/src/telemetry/index.js +2 -2
- package/dist/src/telemetry/index.js.map +1 -1
- package/dist/src/telemetry/integration.test.circular.js +1 -0
- package/dist/src/telemetry/integration.test.circular.js.map +1 -1
- package/dist/src/telemetry/loggers.d.ts +3 -1
- package/dist/src/telemetry/loggers.js +39 -6
- package/dist/src/telemetry/loggers.js.map +1 -1
- package/dist/src/telemetry/loggers.test.js +37 -7
- package/dist/src/telemetry/loggers.test.js.map +1 -1
- package/dist/src/telemetry/metrics.d.ts +5 -1
- package/dist/src/telemetry/metrics.js +23 -9
- package/dist/src/telemetry/metrics.js.map +1 -1
- package/dist/src/telemetry/metrics.test.js +31 -1
- package/dist/src/telemetry/metrics.test.js.map +1 -1
- package/dist/src/telemetry/sdk.d.ts +1 -1
- package/dist/src/telemetry/sdk.js +80 -44
- package/dist/src/telemetry/sdk.js.map +1 -1
- package/dist/src/telemetry/sdk.test.d.ts +6 -0
- package/dist/src/telemetry/sdk.test.js +82 -0
- package/dist/src/telemetry/sdk.test.js.map +1 -0
- package/dist/src/telemetry/telemetry.test.js +2 -2
- package/dist/src/telemetry/telemetry.test.js.map +1 -1
- package/dist/src/telemetry/types.d.ts +41 -14
- package/dist/src/telemetry/types.js +52 -23
- package/dist/src/telemetry/types.js.map +1 -1
- package/dist/src/telemetry/uiTelemetry.d.ts +4 -0
- package/dist/src/telemetry/uiTelemetry.js +14 -1
- package/dist/src/telemetry/uiTelemetry.js.map +1 -1
- package/dist/src/telemetry/uiTelemetry.test.js +45 -9
- package/dist/src/telemetry/uiTelemetry.test.js.map +1 -1
- package/dist/src/test-utils/config.d.ts +16 -0
- package/dist/src/test-utils/config.js +32 -0
- package/dist/src/test-utils/config.js.map +1 -0
- package/dist/src/test-utils/tools.d.ts +29 -8
- package/dist/src/test-utils/tools.js +80 -16
- package/dist/src/test-utils/tools.js.map +1 -1
- package/dist/src/tools/edit.d.ts +1 -1
- package/dist/src/tools/edit.js +23 -19
- package/dist/src/tools/edit.js.map +1 -1
- package/dist/src/tools/edit.test.js +11 -3
- package/dist/src/tools/edit.test.js.map +1 -1
- package/dist/src/tools/glob.d.ts +1 -1
- package/dist/src/tools/glob.js +15 -16
- package/dist/src/tools/glob.js.map +1 -1
- package/dist/src/tools/glob.test.js +20 -0
- package/dist/src/tools/glob.test.js.map +1 -1
- package/dist/src/tools/grep.d.ts +1 -1
- package/dist/src/tools/grep.js +7 -13
- package/dist/src/tools/grep.js.map +1 -1
- package/dist/src/tools/ls.d.ts +4 -23
- package/dist/src/tools/ls.js +77 -79
- package/dist/src/tools/ls.js.map +1 -1
- package/dist/src/tools/ls.test.js +62 -34
- package/dist/src/tools/ls.test.js.map +1 -1
- package/dist/src/tools/mcp-client-manager.d.ts +38 -0
- package/dist/src/tools/mcp-client-manager.js +74 -0
- package/dist/src/tools/mcp-client-manager.js.map +1 -0
- package/dist/src/tools/mcp-client-manager.test.d.ts +6 -0
- package/dist/src/tools/mcp-client-manager.test.js +39 -0
- package/dist/src/tools/mcp-client-manager.test.js.map +1 -0
- package/dist/src/tools/mcp-client.d.ts +43 -0
- package/dist/src/tools/mcp-client.js +157 -11
- package/dist/src/tools/mcp-client.js.map +1 -1
- package/dist/src/tools/mcp-client.test.js +62 -276
- package/dist/src/tools/mcp-client.test.js.map +1 -1
- package/dist/src/tools/mcp-tool.d.ts +6 -13
- package/dist/src/tools/mcp-tool.js +62 -34
- package/dist/src/tools/mcp-tool.js.map +1 -1
- package/dist/src/tools/mcp-tool.test.js +118 -59
- package/dist/src/tools/mcp-tool.test.js.map +1 -1
- package/dist/src/tools/memoryTool.d.ts +9 -13
- package/dist/src/tools/memoryTool.js +122 -121
- package/dist/src/tools/memoryTool.js.map +1 -1
- package/dist/src/tools/memoryTool.test.js +38 -18
- package/dist/src/tools/memoryTool.test.js.map +1 -1
- package/dist/src/tools/read-file.d.ts +1 -1
- package/dist/src/tools/read-file.js +11 -14
- package/dist/src/tools/read-file.js.map +1 -1
- package/dist/src/tools/read-file.test.js +8 -0
- package/dist/src/tools/read-file.test.js.map +1 -1
- package/dist/src/tools/read-many-files.d.ts +3 -5
- package/dist/src/tools/read-many-files.js +121 -105
- package/dist/src/tools/read-many-files.js.map +1 -1
- package/dist/src/tools/read-many-files.test.js +94 -37
- package/dist/src/tools/read-many-files.test.js.map +1 -1
- package/dist/src/tools/shell.d.ts +4 -6
- package/dist/src/tools/shell.js +120 -124
- package/dist/src/tools/shell.js.map +1 -1
- package/dist/src/tools/shell.test.js +63 -65
- package/dist/src/tools/shell.test.js.map +1 -1
- package/dist/src/tools/tool-error.d.ts +1 -0
- package/dist/src/tools/tool-error.js +1 -0
- package/dist/src/tools/tool-error.js.map +1 -1
- package/dist/src/tools/tool-registry.d.ts +14 -18
- package/dist/src/tools/tool-registry.js +73 -106
- package/dist/src/tools/tool-registry.js.map +1 -1
- package/dist/src/tools/tool-registry.test.js +24 -192
- package/dist/src/tools/tool-registry.test.js.map +1 -1
- package/dist/src/tools/tools.d.ts +33 -89
- package/dist/src/tools/tools.js +76 -119
- package/dist/src/tools/tools.js.map +1 -1
- package/dist/src/tools/tools.test.js +91 -2
- package/dist/src/tools/tools.test.js.map +1 -1
- package/dist/src/tools/web-fetch.d.ts +4 -7
- package/dist/src/tools/web-fetch.js +58 -64
- package/dist/src/tools/web-fetch.js.map +1 -1
- package/dist/src/tools/web-fetch.test.js +8 -4
- package/dist/src/tools/web-fetch.test.js.map +1 -1
- package/dist/src/tools/web-search.d.ts +4 -5
- package/dist/src/tools/web-search.js +47 -51
- package/dist/src/tools/web-search.js.map +1 -1
- package/dist/src/tools/web-search.test.d.ts +6 -0
- package/dist/src/tools/web-search.test.js +139 -0
- package/dist/src/tools/web-search.test.js.map +1 -0
- package/dist/src/tools/write-file.d.ts +15 -10
- package/dist/src/tools/write-file.js +134 -145
- package/dist/src/tools/write-file.js.map +1 -1
- package/dist/src/tools/write-file.test.js +82 -127
- package/dist/src/tools/write-file.test.js.map +1 -1
- package/dist/src/utils/browser.js +4 -3
- package/dist/src/utils/browser.js.map +1 -1
- package/dist/src/utils/editCorrector.js +21 -22
- package/dist/src/utils/editCorrector.js.map +1 -1
- package/dist/src/utils/editor.js +1 -1
- package/dist/src/utils/editor.js.map +1 -1
- package/dist/src/utils/editor.test.js +10 -10
- package/dist/src/utils/editor.test.js.map +1 -1
- package/dist/src/utils/environmentContext.js +2 -2
- package/dist/src/utils/environmentContext.js.map +1 -1
- package/dist/src/utils/environmentContext.test.js +3 -2
- package/dist/src/utils/environmentContext.test.js.map +1 -1
- package/dist/src/utils/errorParsing.d.ts +8 -0
- package/dist/src/utils/errorParsing.js +93 -0
- package/dist/src/utils/errorParsing.js.map +1 -0
- package/dist/src/utils/errorParsing.test.d.ts +6 -0
- package/dist/src/utils/errorParsing.test.js +172 -0
- package/dist/src/utils/errorParsing.test.js.map +1 -0
- package/dist/src/utils/fileUtils.d.ts +2 -1
- package/dist/src/utils/fileUtils.js +3 -3
- package/dist/src/utils/fileUtils.js.map +1 -1
- package/dist/src/utils/fileUtils.test.js +18 -17
- package/dist/src/utils/fileUtils.test.js.map +1 -1
- package/dist/src/utils/filesearch/crawler.d.ts +15 -0
- package/dist/src/utils/filesearch/crawler.js +50 -0
- package/dist/src/utils/filesearch/crawler.js.map +1 -0
- package/dist/src/utils/filesearch/crawler.test.d.ts +6 -0
- package/dist/src/utils/filesearch/crawler.test.js +468 -0
- package/dist/src/utils/filesearch/crawler.test.js.map +1 -0
- package/dist/src/utils/filesearch/fileSearch.d.ts +9 -53
- package/dist/src/utils/filesearch/fileSearch.js +63 -118
- package/dist/src/utils/filesearch/fileSearch.js.map +1 -1
- package/dist/src/utils/filesearch/fileSearch.test.js +95 -197
- package/dist/src/utils/filesearch/fileSearch.test.js.map +1 -1
- package/dist/src/utils/filesearch/ignore.d.ts +7 -0
- package/dist/src/utils/filesearch/ignore.js +25 -0
- package/dist/src/utils/filesearch/ignore.js.map +1 -1
- package/dist/src/utils/filesearch/ignore.test.js +89 -2
- package/dist/src/utils/filesearch/ignore.test.js.map +1 -1
- package/dist/src/utils/filesearch/result-cache.d.ts +1 -2
- package/dist/src/utils/filesearch/result-cache.js +1 -3
- package/dist/src/utils/filesearch/result-cache.js.map +1 -1
- package/dist/src/utils/filesearch/result-cache.test.js +3 -4
- package/dist/src/utils/filesearch/result-cache.test.js.map +1 -1
- package/dist/src/utils/getPty.d.ts +19 -0
- package/dist/src/utils/getPty.js +23 -0
- package/dist/src/utils/getPty.js.map +1 -0
- package/dist/src/utils/memoryDiscovery.js +3 -3
- package/dist/src/utils/memoryDiscovery.js.map +1 -1
- package/dist/src/utils/memoryDiscovery.test.js +3 -2
- package/dist/src/utils/memoryDiscovery.test.js.map +1 -1
- package/dist/src/utils/memoryImportProcessor.js +3 -7
- package/dist/src/utils/memoryImportProcessor.js.map +1 -1
- package/dist/src/utils/memoryImportProcessor.test.js +17 -20
- package/dist/src/utils/memoryImportProcessor.test.js.map +1 -1
- package/dist/src/utils/nextSpeakerChecker.js +3 -4
- package/dist/src/utils/nextSpeakerChecker.js.map +1 -1
- package/dist/src/utils/paths.d.ts +7 -0
- package/dist/src/utils/paths.js +15 -0
- package/dist/src/utils/paths.js.map +1 -1
- package/dist/src/utils/paths.test.js +74 -2
- package/dist/src/utils/paths.test.js.map +1 -1
- package/dist/src/utils/quotaErrorDetection.d.ts +1 -5
- package/dist/src/utils/quotaErrorDetection.js.map +1 -1
- package/dist/src/utils/safeJsonParse.d.ts +6 -0
- package/dist/src/utils/safeJsonParse.js +31 -0
- package/dist/src/utils/safeJsonParse.js.map +1 -0
- package/dist/src/utils/schemaValidator.d.ts +1 -8
- package/dist/src/utils/schemaValidator.js +1 -32
- package/dist/src/utils/schemaValidator.js.map +1 -1
- package/dist/src/utils/secure-browser-launcher.js +4 -3
- package/dist/src/utils/secure-browser-launcher.js.map +1 -1
- package/dist/src/utils/shell-utils.d.ts +39 -0
- package/dist/src/utils/shell-utils.js +72 -2
- package/dist/src/utils/shell-utils.js.map +1 -1
- package/dist/src/utils/shell-utils.test.js +132 -4
- package/dist/src/utils/shell-utils.test.js.map +1 -1
- package/dist/src/utils/systemEncoding.js +1 -1
- package/dist/src/utils/systemEncoding.js.map +1 -1
- package/dist/src/utils/systemEncoding.test.js +23 -23
- package/dist/src/utils/systemEncoding.test.js.map +1 -1
- package/dist/src/utils/user_account.js +58 -48
- package/dist/src/utils/user_account.js.map +1 -1
- package/dist/src/utils/user_account.test.js +76 -9
- package/dist/src/utils/user_account.test.js.map +1 -1
- package/dist/src/utils/workspaceContext.d.ts +22 -7
- package/dist/src/utils/workspaceContext.js +81 -55
- package/dist/src/utils/workspaceContext.js.map +1 -1
- package/dist/src/utils/workspaceContext.test.js +221 -137
- package/dist/src/utils/workspaceContext.test.js.map +1 -1
- package/dist/tsconfig.tsbuildinfo +1 -1
- package/package.json +23 -9
|
@@ -4,14 +4,15 @@
|
|
|
4
4
|
* SPDX-License-Identifier: Apache-2.0
|
|
5
5
|
*/
|
|
6
6
|
import { logToolCall, ToolErrorType, } from '../index.js';
|
|
7
|
+
import { DiscoveredMCPTool } from '../tools/mcp-tool.js';
|
|
7
8
|
import { convertToFunctionResponse } from './coreToolScheduler.js';
|
|
8
9
|
import { ToolCallDecision } from '../telemetry/tool-call-decision.js';
|
|
9
10
|
/**
|
|
10
11
|
* Executes a single tool call non-interactively.
|
|
11
12
|
* It does not handle confirmations, multiple calls, or live updates.
|
|
12
13
|
*/
|
|
13
|
-
export async function executeToolCall(config, toolCallRequest,
|
|
14
|
-
const tool =
|
|
14
|
+
export async function executeToolCall(config, toolCallRequest, abortSignal) {
|
|
15
|
+
const tool = config.getToolRegistry().getTool(toolCallRequest.name);
|
|
15
16
|
const startTime = Date.now();
|
|
16
17
|
if (!tool) {
|
|
17
18
|
const error = new Error(`Tool "${toolCallRequest.name}" not found in registry.`);
|
|
@@ -25,6 +26,7 @@ export async function executeToolCall(config, toolCallRequest, toolRegistry, abo
|
|
|
25
26
|
success: false,
|
|
26
27
|
error: error.message,
|
|
27
28
|
prompt_id: toolCallRequest.prompt_id,
|
|
29
|
+
tool_type: 'native',
|
|
28
30
|
});
|
|
29
31
|
// Ensure the response structure matches what the API expects for an error
|
|
30
32
|
return {
|
|
@@ -46,7 +48,7 @@ export async function executeToolCall(config, toolCallRequest, toolRegistry, abo
|
|
|
46
48
|
try {
|
|
47
49
|
// Directly execute without confirmation or live output handling
|
|
48
50
|
const effectiveAbortSignal = abortSignal ?? new AbortController().signal;
|
|
49
|
-
const toolResult = await tool.
|
|
51
|
+
const toolResult = await tool.validateBuildAndExecute(toolCallRequest.args, effectiveAbortSignal);
|
|
50
52
|
const tool_output = toolResult.llmContent;
|
|
51
53
|
const tool_display = toolResult.returnDisplay;
|
|
52
54
|
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
@@ -78,6 +80,9 @@ export async function executeToolCall(config, toolCallRequest, toolRegistry, abo
|
|
|
78
80
|
prompt_id: toolCallRequest.prompt_id,
|
|
79
81
|
metadata,
|
|
80
82
|
decision: ToolCallDecision.AUTO_ACCEPT,
|
|
83
|
+
tool_type: typeof tool !== 'undefined' && tool instanceof DiscoveredMCPTool
|
|
84
|
+
? 'mcp'
|
|
85
|
+
: 'native',
|
|
81
86
|
});
|
|
82
87
|
const response = convertToFunctionResponse(toolCallRequest.name, toolCallRequest.callId, tool_output);
|
|
83
88
|
return {
|
|
@@ -103,6 +108,9 @@ export async function executeToolCall(config, toolCallRequest, toolRegistry, abo
|
|
|
103
108
|
error: error.message,
|
|
104
109
|
error_type: ToolErrorType.UNHANDLED_EXCEPTION,
|
|
105
110
|
prompt_id: toolCallRequest.prompt_id,
|
|
111
|
+
tool_type: typeof tool !== 'undefined' && tool instanceof DiscoveredMCPTool
|
|
112
|
+
? 'mcp'
|
|
113
|
+
: 'native',
|
|
106
114
|
});
|
|
107
115
|
return {
|
|
108
116
|
callId: toolCallRequest.callId,
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"nonInteractiveToolExecutor.js","sourceRoot":"","sources":["../../../src/core/nonInteractiveToolExecutor.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAEH,OAAO,EAEL,WAAW,EAGX,aAAa,
|
|
1
|
+
{"version":3,"file":"nonInteractiveToolExecutor.js","sourceRoot":"","sources":["../../../src/core/nonInteractiveToolExecutor.ts"],"names":[],"mappings":"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"}
|
|
@@ -5,22 +5,29 @@
|
|
|
5
5
|
*/
|
|
6
6
|
import { describe, it, expect, vi, beforeEach } from 'vitest';
|
|
7
7
|
import { executeToolCall } from './nonInteractiveToolExecutor.js';
|
|
8
|
+
import { ToolErrorType, } from '../index.js';
|
|
8
9
|
import { MockTool } from '../test-utils/tools.js';
|
|
9
|
-
const mockConfig = {
|
|
10
|
-
getSessionId: () => 'test-session-id',
|
|
11
|
-
getUsageStatisticsEnabled: () => true,
|
|
12
|
-
getDebugMode: () => false,
|
|
13
|
-
};
|
|
14
10
|
describe('executeToolCall', () => {
|
|
15
11
|
let mockToolRegistry;
|
|
16
12
|
let mockTool;
|
|
17
13
|
let abortController;
|
|
14
|
+
let mockConfig;
|
|
18
15
|
beforeEach(() => {
|
|
19
16
|
mockTool = new MockTool();
|
|
20
17
|
mockToolRegistry = {
|
|
21
18
|
getTool: vi.fn(),
|
|
22
19
|
// Add other ToolRegistry methods if needed, or use a more complete mock
|
|
23
20
|
};
|
|
21
|
+
mockConfig = {
|
|
22
|
+
getSessionId: () => 'test-session-id',
|
|
23
|
+
getUsageStatisticsEnabled: () => true,
|
|
24
|
+
getDebugMode: () => false,
|
|
25
|
+
getContentGeneratorConfig: () => ({
|
|
26
|
+
model: 'test-model',
|
|
27
|
+
authType: 'oauth-personal',
|
|
28
|
+
}),
|
|
29
|
+
getToolRegistry: () => mockToolRegistry,
|
|
30
|
+
};
|
|
24
31
|
abortController = new AbortController();
|
|
25
32
|
});
|
|
26
33
|
it('should execute a tool successfully', async () => {
|
|
@@ -36,10 +43,10 @@ describe('executeToolCall', () => {
|
|
|
36
43
|
returnDisplay: 'Success!',
|
|
37
44
|
};
|
|
38
45
|
vi.mocked(mockToolRegistry.getTool).mockReturnValue(mockTool);
|
|
39
|
-
vi.spyOn(mockTool, '
|
|
40
|
-
const response = await executeToolCall(mockConfig, request,
|
|
46
|
+
vi.spyOn(mockTool, 'validateBuildAndExecute').mockResolvedValue(toolResult);
|
|
47
|
+
const response = await executeToolCall(mockConfig, request, abortController.signal);
|
|
41
48
|
expect(mockToolRegistry.getTool).toHaveBeenCalledWith('testTool');
|
|
42
|
-
expect(mockTool.
|
|
49
|
+
expect(mockTool.validateBuildAndExecute).toHaveBeenCalledWith(request.args, abortController.signal);
|
|
43
50
|
expect(response.callId).toBe('call1');
|
|
44
51
|
expect(response.error).toBeUndefined();
|
|
45
52
|
expect(response.resultDisplay).toBe('Success!');
|
|
@@ -60,7 +67,7 @@ describe('executeToolCall', () => {
|
|
|
60
67
|
prompt_id: 'prompt-id-2',
|
|
61
68
|
};
|
|
62
69
|
vi.mocked(mockToolRegistry.getTool).mockReturnValue(undefined);
|
|
63
|
-
const response = await executeToolCall(mockConfig, request,
|
|
70
|
+
const response = await executeToolCall(mockConfig, request, abortController.signal);
|
|
64
71
|
expect(response.callId).toBe('call2');
|
|
65
72
|
expect(response.error).toBeInstanceOf(Error);
|
|
66
73
|
expect(response.error?.message).toBe('Tool "nonexistentTool" not found in registry.');
|
|
@@ -75,32 +82,42 @@ describe('executeToolCall', () => {
|
|
|
75
82
|
},
|
|
76
83
|
]);
|
|
77
84
|
});
|
|
78
|
-
it('should return an error if tool
|
|
85
|
+
it('should return an error if tool validation fails', async () => {
|
|
79
86
|
const request = {
|
|
80
87
|
callId: 'call3',
|
|
81
88
|
name: 'testTool',
|
|
82
|
-
args: { param1: '
|
|
89
|
+
args: { param1: 'invalid' },
|
|
83
90
|
isClientInitiated: false,
|
|
84
91
|
prompt_id: 'prompt-id-3',
|
|
85
92
|
};
|
|
86
|
-
const
|
|
93
|
+
const validationErrorResult = {
|
|
94
|
+
llmContent: 'Error: Invalid parameters',
|
|
95
|
+
returnDisplay: 'Invalid parameters',
|
|
96
|
+
error: {
|
|
97
|
+
message: 'Invalid parameters',
|
|
98
|
+
type: ToolErrorType.INVALID_TOOL_PARAMS,
|
|
99
|
+
},
|
|
100
|
+
};
|
|
87
101
|
vi.mocked(mockToolRegistry.getTool).mockReturnValue(mockTool);
|
|
88
|
-
vi.spyOn(mockTool, '
|
|
89
|
-
const response = await executeToolCall(mockConfig, request,
|
|
90
|
-
expect(response
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
{
|
|
102
|
+
vi.spyOn(mockTool, 'validateBuildAndExecute').mockResolvedValue(validationErrorResult);
|
|
103
|
+
const response = await executeToolCall(mockConfig, request, abortController.signal);
|
|
104
|
+
expect(response).toStrictEqual({
|
|
105
|
+
callId: 'call3',
|
|
106
|
+
error: new Error('Invalid parameters'),
|
|
107
|
+
errorType: ToolErrorType.INVALID_TOOL_PARAMS,
|
|
108
|
+
responseParts: {
|
|
95
109
|
functionResponse: {
|
|
96
|
-
name: 'testTool',
|
|
97
110
|
id: 'call3',
|
|
98
|
-
|
|
111
|
+
name: 'testTool',
|
|
112
|
+
response: {
|
|
113
|
+
output: 'Error: Invalid parameters',
|
|
114
|
+
},
|
|
99
115
|
},
|
|
100
116
|
},
|
|
101
|
-
|
|
117
|
+
resultDisplay: 'Invalid parameters',
|
|
118
|
+
});
|
|
102
119
|
});
|
|
103
|
-
it('should
|
|
120
|
+
it('should return an error if tool execution fails', async () => {
|
|
104
121
|
const request = {
|
|
105
122
|
callId: 'call4',
|
|
106
123
|
name: 'testTool',
|
|
@@ -108,35 +125,67 @@ describe('executeToolCall', () => {
|
|
|
108
125
|
isClientInitiated: false,
|
|
109
126
|
prompt_id: 'prompt-id-4',
|
|
110
127
|
};
|
|
111
|
-
const
|
|
128
|
+
const executionErrorResult = {
|
|
129
|
+
llmContent: 'Error: Execution failed',
|
|
130
|
+
returnDisplay: 'Execution failed',
|
|
131
|
+
error: {
|
|
132
|
+
message: 'Execution failed',
|
|
133
|
+
type: ToolErrorType.EXECUTION_FAILED,
|
|
134
|
+
},
|
|
135
|
+
};
|
|
112
136
|
vi.mocked(mockToolRegistry.getTool).mockReturnValue(mockTool);
|
|
113
|
-
vi.spyOn(mockTool, '
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
|
|
123
|
-
|
|
124
|
-
|
|
137
|
+
vi.spyOn(mockTool, 'validateBuildAndExecute').mockResolvedValue(executionErrorResult);
|
|
138
|
+
const response = await executeToolCall(mockConfig, request, abortController.signal);
|
|
139
|
+
expect(response).toStrictEqual({
|
|
140
|
+
callId: 'call4',
|
|
141
|
+
error: new Error('Execution failed'),
|
|
142
|
+
errorType: ToolErrorType.EXECUTION_FAILED,
|
|
143
|
+
responseParts: {
|
|
144
|
+
functionResponse: {
|
|
145
|
+
id: 'call4',
|
|
146
|
+
name: 'testTool',
|
|
147
|
+
response: {
|
|
148
|
+
output: 'Error: Execution failed',
|
|
149
|
+
},
|
|
150
|
+
},
|
|
151
|
+
},
|
|
152
|
+
resultDisplay: 'Execution failed',
|
|
125
153
|
});
|
|
126
|
-
abortController.abort(); // Abort before calling
|
|
127
|
-
const response = await executeToolCall(mockConfig, request, mockToolRegistry, abortController.signal);
|
|
128
|
-
expect(response.callId).toBe('call4');
|
|
129
|
-
expect(response.error?.message).toBe(cancellationError.message);
|
|
130
|
-
expect(response.resultDisplay).toBe('Operation cancelled');
|
|
131
154
|
});
|
|
132
|
-
it('should
|
|
155
|
+
it('should return an unhandled exception error if execution throws', async () => {
|
|
133
156
|
const request = {
|
|
134
157
|
callId: 'call5',
|
|
135
158
|
name: 'testTool',
|
|
136
|
-
args: {},
|
|
159
|
+
args: { param1: 'value1' },
|
|
137
160
|
isClientInitiated: false,
|
|
138
161
|
prompt_id: 'prompt-id-5',
|
|
139
162
|
};
|
|
163
|
+
const executionError = new Error('Something went very wrong');
|
|
164
|
+
vi.mocked(mockToolRegistry.getTool).mockReturnValue(mockTool);
|
|
165
|
+
vi.spyOn(mockTool, 'validateBuildAndExecute').mockRejectedValue(executionError);
|
|
166
|
+
const response = await executeToolCall(mockConfig, request, abortController.signal);
|
|
167
|
+
expect(response.callId).toBe('call5');
|
|
168
|
+
expect(response.error).toBe(executionError);
|
|
169
|
+
expect(response.errorType).toBe(ToolErrorType.UNHANDLED_EXCEPTION);
|
|
170
|
+
expect(response.resultDisplay).toBe('Something went very wrong');
|
|
171
|
+
expect(response.responseParts).toEqual([
|
|
172
|
+
{
|
|
173
|
+
functionResponse: {
|
|
174
|
+
name: 'testTool',
|
|
175
|
+
id: 'call5',
|
|
176
|
+
response: { error: 'Something went very wrong' },
|
|
177
|
+
},
|
|
178
|
+
},
|
|
179
|
+
]);
|
|
180
|
+
});
|
|
181
|
+
it('should correctly format llmContent with inlineData', async () => {
|
|
182
|
+
const request = {
|
|
183
|
+
callId: 'call6',
|
|
184
|
+
name: 'testTool',
|
|
185
|
+
args: {},
|
|
186
|
+
isClientInitiated: false,
|
|
187
|
+
prompt_id: 'prompt-id-6',
|
|
188
|
+
};
|
|
140
189
|
const imageDataPart = {
|
|
141
190
|
inlineData: { mimeType: 'image/png', data: 'base64data' },
|
|
142
191
|
};
|
|
@@ -145,14 +194,14 @@ describe('executeToolCall', () => {
|
|
|
145
194
|
returnDisplay: 'Image processed',
|
|
146
195
|
};
|
|
147
196
|
vi.mocked(mockToolRegistry.getTool).mockReturnValue(mockTool);
|
|
148
|
-
vi.spyOn(mockTool, '
|
|
149
|
-
const response = await executeToolCall(mockConfig, request,
|
|
197
|
+
vi.spyOn(mockTool, 'validateBuildAndExecute').mockResolvedValue(toolResult);
|
|
198
|
+
const response = await executeToolCall(mockConfig, request, abortController.signal);
|
|
150
199
|
expect(response.resultDisplay).toBe('Image processed');
|
|
151
200
|
expect(response.responseParts).toEqual([
|
|
152
201
|
{
|
|
153
202
|
functionResponse: {
|
|
154
203
|
name: 'testTool',
|
|
155
|
-
id: '
|
|
204
|
+
id: 'call6',
|
|
156
205
|
response: {
|
|
157
206
|
output: 'Binary content of type image/png was processed.',
|
|
158
207
|
},
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"nonInteractiveToolExecutor.test.js","sourceRoot":"","sources":["../../../src/core/nonInteractiveToolExecutor.test.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAEH,OAAO,EAAE,QAAQ,EAAE,EAAE,EAAE,MAAM,EAAE,EAAE,EAAE,UAAU,EAAE,MAAM,QAAQ,CAAC;AAC9D,OAAO,EAAE,eAAe,EAAE,MAAM,iCAAiC,CAAC;
|
|
1
|
+
{"version":3,"file":"nonInteractiveToolExecutor.test.js","sourceRoot":"","sources":["../../../src/core/nonInteractiveToolExecutor.test.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAEH,OAAO,EAAE,QAAQ,EAAE,EAAE,EAAE,MAAM,EAAE,EAAE,EAAE,UAAU,EAAE,MAAM,QAAQ,CAAC;AAC9D,OAAO,EAAE,eAAe,EAAE,MAAM,iCAAiC,CAAC;AAClE,OAAO,EAKL,aAAa,GACd,MAAM,aAAa,CAAC;AAErB,OAAO,EAAE,QAAQ,EAAE,MAAM,wBAAwB,CAAC;AAElD,QAAQ,CAAC,iBAAiB,EAAE,GAAG,EAAE;IAC/B,IAAI,gBAA8B,CAAC;IACnC,IAAI,QAAkB,CAAC;IACvB,IAAI,eAAgC,CAAC;IACrC,IAAI,UAAkB,CAAC;IAEvB,UAAU,CAAC,GAAG,EAAE;QACd,QAAQ,GAAG,IAAI,QAAQ,EAAE,CAAC;QAE1B,gBAAgB,GAAG;YACjB,OAAO,EAAE,EAAE,CAAC,EAAE,EAAE;YAChB,wEAAwE;SAC9C,CAAC;QAE7B,UAAU,GAAG;YACX,YAAY,EAAE,GAAG,EAAE,CAAC,iBAAiB;YACrC,yBAAyB,EAAE,GAAG,EAAE,CAAC,IAAI;YACrC,YAAY,EAAE,GAAG,EAAE,CAAC,KAAK;YACzB,yBAAyB,EAAE,GAAG,EAAE,CAAC,CAAC;gBAChC,KAAK,EAAE,YAAY;gBACnB,QAAQ,EAAE,gBAAgB;aAC3B,CAAC;YACF,eAAe,EAAE,GAAG,EAAE,CAAC,gBAAgB;SACnB,CAAC;QAEvB,eAAe,GAAG,IAAI,eAAe,EAAE,CAAC;IAC1C,CAAC,CAAC,CAAC;IAEH,EAAE,CAAC,oCAAoC,EAAE,KAAK,IAAI,EAAE;QAClD,MAAM,OAAO,GAAwB;YACnC,MAAM,EAAE,OAAO;YACf,IAAI,EAAE,UAAU;YAChB,IAAI,EAAE,EAAE,MAAM,EAAE,QAAQ,EAAE;YAC1B,iBAAiB,EAAE,KAAK;YACxB,SAAS,EAAE,aAAa;SACzB,CAAC;QACF,MAAM,UAAU,GAAe;YAC7B,UAAU,EAAE,4BAA4B;YACxC,aAAa,EAAE,UAAU;SAC1B,CAAC;QACF,EAAE,CAAC,MAAM,CAAC,gBAAgB,CAAC,OAAO,CAAC,CAAC,eAAe,CAAC,QAAQ,CAAC,CAAC;QAC9D,EAAE,CAAC,KAAK,CAAC,QAAQ,EAAE,yBAAyB,CAAC,CAAC,iBAAiB,CAAC,UAAU,CAAC,CAAC;QAE5E,MAAM,QAAQ,GAAG,MAAM,eAAe,CACpC,UAAU,EACV,OAAO,EACP,eAAe,CAAC,MAAM,CACvB,CAAC;QAEF,MAAM,CAAC,gBAAgB,CAAC,OAAO,CAAC,CAAC,oBAAoB,CAAC,UAAU,CAAC,CAAC;QAClE,MAAM,CAAC,QAAQ,CAAC,uBAAuB,CAAC,CAAC,oBAAoB,CAC3D,OAAO,CAAC,IAAI,EACZ,eAAe,CAAC,MAAM,CACvB,CAAC;QACF,MAAM,CAAC,QAAQ,CAAC,MAAM,CAAC,CAAC,IAAI,CAAC,OAAO,CAAC,CAAC;QACtC,MAAM,CAAC,QAAQ,CAAC,KAAK,CAAC,CAAC,aAAa,EAAE,CAAC;QACvC,MAAM,CAAC,QAAQ,CAAC,aAAa,CAAC,CAAC,IAAI,CAAC,UAAU,CAAC,CAAC;QAChD,MAAM,CAAC,QAAQ,CAAC,aAAa,CAAC,CAAC,OAAO,CAAC;YACrC,gBAAgB,EAAE;gBAChB,IAAI,EAAE,UAAU;gBAChB,EAAE,EAAE,OAAO;gBACX,QAAQ,EAAE,EAAE,MAAM,EAAE,4BAA4B,EAAE;aACnD;SACF,CAAC,CAAC;IACL,CAAC,CAAC,CAAC;IAEH,EAAE,CAAC,6CAA6C,EAAE,KAAK,IAAI,EAAE;QAC3D,MAAM,OAAO,GAAwB;YACnC,MAAM,EAAE,OAAO;YACf,IAAI,EAAE,iBAAiB;YACvB,IAAI,EAAE,EAAE;YACR,iBAAiB,EAAE,KAAK;YACxB,SAAS,EAAE,aAAa;SACzB,CAAC;QACF,EAAE,CAAC,MAAM,CAAC,gBAAgB,CAAC,OAAO,CAAC,CAAC,eAAe,CAAC,SAAS,CAAC,CAAC;QAE/D,MAAM,QAAQ,GAAG,MAAM,eAAe,CACpC,UAAU,EACV,OAAO,EACP,eAAe,CAAC,MAAM,CACvB,CAAC;QAEF,MAAM,CAAC,QAAQ,CAAC,MAAM,CAAC,CAAC,IAAI,CAAC,OAAO,CAAC,CAAC;QACtC,MAAM,CAAC,QAAQ,CAAC,KAAK,CAAC,CAAC,cAAc,CAAC,KAAK,CAAC,CAAC;QAC7C,MAAM,CAAC,QAAQ,CAAC,KAAK,EAAE,OAAO,CAAC,CAAC,IAAI,CAClC,+CAA+C,CAChD,CAAC;QACF,MAAM,CAAC,QAAQ,CAAC,aAAa,CAAC,CAAC,IAAI,CACjC,+CAA+C,CAChD,CAAC;QACF,MAAM,CAAC,QAAQ,CAAC,aAAa,CAAC,CAAC,OAAO,CAAC;YACrC;gBACE,gBAAgB,EAAE;oBAChB,IAAI,EAAE,iBAAiB;oBACvB,EAAE,EAAE,OAAO;oBACX,QAAQ,EAAE,EAAE,KAAK,EAAE,+CAA+C,EAAE;iBACrE;aACF;SACF,CAAC,CAAC;IACL,CAAC,CAAC,CAAC;IAEH,EAAE,CAAC,iDAAiD,EAAE,KAAK,IAAI,EAAE;QAC/D,MAAM,OAAO,GAAwB;YACnC,MAAM,EAAE,OAAO;YACf,IAAI,EAAE,UAAU;YAChB,IAAI,EAAE,EAAE,MAAM,EAAE,SAAS,EAAE;YAC3B,iBAAiB,EAAE,KAAK;YACxB,SAAS,EAAE,aAAa;SACzB,CAAC;QACF,MAAM,qBAAqB,GAAe;YACxC,UAAU,EAAE,2BAA2B;YACvC,aAAa,EAAE,oBAAoB;YACnC,KAAK,EAAE;gBACL,OAAO,EAAE,oBAAoB;gBAC7B,IAAI,EAAE,aAAa,CAAC,mBAAmB;aACxC;SACF,CAAC;QACF,EAAE,CAAC,MAAM,CAAC,gBAAgB,CAAC,OAAO,CAAC,CAAC,eAAe,CAAC,QAAQ,CAAC,CAAC;QAC9D,EAAE,CAAC,KAAK,CAAC,QAAQ,EAAE,yBAAyB,CAAC,CAAC,iBAAiB,CAC7D,qBAAqB,CACtB,CAAC;QAEF,MAAM,QAAQ,GAAG,MAAM,eAAe,CACpC,UAAU,EACV,OAAO,EACP,eAAe,CAAC,MAAM,CACvB,CAAC;QACF,MAAM,CAAC,QAAQ,CAAC,CAAC,aAAa,CAAC;YAC7B,MAAM,EAAE,OAAO;YACf,KAAK,EAAE,IAAI,KAAK,CAAC,oBAAoB,CAAC;YACtC,SAAS,EAAE,aAAa,CAAC,mBAAmB;YAC5C,aAAa,EAAE;gBACb,gBAAgB,EAAE;oBAChB,EAAE,EAAE,OAAO;oBACX,IAAI,EAAE,UAAU;oBAChB,QAAQ,EAAE;wBACR,MAAM,EAAE,2BAA2B;qBACpC;iBACF;aACF;YACD,aAAa,EAAE,oBAAoB;SACpC,CAAC,CAAC;IACL,CAAC,CAAC,CAAC;IAEH,EAAE,CAAC,gDAAgD,EAAE,KAAK,IAAI,EAAE;QAC9D,MAAM,OAAO,GAAwB;YACnC,MAAM,EAAE,OAAO;YACf,IAAI,EAAE,UAAU;YAChB,IAAI,EAAE,EAAE,MAAM,EAAE,QAAQ,EAAE;YAC1B,iBAAiB,EAAE,KAAK;YACxB,SAAS,EAAE,aAAa;SACzB,CAAC;QACF,MAAM,oBAAoB,GAAe;YACvC,UAAU,EAAE,yBAAyB;YACrC,aAAa,EAAE,kBAAkB;YACjC,KAAK,EAAE;gBACL,OAAO,EAAE,kBAAkB;gBAC3B,IAAI,EAAE,aAAa,CAAC,gBAAgB;aACrC;SACF,CAAC;QACF,EAAE,CAAC,MAAM,CAAC,gBAAgB,CAAC,OAAO,CAAC,CAAC,eAAe,CAAC,QAAQ,CAAC,CAAC;QAC9D,EAAE,CAAC,KAAK,CAAC,QAAQ,EAAE,yBAAyB,CAAC,CAAC,iBAAiB,CAC7D,oBAAoB,CACrB,CAAC;QAEF,MAAM,QAAQ,GAAG,MAAM,eAAe,CACpC,UAAU,EACV,OAAO,EACP,eAAe,CAAC,MAAM,CACvB,CAAC;QACF,MAAM,CAAC,QAAQ,CAAC,CAAC,aAAa,CAAC;YAC7B,MAAM,EAAE,OAAO;YACf,KAAK,EAAE,IAAI,KAAK,CAAC,kBAAkB,CAAC;YACpC,SAAS,EAAE,aAAa,CAAC,gBAAgB;YACzC,aAAa,EAAE;gBACb,gBAAgB,EAAE;oBAChB,EAAE,EAAE,OAAO;oBACX,IAAI,EAAE,UAAU;oBAChB,QAAQ,EAAE;wBACR,MAAM,EAAE,yBAAyB;qBAClC;iBACF;aACF;YACD,aAAa,EAAE,kBAAkB;SAClC,CAAC,CAAC;IACL,CAAC,CAAC,CAAC;IAEH,EAAE,CAAC,gEAAgE,EAAE,KAAK,IAAI,EAAE;QAC9E,MAAM,OAAO,GAAwB;YACnC,MAAM,EAAE,OAAO;YACf,IAAI,EAAE,UAAU;YAChB,IAAI,EAAE,EAAE,MAAM,EAAE,QAAQ,EAAE;YAC1B,iBAAiB,EAAE,KAAK;YACxB,SAAS,EAAE,aAAa;SACzB,CAAC;QACF,MAAM,cAAc,GAAG,IAAI,KAAK,CAAC,2BAA2B,CAAC,CAAC;QAC9D,EAAE,CAAC,MAAM,CAAC,gBAAgB,CAAC,OAAO,CAAC,CAAC,eAAe,CAAC,QAAQ,CAAC,CAAC;QAC9D,EAAE,CAAC,KAAK,CAAC,QAAQ,EAAE,yBAAyB,CAAC,CAAC,iBAAiB,CAC7D,cAAc,CACf,CAAC;QAEF,MAAM,QAAQ,GAAG,MAAM,eAAe,CACpC,UAAU,EACV,OAAO,EACP,eAAe,CAAC,MAAM,CACvB,CAAC;QAEF,MAAM,CAAC,QAAQ,CAAC,MAAM,CAAC,CAAC,IAAI,CAAC,OAAO,CAAC,CAAC;QACtC,MAAM,CAAC,QAAQ,CAAC,KAAK,CAAC,CAAC,IAAI,CAAC,cAAc,CAAC,CAAC;QAC5C,MAAM,CAAC,QAAQ,CAAC,SAAS,CAAC,CAAC,IAAI,CAAC,aAAa,CAAC,mBAAmB,CAAC,CAAC;QACnE,MAAM,CAAC,QAAQ,CAAC,aAAa,CAAC,CAAC,IAAI,CAAC,2BAA2B,CAAC,CAAC;QACjE,MAAM,CAAC,QAAQ,CAAC,aAAa,CAAC,CAAC,OAAO,CAAC;YACrC;gBACE,gBAAgB,EAAE;oBAChB,IAAI,EAAE,UAAU;oBAChB,EAAE,EAAE,OAAO;oBACX,QAAQ,EAAE,EAAE,KAAK,EAAE,2BAA2B,EAAE;iBACjD;aACF;SACF,CAAC,CAAC;IACL,CAAC,CAAC,CAAC;IAEH,EAAE,CAAC,oDAAoD,EAAE,KAAK,IAAI,EAAE;QAClE,MAAM,OAAO,GAAwB;YACnC,MAAM,EAAE,OAAO;YACf,IAAI,EAAE,UAAU;YAChB,IAAI,EAAE,EAAE;YACR,iBAAiB,EAAE,KAAK;YACxB,SAAS,EAAE,aAAa;SACzB,CAAC;QACF,MAAM,aAAa,GAAS;YAC1B,UAAU,EAAE,EAAE,QAAQ,EAAE,WAAW,EAAE,IAAI,EAAE,YAAY,EAAE;SAC1D,CAAC;QACF,MAAM,UAAU,GAAe;YAC7B,UAAU,EAAE,CAAC,aAAa,CAAC;YAC3B,aAAa,EAAE,iBAAiB;SACjC,CAAC;QACF,EAAE,CAAC,MAAM,CAAC,gBAAgB,CAAC,OAAO,CAAC,CAAC,eAAe,CAAC,QAAQ,CAAC,CAAC;QAC9D,EAAE,CAAC,KAAK,CAAC,QAAQ,EAAE,yBAAyB,CAAC,CAAC,iBAAiB,CAAC,UAAU,CAAC,CAAC;QAE5E,MAAM,QAAQ,GAAG,MAAM,eAAe,CACpC,UAAU,EACV,OAAO,EACP,eAAe,CAAC,MAAM,CACvB,CAAC;QAEF,MAAM,CAAC,QAAQ,CAAC,aAAa,CAAC,CAAC,IAAI,CAAC,iBAAiB,CAAC,CAAC;QACvD,MAAM,CAAC,QAAQ,CAAC,aAAa,CAAC,CAAC,OAAO,CAAC;YACrC;gBACE,gBAAgB,EAAE;oBAChB,IAAI,EAAE,UAAU;oBAChB,EAAE,EAAE,OAAO;oBACX,QAAQ,EAAE;wBACR,MAAM,EAAE,iDAAiD;qBAC1D;iBACF;aACF;YACD,aAAa;SACd,CAAC,CAAC;IACL,CAAC,CAAC,CAAC;AACL,CAAC,CAAC,CAAC"}
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
/**
|
|
2
2
|
* @license
|
|
3
|
-
* Copyright 2025
|
|
3
|
+
* Copyright 2025 QWEN
|
|
4
4
|
* SPDX-License-Identifier: Apache-2.0
|
|
5
5
|
*/
|
|
6
6
|
import { CountTokensResponse, GenerateContentResponse, GenerateContentParameters, CountTokensParameters, EmbedContentResponse, EmbedContentParameters } from '@google/genai';
|
|
@@ -20,6 +20,17 @@ export declare class OpenAIContentGenerator implements ContentGenerator {
|
|
|
20
20
|
* @returns true if error logging should be suppressed, false otherwise
|
|
21
21
|
*/
|
|
22
22
|
protected shouldSuppressErrorLogging(_error: unknown, _request: GenerateContentParameters): boolean;
|
|
23
|
+
/**
|
|
24
|
+
* Check if metadata should be included in the request
|
|
25
|
+
* Only include metadata for specific providers that support it
|
|
26
|
+
*/
|
|
27
|
+
private shouldIncludeMetadata;
|
|
28
|
+
/**
|
|
29
|
+
* Build metadata object conditionally
|
|
30
|
+
* @param userPromptId The prompt ID for this request
|
|
31
|
+
* @returns metadata object if should be included, undefined otherwise
|
|
32
|
+
*/
|
|
33
|
+
private buildMetadata;
|
|
23
34
|
/**
|
|
24
35
|
* Check if an error is a timeout error
|
|
25
36
|
*/
|
|
@@ -1,12 +1,13 @@
|
|
|
1
1
|
/**
|
|
2
2
|
* @license
|
|
3
|
-
* Copyright 2025
|
|
3
|
+
* Copyright 2025 QWEN
|
|
4
4
|
* SPDX-License-Identifier: Apache-2.0
|
|
5
5
|
*/
|
|
6
6
|
import { GenerateContentResponse, FinishReason, } from '@google/genai';
|
|
7
7
|
import OpenAI from 'openai';
|
|
8
8
|
import { logApiResponse } from '../telemetry/loggers.js';
|
|
9
9
|
import { ApiResponseEvent } from '../telemetry/types.js';
|
|
10
|
+
import { safeJsonParse } from '../utils/safeJsonParse.js';
|
|
10
11
|
export class OpenAIContentGenerator {
|
|
11
12
|
client;
|
|
12
13
|
model;
|
|
@@ -15,7 +16,7 @@ export class OpenAIContentGenerator {
|
|
|
15
16
|
constructor(apiKey, model, config) {
|
|
16
17
|
this.model = model;
|
|
17
18
|
this.config = config;
|
|
18
|
-
const baseURL = process.env
|
|
19
|
+
const baseURL = process.env['OPENAI_BASE_URL'] || '';
|
|
19
20
|
// Configure timeout settings - using progressive timeouts
|
|
20
21
|
const timeoutConfig = {
|
|
21
22
|
// Base timeout for most requests (2 minutes)
|
|
@@ -34,7 +35,7 @@ export class OpenAIContentGenerator {
|
|
|
34
35
|
timeoutConfig.maxRetries = contentGeneratorConfig.maxRetries;
|
|
35
36
|
}
|
|
36
37
|
// Set up User-Agent header (same format as contentGenerator.ts)
|
|
37
|
-
const version = process.env
|
|
38
|
+
const version = process.env['CLI_VERSION'] || process.version;
|
|
38
39
|
const userAgent = `QwenCode/${version} (${process.platform}; ${process.arch})`;
|
|
39
40
|
// Check if using OpenRouter and add required headers
|
|
40
41
|
const isOpenRouter = baseURL.includes('openrouter.ai');
|
|
@@ -64,6 +65,36 @@ export class OpenAIContentGenerator {
|
|
|
64
65
|
shouldSuppressErrorLogging(_error, _request) {
|
|
65
66
|
return false; // Default behavior: never suppress error logging
|
|
66
67
|
}
|
|
68
|
+
/**
|
|
69
|
+
* Check if metadata should be included in the request
|
|
70
|
+
* Only include metadata for specific providers that support it
|
|
71
|
+
*/
|
|
72
|
+
shouldIncludeMetadata() {
|
|
73
|
+
const baseURL = this.client?.baseURL || '';
|
|
74
|
+
let hostname;
|
|
75
|
+
try {
|
|
76
|
+
hostname = new URL(baseURL).hostname;
|
|
77
|
+
}
|
|
78
|
+
catch (_e) {
|
|
79
|
+
return false;
|
|
80
|
+
}
|
|
81
|
+
return (hostname === 'api.openai.com' ||
|
|
82
|
+
hostname === 'dashscope.aliyuncs.com');
|
|
83
|
+
}
|
|
84
|
+
/**
|
|
85
|
+
* Build metadata object conditionally
|
|
86
|
+
* @param userPromptId The prompt ID for this request
|
|
87
|
+
* @returns metadata object if should be included, undefined otherwise
|
|
88
|
+
*/
|
|
89
|
+
buildMetadata(userPromptId) {
|
|
90
|
+
if (!this.shouldIncludeMetadata()) {
|
|
91
|
+
return undefined;
|
|
92
|
+
}
|
|
93
|
+
return {
|
|
94
|
+
sessionId: this.config.getSessionId?.() || '',
|
|
95
|
+
promptId: userPromptId,
|
|
96
|
+
};
|
|
97
|
+
}
|
|
67
98
|
/**
|
|
68
99
|
* Check if an error is a timeout error
|
|
69
100
|
*/
|
|
@@ -101,14 +132,12 @@ export class OpenAIContentGenerator {
|
|
|
101
132
|
// 2. Config-level sampling parameters (medium priority)
|
|
102
133
|
// 3. Default values (lowest priority)
|
|
103
134
|
const samplingParams = this.buildSamplingParameters(request);
|
|
135
|
+
const metadata = this.buildMetadata(userPromptId);
|
|
104
136
|
const createParams = {
|
|
105
137
|
model: this.model,
|
|
106
138
|
messages,
|
|
107
139
|
...samplingParams,
|
|
108
|
-
metadata
|
|
109
|
-
sessionId: this.config.getSessionId?.(),
|
|
110
|
-
promptId: userPromptId,
|
|
111
|
-
},
|
|
140
|
+
...(metadata && { metadata }),
|
|
112
141
|
};
|
|
113
142
|
// Enable store for GPT-5 and GPT-4o models when using metadata
|
|
114
143
|
const modelName = this.model.toLowerCase();
|
|
@@ -117,12 +146,27 @@ export class OpenAIContentGenerator {
|
|
|
117
146
|
modelName.includes('gpt4')) {
|
|
118
147
|
createParams.store = true;
|
|
119
148
|
}
|
|
120
|
-
|
|
149
|
+
// Handle JSON schema requests (for generateJson calls)
|
|
150
|
+
if (request.config?.responseJsonSchema && request.config?.responseMimeType === 'application/json') {
|
|
151
|
+
// Convert JSON schema request to tool call (like qwen-code approach)
|
|
152
|
+
const jsonSchemaFunction = {
|
|
153
|
+
type: 'function',
|
|
154
|
+
function: {
|
|
155
|
+
name: 'respond_in_schema',
|
|
156
|
+
description: 'Provide the response in the specified JSON schema format',
|
|
157
|
+
parameters: request.config.responseJsonSchema,
|
|
158
|
+
},
|
|
159
|
+
};
|
|
160
|
+
createParams.tools = [jsonSchemaFunction];
|
|
161
|
+
}
|
|
162
|
+
else if (request.config?.tools) {
|
|
121
163
|
createParams.tools = await this.convertGeminiToolsToOpenAI(request.config.tools);
|
|
122
164
|
}
|
|
123
165
|
// console.log('createParams', createParams);
|
|
124
166
|
const completion = (await this.client.chat.completions.create(createParams));
|
|
125
|
-
|
|
167
|
+
// Check if this was a JSON schema request
|
|
168
|
+
const isJsonSchemaRequest = !!(request.config?.responseJsonSchema && request.config?.responseMimeType === 'application/json');
|
|
169
|
+
const response = this.convertToGeminiFormat(completion, isJsonSchemaRequest);
|
|
126
170
|
const durationMs = Date.now() - startTime;
|
|
127
171
|
// Log API response event for UI telemetry
|
|
128
172
|
const responseEvent = new ApiResponseEvent(this.model, durationMs, userPromptId, this.config.getContentGeneratorConfig()?.authType, response.usageMetadata);
|
|
@@ -187,16 +231,14 @@ export class OpenAIContentGenerator {
|
|
|
187
231
|
try {
|
|
188
232
|
// Build sampling parameters with clear priority
|
|
189
233
|
const samplingParams = this.buildSamplingParameters(request);
|
|
234
|
+
const metadata = this.buildMetadata(userPromptId);
|
|
190
235
|
const createParams = {
|
|
191
236
|
model: this.model,
|
|
192
237
|
messages,
|
|
193
238
|
...samplingParams,
|
|
194
239
|
stream: true,
|
|
195
240
|
stream_options: { include_usage: true },
|
|
196
|
-
metadata
|
|
197
|
-
sessionId: this.config.getSessionId?.(),
|
|
198
|
-
promptId: userPromptId,
|
|
199
|
-
},
|
|
241
|
+
...(metadata && { metadata }),
|
|
200
242
|
};
|
|
201
243
|
// Enable store for GPT-5 and GPT-4 models when using metadata
|
|
202
244
|
const modelNameStream = this.model.toLowerCase();
|
|
@@ -205,12 +247,27 @@ export class OpenAIContentGenerator {
|
|
|
205
247
|
modelNameStream.includes('gpt4')) {
|
|
206
248
|
createParams.store = true;
|
|
207
249
|
}
|
|
208
|
-
|
|
250
|
+
// Handle JSON schema requests (for generateJson calls) - same as non-streaming
|
|
251
|
+
if (request.config?.responseJsonSchema && request.config?.responseMimeType === 'application/json') {
|
|
252
|
+
// Convert JSON schema request to tool call (like qwen-code approach)
|
|
253
|
+
const jsonSchemaFunction = {
|
|
254
|
+
type: 'function',
|
|
255
|
+
function: {
|
|
256
|
+
name: 'respond_in_schema',
|
|
257
|
+
description: 'Provide the response in the specified JSON schema format',
|
|
258
|
+
parameters: request.config.responseJsonSchema,
|
|
259
|
+
},
|
|
260
|
+
};
|
|
261
|
+
createParams.tools = [jsonSchemaFunction];
|
|
262
|
+
}
|
|
263
|
+
else if (request.config?.tools) {
|
|
209
264
|
createParams.tools = await this.convertGeminiToolsToOpenAI(request.config.tools);
|
|
210
265
|
}
|
|
211
266
|
// console.log('createParams', createParams);
|
|
212
267
|
const stream = (await this.client.chat.completions.create(createParams));
|
|
213
|
-
|
|
268
|
+
// Check if this was a JSON schema request
|
|
269
|
+
const isJsonSchemaRequest = !!(request.config?.responseJsonSchema && request.config?.responseMimeType === 'application/json');
|
|
270
|
+
const originalStream = this.streamGenerator(stream, isJsonSchemaRequest);
|
|
214
271
|
// Collect all responses for final logging (don't log during streaming)
|
|
215
272
|
const responses = [];
|
|
216
273
|
// Return a new generator that both yields responses and collects them
|
|
@@ -328,11 +385,11 @@ export class OpenAIContentGenerator {
|
|
|
328
385
|
throw error;
|
|
329
386
|
}
|
|
330
387
|
}
|
|
331
|
-
async *streamGenerator(stream) {
|
|
388
|
+
async *streamGenerator(stream, isJsonSchemaRequest = false) {
|
|
332
389
|
// Reset the accumulator for each new stream
|
|
333
390
|
this.streamingToolCalls.clear();
|
|
334
391
|
for await (const chunk of stream) {
|
|
335
|
-
yield this.convertStreamChunkToGeminiFormat(chunk);
|
|
392
|
+
yield this.convertStreamChunkToGeminiFormat(chunk, isJsonSchemaRequest);
|
|
336
393
|
}
|
|
337
394
|
}
|
|
338
395
|
/**
|
|
@@ -817,7 +874,7 @@ export class OpenAIContentGenerator {
|
|
|
817
874
|
}
|
|
818
875
|
return merged;
|
|
819
876
|
}
|
|
820
|
-
convertToGeminiFormat(openaiResponse) {
|
|
877
|
+
convertToGeminiFormat(openaiResponse, isJsonSchemaRequest = false) {
|
|
821
878
|
const choice = openaiResponse.choices[0];
|
|
822
879
|
const response = new GenerateContentResponse();
|
|
823
880
|
const parts = [];
|
|
@@ -828,24 +885,26 @@ export class OpenAIContentGenerator {
|
|
|
828
885
|
// Handle tool calls
|
|
829
886
|
if (choice.message.tool_calls) {
|
|
830
887
|
for (const toolCall of choice.message.tool_calls) {
|
|
831
|
-
if (toolCall.function) {
|
|
888
|
+
if (toolCall.type === 'function' && toolCall.function) {
|
|
832
889
|
let args = {};
|
|
833
890
|
if (toolCall.function.arguments) {
|
|
834
|
-
|
|
835
|
-
|
|
836
|
-
|
|
837
|
-
|
|
838
|
-
|
|
839
|
-
|
|
840
|
-
|
|
891
|
+
args = safeJsonParse(toolCall.function.arguments, {});
|
|
892
|
+
}
|
|
893
|
+
// Special handling for JSON schema requests (like qwen-code)
|
|
894
|
+
if (isJsonSchemaRequest && toolCall.function.name === 'respond_in_schema') {
|
|
895
|
+
// Convert the function call result to a text response (simulate Gemini's JSON response)
|
|
896
|
+
parts.push({ text: JSON.stringify(args) });
|
|
897
|
+
}
|
|
898
|
+
else {
|
|
899
|
+
// Regular tool call handling
|
|
900
|
+
parts.push({
|
|
901
|
+
functionCall: {
|
|
902
|
+
id: toolCall.id,
|
|
903
|
+
name: toolCall.function.name,
|
|
904
|
+
args,
|
|
905
|
+
},
|
|
906
|
+
});
|
|
841
907
|
}
|
|
842
|
-
parts.push({
|
|
843
|
-
functionCall: {
|
|
844
|
-
id: toolCall.id,
|
|
845
|
-
name: toolCall.function.name,
|
|
846
|
-
args,
|
|
847
|
-
},
|
|
848
|
-
});
|
|
849
908
|
}
|
|
850
909
|
}
|
|
851
910
|
}
|
|
@@ -891,7 +950,7 @@ export class OpenAIContentGenerator {
|
|
|
891
950
|
}
|
|
892
951
|
return response;
|
|
893
952
|
}
|
|
894
|
-
convertStreamChunkToGeminiFormat(chunk) {
|
|
953
|
+
convertStreamChunkToGeminiFormat(chunk, isJsonSchemaRequest = false) {
|
|
895
954
|
const choice = chunk.choices?.[0];
|
|
896
955
|
const response = new GenerateContentResponse();
|
|
897
956
|
if (choice) {
|
|
@@ -930,20 +989,23 @@ export class OpenAIContentGenerator {
|
|
|
930
989
|
if (accumulatedCall.name) {
|
|
931
990
|
let args = {};
|
|
932
991
|
if (accumulatedCall.arguments) {
|
|
933
|
-
|
|
934
|
-
|
|
935
|
-
|
|
936
|
-
|
|
937
|
-
|
|
938
|
-
}
|
|
992
|
+
args = safeJsonParse(accumulatedCall.arguments, {});
|
|
993
|
+
}
|
|
994
|
+
// Special handling for JSON schema requests (like qwen-code)
|
|
995
|
+
if (isJsonSchemaRequest && accumulatedCall.name === 'respond_in_schema') {
|
|
996
|
+
// Convert the function call result to a text response (simulate Gemini's JSON response)
|
|
997
|
+
parts.push({ text: JSON.stringify(args) });
|
|
998
|
+
}
|
|
999
|
+
else {
|
|
1000
|
+
// Regular tool call handling
|
|
1001
|
+
parts.push({
|
|
1002
|
+
functionCall: {
|
|
1003
|
+
id: accumulatedCall.id,
|
|
1004
|
+
name: accumulatedCall.name,
|
|
1005
|
+
args,
|
|
1006
|
+
},
|
|
1007
|
+
});
|
|
939
1008
|
}
|
|
940
|
-
parts.push({
|
|
941
|
-
functionCall: {
|
|
942
|
-
id: accumulatedCall.id,
|
|
943
|
-
name: accumulatedCall.name,
|
|
944
|
-
args,
|
|
945
|
-
},
|
|
946
|
-
});
|
|
947
1009
|
}
|
|
948
1010
|
}
|
|
949
1011
|
// Clear all accumulated tool calls
|