@vybestack/llxprt-code-core 0.1.18-nightly.250808.f9b79d74 → 0.1.18-nightly.250811.b0db22c6
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/auth/auth-integration.spec.d.ts +6 -0
- package/dist/src/auth/auth-integration.spec.js +384 -0
- package/dist/src/auth/auth-integration.spec.js.map +1 -0
- package/dist/src/auth/precedence.d.ts +55 -0
- package/dist/src/auth/precedence.js +211 -0
- package/dist/src/auth/precedence.js.map +1 -0
- package/dist/src/auth/precedence.test.d.ts +6 -0
- package/dist/src/auth/precedence.test.js +374 -0
- package/dist/src/auth/precedence.test.js.map +1 -0
- package/dist/src/auth/qwen-device-flow.d.ts +45 -0
- package/dist/src/auth/qwen-device-flow.js +179 -0
- package/dist/src/auth/qwen-device-flow.js.map +1 -0
- package/dist/src/auth/qwen-device-flow.spec.d.ts +6 -0
- package/dist/src/auth/qwen-device-flow.spec.js +793 -0
- package/dist/src/auth/qwen-device-flow.spec.js.map +1 -0
- package/dist/src/auth/token-store.d.ts +66 -0
- package/dist/src/auth/token-store.js +147 -0
- package/dist/src/auth/token-store.js.map +1 -0
- package/dist/src/auth/token-store.spec.d.ts +6 -0
- package/dist/src/auth/token-store.spec.js +405 -0
- package/dist/src/auth/token-store.spec.js.map +1 -0
- package/dist/src/auth/types.d.ts +130 -0
- package/dist/src/auth/types.js +60 -0
- package/dist/src/auth/types.js.map +1 -0
- package/dist/src/code_assist/converter.d.ts +2 -1
- package/dist/src/code_assist/converter.js +1 -1
- package/dist/src/code_assist/converter.js.map +1 -1
- package/dist/src/code_assist/converter.test.js +48 -1
- package/dist/src/code_assist/converter.test.js.map +1 -1
- package/dist/src/code_assist/oauth2.js +2 -1
- package/dist/src/code_assist/oauth2.js.map +1 -1
- package/dist/src/code_assist/server.test.js +4 -1
- package/dist/src/code_assist/server.test.js.map +1 -1
- package/dist/src/config/config.d.ts +71 -2
- package/dist/src/config/config.ephemeral.test.d.ts +6 -0
- package/dist/src/config/config.ephemeral.test.js +152 -0
- package/dist/src/config/config.ephemeral.test.js.map +1 -0
- package/dist/src/config/config.js +117 -2
- package/dist/src/config/config.js.map +1 -1
- package/dist/src/config/config.test.js +8 -0
- package/dist/src/config/config.test.js.map +1 -1
- package/dist/src/config/endpoints.d.ts +60 -0
- package/dist/src/config/endpoints.js +126 -0
- package/dist/src/config/endpoints.js.map +1 -0
- package/dist/src/config/endpoints.test.d.ts +6 -0
- package/dist/src/config/endpoints.test.js +196 -0
- package/dist/src/config/endpoints.test.js.map +1 -0
- package/dist/src/core/client.js +16 -16
- package/dist/src/core/client.js.map +1 -1
- package/dist/src/core/client.test.js +13 -7
- package/dist/src/core/client.test.js.map +1 -1
- package/dist/src/core/contentGenerator.d.ts +3 -1
- package/dist/src/core/contentGenerator.js +2 -0
- package/dist/src/core/contentGenerator.js.map +1 -1
- package/dist/src/core/logger.d.ts +1 -0
- package/dist/src/core/logger.js +18 -0
- package/dist/src/core/logger.js.map +1 -1
- package/dist/src/core/logger.test.js +29 -0
- package/dist/src/core/logger.test.js.map +1 -1
- package/dist/src/core/loggingContentGenerator.d.ts +24 -0
- package/dist/src/core/loggingContentGenerator.js +89 -0
- package/dist/src/core/loggingContentGenerator.js.map +1 -0
- package/dist/src/core/nonInteractiveToolExecutor.js +17 -0
- package/dist/src/core/nonInteractiveToolExecutor.js.map +1 -1
- package/dist/src/core/subagent.js +12 -10
- package/dist/src/core/subagent.js.map +1 -1
- package/dist/src/core/subagent.test.js +8 -17
- package/dist/src/core/subagent.test.js.map +1 -1
- package/dist/src/ide/ide-client.d.ts +2 -2
- package/dist/src/ide/ide-client.js +56 -18
- package/dist/src/ide/ide-client.js.map +1 -1
- package/dist/src/index.d.ts +5 -0
- package/dist/src/index.js +7 -0
- package/dist/src/index.js.map +1 -1
- package/dist/src/integration-tests/oauth-integration.spec.d.ts +6 -0
- package/dist/src/integration-tests/oauth-integration.spec.js +518 -0
- package/dist/src/integration-tests/oauth-integration.spec.js.map +1 -0
- package/dist/src/integration-tests/oauth-simple-test.spec.d.ts +1 -0
- package/dist/src/integration-tests/oauth-simple-test.spec.js +88 -0
- package/dist/src/integration-tests/oauth-simple-test.spec.js.map +1 -0
- package/dist/src/providers/BaseProvider.d.ts +98 -0
- package/dist/src/providers/BaseProvider.js +180 -0
- package/dist/src/providers/BaseProvider.js.map +1 -0
- package/dist/src/providers/BaseProvider.test.d.ts +6 -0
- package/dist/src/providers/BaseProvider.test.js +472 -0
- package/dist/src/providers/BaseProvider.test.js.map +1 -0
- package/dist/src/providers/IProviderManager.d.ts +5 -0
- package/dist/src/providers/LoggingProviderWrapper.d.ts +53 -0
- package/dist/src/providers/LoggingProviderWrapper.js +347 -0
- package/dist/src/providers/LoggingProviderWrapper.js.map +1 -0
- package/dist/src/providers/ProviderManager.d.ts +20 -0
- package/dist/src/providers/ProviderManager.js +214 -1
- package/dist/src/providers/ProviderManager.js.map +1 -1
- package/dist/src/providers/gemini/GeminiProvider.d.ts +12 -7
- package/dist/src/providers/gemini/GeminiProvider.js +130 -147
- package/dist/src/providers/gemini/GeminiProvider.js.map +1 -1
- package/dist/src/providers/integration/multi-provider.integration.test.js +18 -2
- package/dist/src/providers/integration/multi-provider.integration.test.js.map +1 -1
- package/dist/src/providers/logging/ProviderContentExtractor.d.ts +27 -0
- package/dist/src/providers/logging/ProviderContentExtractor.js +198 -0
- package/dist/src/providers/logging/ProviderContentExtractor.js.map +1 -0
- package/dist/src/providers/logging/ProviderPerformanceTracker.d.ts +43 -0
- package/dist/src/providers/logging/ProviderPerformanceTracker.js +98 -0
- package/dist/src/providers/logging/ProviderPerformanceTracker.js.map +1 -0
- package/dist/src/providers/openai/OpenAIProvider.d.ts +21 -6
- package/dist/src/providers/openai/OpenAIProvider.js +173 -27
- package/dist/src/providers/openai/OpenAIProvider.js.map +1 -1
- package/dist/src/providers/openai/OpenAIProvider.test.js +3 -2
- package/dist/src/providers/openai/OpenAIProvider.test.js.map +1 -1
- package/dist/src/providers/openai/openai-oauth.spec.d.ts +16 -0
- package/dist/src/providers/openai/openai-oauth.spec.js +544 -0
- package/dist/src/providers/openai/openai-oauth.spec.js.map +1 -0
- package/dist/src/providers/types.d.ts +47 -0
- package/dist/src/services/git-stats-service.d.ts +32 -0
- package/dist/src/services/git-stats-service.js +22 -0
- package/dist/src/services/git-stats-service.js.map +1 -0
- package/dist/src/services/loopDetectionService.js +10 -6
- package/dist/src/services/loopDetectionService.js.map +1 -1
- package/dist/src/services/loopDetectionService.test.js +139 -0
- package/dist/src/services/loopDetectionService.test.js.map +1 -1
- package/dist/src/services/shellExecutionService.js +44 -8
- package/dist/src/services/shellExecutionService.js.map +1 -1
- package/dist/src/storage/ConversationFileWriter.d.ts +16 -0
- package/dist/src/storage/ConversationFileWriter.js +69 -0
- package/dist/src/storage/ConversationFileWriter.js.map +1 -0
- package/dist/src/telemetry/clearcut-logger/clearcut-logger.d.ts +8 -0
- package/dist/src/telemetry/clearcut-logger/clearcut-logger.js +56 -3
- package/dist/src/telemetry/clearcut-logger/clearcut-logger.js.map +1 -1
- package/dist/src/telemetry/clearcut-logger/clearcut-logger.test.d.ts +6 -0
- package/dist/src/telemetry/clearcut-logger/clearcut-logger.test.js +187 -0
- package/dist/src/telemetry/clearcut-logger/clearcut-logger.test.js.map +1 -0
- package/dist/src/telemetry/clearcut-logger/event-metadata-key.d.ts +5 -1
- package/dist/src/telemetry/clearcut-logger/event-metadata-key.js +11 -0
- package/dist/src/telemetry/clearcut-logger/event-metadata-key.js.map +1 -1
- package/dist/src/telemetry/constants.d.ts +5 -0
- package/dist/src/telemetry/constants.js +5 -0
- package/dist/src/telemetry/constants.js.map +1 -1
- package/dist/src/telemetry/loggers.d.ts +5 -1
- package/dist/src/telemetry/loggers.js +87 -1
- package/dist/src/telemetry/loggers.js.map +1 -1
- package/dist/src/telemetry/loggers.test.js +2 -1
- package/dist/src/telemetry/loggers.test.js.map +1 -1
- package/dist/src/telemetry/metrics.d.ts +2 -1
- package/dist/src/telemetry/metrics.js +7 -1
- package/dist/src/telemetry/metrics.js.map +1 -1
- package/dist/src/telemetry/metrics.test.js +50 -0
- package/dist/src/telemetry/metrics.test.js.map +1 -1
- package/dist/src/telemetry/tool-call-decision.d.ts +13 -0
- package/dist/src/telemetry/tool-call-decision.js +29 -0
- package/dist/src/telemetry/tool-call-decision.js.map +1 -0
- package/dist/src/telemetry/types.d.ts +56 -1
- package/dist/src/telemetry/types.js +123 -0
- package/dist/src/telemetry/types.js.map +1 -1
- package/dist/src/telemetry/uiTelemetry.d.ts +2 -1
- package/dist/src/telemetry/uiTelemetry.js +1 -1
- package/dist/src/telemetry/uiTelemetry.js.map +1 -1
- package/dist/src/telemetry/uiTelemetry.test.js +2 -1
- package/dist/src/telemetry/uiTelemetry.test.js.map +1 -1
- package/dist/src/tools/diffOptions.d.ts +2 -0
- package/dist/src/tools/diffOptions.js +28 -0
- package/dist/src/tools/diffOptions.js.map +1 -1
- package/dist/src/tools/diffOptions.test.d.ts +6 -0
- package/dist/src/tools/diffOptions.test.js +119 -0
- package/dist/src/tools/diffOptions.test.js.map +1 -0
- package/dist/src/tools/edit.d.ts +8 -32
- package/dist/src/tools/edit.js +153 -136
- package/dist/src/tools/edit.js.map +1 -1
- package/dist/src/tools/edit.test.js +77 -51
- package/dist/src/tools/edit.test.js.map +1 -1
- package/dist/src/tools/glob.d.ts +3 -10
- package/dist/src/tools/glob.js +97 -99
- package/dist/src/tools/glob.js.map +1 -1
- package/dist/src/tools/glob.test.js +37 -26
- package/dist/src/tools/glob.test.js.map +1 -1
- package/dist/src/tools/grep.d.ts +3 -35
- package/dist/src/tools/grep.js +117 -88
- package/dist/src/tools/grep.js.map +1 -1
- package/dist/src/tools/grep.test.js +36 -22
- package/dist/src/tools/grep.test.js.map +1 -1
- package/dist/src/tools/mcp-client.d.ts +4 -3
- package/dist/src/tools/mcp-client.js +23 -6
- package/dist/src/tools/mcp-client.js.map +1 -1
- package/dist/src/tools/mcp-client.test.js +44 -2
- package/dist/src/tools/mcp-client.test.js.map +1 -1
- package/dist/src/tools/read-file.js +37 -9
- package/dist/src/tools/read-file.js.map +1 -1
- package/dist/src/tools/read-file.test.js +8 -2
- package/dist/src/tools/read-file.test.js.map +1 -1
- package/dist/src/tools/shell.test.js +17 -0
- package/dist/src/tools/shell.test.js.map +1 -1
- package/dist/src/tools/todo-pause.d.ts +22 -0
- package/dist/src/tools/todo-pause.js +93 -0
- package/dist/src/tools/todo-pause.js.map +1 -0
- package/dist/src/tools/todo-pause.spec.d.ts +6 -0
- package/dist/src/tools/todo-pause.spec.js +287 -0
- package/dist/src/tools/todo-pause.spec.js.map +1 -0
- package/dist/src/tools/tool-error.d.ts +4 -0
- package/dist/src/tools/tool-error.js +4 -0
- package/dist/src/tools/tool-error.js.map +1 -1
- package/dist/src/tools/tool-registry.js +3 -3
- package/dist/src/tools/tool-registry.js.map +1 -1
- package/dist/src/tools/tool-registry.test.js +2 -2
- package/dist/src/tools/tool-registry.test.js.map +1 -1
- package/dist/src/tools/tools.d.ts +18 -0
- package/dist/src/tools/tools.js +15 -0
- package/dist/src/tools/tools.js.map +1 -1
- package/dist/src/tools/web-search.test.js +1 -0
- package/dist/src/tools/web-search.test.js.map +1 -1
- package/dist/src/tools/write-file.d.ts +4 -0
- package/dist/src/tools/write-file.js +90 -16
- package/dist/src/tools/write-file.js.map +1 -1
- package/dist/src/tools/write-file.test.js +5 -4
- package/dist/src/tools/write-file.test.js.map +1 -1
- package/dist/src/types/modelParams.d.ts +2 -0
- package/dist/src/utils/environmentContext.js +1 -1
- package/dist/src/utils/errors.d.ts +3 -0
- package/dist/src/utils/errors.js +6 -0
- package/dist/src/utils/errors.js.map +1 -1
- package/dist/src/utils/fileUtils.d.ts +7 -0
- package/dist/src/utils/fileUtils.js +9 -0
- package/dist/src/utils/fileUtils.js.map +1 -1
- package/dist/src/utils/filesearch/fileSearch.d.ts +1 -0
- package/dist/src/utils/filesearch/fileSearch.js +27 -19
- package/dist/src/utils/filesearch/fileSearch.js.map +1 -1
- package/package.json +1 -1
|
@@ -0,0 +1,347 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* @license
|
|
3
|
+
* Copyright 2025 Vybestack LLC
|
|
4
|
+
* SPDX-License-Identifier: Apache-2.0
|
|
5
|
+
*/
|
|
6
|
+
import { logConversationRequest, logConversationResponse, } from '../telemetry/loggers.js';
|
|
7
|
+
import { ConversationRequestEvent, ConversationResponseEvent, } from '../telemetry/types.js';
|
|
8
|
+
import { getConversationFileWriter } from '../storage/ConversationFileWriter.js';
|
|
9
|
+
// Simple redactor that works with RedactionConfig
|
|
10
|
+
class ConfigBasedRedactor {
|
|
11
|
+
redactionConfig;
|
|
12
|
+
constructor(redactionConfig) {
|
|
13
|
+
this.redactionConfig = redactionConfig;
|
|
14
|
+
}
|
|
15
|
+
redactMessage(message, providerName) {
|
|
16
|
+
if (!this.shouldRedact()) {
|
|
17
|
+
return message;
|
|
18
|
+
}
|
|
19
|
+
const redactedMessage = { ...message };
|
|
20
|
+
if (typeof redactedMessage.content === 'string') {
|
|
21
|
+
redactedMessage.content = this.redactContent(redactedMessage.content, providerName);
|
|
22
|
+
}
|
|
23
|
+
// Redact tool_calls if present
|
|
24
|
+
if (redactedMessage.tool_calls) {
|
|
25
|
+
redactedMessage.tool_calls = redactedMessage.tool_calls.map((call) => ({
|
|
26
|
+
...call,
|
|
27
|
+
function: {
|
|
28
|
+
...call.function,
|
|
29
|
+
arguments: this.redactContent(call.function.arguments, providerName),
|
|
30
|
+
},
|
|
31
|
+
}));
|
|
32
|
+
}
|
|
33
|
+
return redactedMessage;
|
|
34
|
+
}
|
|
35
|
+
redactToolCall(tool) {
|
|
36
|
+
if (!this.shouldRedact()) {
|
|
37
|
+
return tool;
|
|
38
|
+
}
|
|
39
|
+
const redactedTool = { ...tool };
|
|
40
|
+
if (redactedTool.function.parameters && tool.function.name) {
|
|
41
|
+
const redactedParams = this.redactContent(JSON.stringify(redactedTool.function.parameters), 'global');
|
|
42
|
+
try {
|
|
43
|
+
redactedTool.function.parameters = JSON.parse(redactedParams);
|
|
44
|
+
}
|
|
45
|
+
catch {
|
|
46
|
+
// If parsing fails, keep original parameters
|
|
47
|
+
redactedTool.function.parameters = tool.function.parameters;
|
|
48
|
+
}
|
|
49
|
+
}
|
|
50
|
+
return redactedTool;
|
|
51
|
+
}
|
|
52
|
+
redactResponseContent(content, providerName) {
|
|
53
|
+
if (!this.shouldRedact()) {
|
|
54
|
+
return content;
|
|
55
|
+
}
|
|
56
|
+
return this.redactContent(content, providerName);
|
|
57
|
+
}
|
|
58
|
+
shouldRedact() {
|
|
59
|
+
return (this.redactionConfig.redactApiKeys ||
|
|
60
|
+
this.redactionConfig.redactCredentials ||
|
|
61
|
+
this.redactionConfig.redactFilePaths ||
|
|
62
|
+
this.redactionConfig.redactUrls ||
|
|
63
|
+
this.redactionConfig.redactEmails ||
|
|
64
|
+
this.redactionConfig.redactPersonalInfo);
|
|
65
|
+
}
|
|
66
|
+
redactContent(content, _providerName) {
|
|
67
|
+
let redacted = content;
|
|
68
|
+
// Apply basic API key redaction if enabled
|
|
69
|
+
if (this.redactionConfig.redactApiKeys) {
|
|
70
|
+
redacted = redacted.replace(/sk-[a-zA-Z0-9]{32,}/g, '[REDACTED-API-KEY]');
|
|
71
|
+
redacted = redacted.replace(/sk-proj-[a-zA-Z0-9]{48}/g, '[REDACTED-OPENAI-PROJECT-KEY]');
|
|
72
|
+
redacted = redacted.replace(/sk-ant-[a-zA-Z0-9\-_]{95}/g, '[REDACTED-ANTHROPIC-KEY]');
|
|
73
|
+
redacted = redacted.replace(/AIza[0-9A-Za-z\-_]{35}/g, '[REDACTED-GOOGLE-KEY]');
|
|
74
|
+
}
|
|
75
|
+
// Apply credential redaction if enabled
|
|
76
|
+
if (this.redactionConfig.redactCredentials) {
|
|
77
|
+
redacted = redacted.replace(/(?:password|pwd|pass)[=:\s]+[^\s\n\r]+/gi, 'password=[REDACTED]');
|
|
78
|
+
redacted = redacted.replace(/bearer [a-zA-Z0-9-_.]{16,}/gi, 'bearer [REDACTED-BEARER-TOKEN]');
|
|
79
|
+
}
|
|
80
|
+
// Apply file path redaction if enabled
|
|
81
|
+
if (this.redactionConfig.redactFilePaths) {
|
|
82
|
+
redacted = redacted.replace(/\/[^"\s]*\.ssh\/[^"\s]*/g, '[REDACTED-SSH-PATH]');
|
|
83
|
+
redacted = redacted.replace(/\/[^"\s]*\.env[^"\s]*/g, '[REDACTED-ENV-FILE]');
|
|
84
|
+
redacted = redacted.replace(/\/home\/[^/\s"]+/g, '[REDACTED-HOME-DIR]');
|
|
85
|
+
redacted = redacted.replace(/\/Users\/[^/\s"]+/g, '[REDACTED-USER-DIR]');
|
|
86
|
+
}
|
|
87
|
+
// Apply email redaction if enabled
|
|
88
|
+
if (this.redactionConfig.redactEmails) {
|
|
89
|
+
redacted = redacted.replace(/[a-zA-Z0-9._%+-]+@[a-zA-Z0-9.-]+\.[a-zA-Z]{2,}/g, '[REDACTED-EMAIL]');
|
|
90
|
+
}
|
|
91
|
+
// Apply personal info redaction if enabled
|
|
92
|
+
if (this.redactionConfig.redactPersonalInfo) {
|
|
93
|
+
redacted = redacted.replace(/\b\d{3}-\d{3}-\d{4}\b/g, '[REDACTED-PHONE]');
|
|
94
|
+
redacted = redacted.replace(/\b\d{4}[-\s]?\d{4}[-\s]?\d{4}[-\s]?\d{4}\b/g, '[REDACTED-CC-NUMBER]');
|
|
95
|
+
}
|
|
96
|
+
return redacted;
|
|
97
|
+
}
|
|
98
|
+
}
|
|
99
|
+
/**
|
|
100
|
+
* A minimal logging wrapper that acts as a transparent passthrough to the wrapped provider.
|
|
101
|
+
* Only intercepts generateChatCompletion to log conversations while forwarding all other
|
|
102
|
+
* methods directly to the wrapped provider without modification.
|
|
103
|
+
*/
|
|
104
|
+
export class LoggingProviderWrapper {
|
|
105
|
+
wrapped;
|
|
106
|
+
config;
|
|
107
|
+
conversationId;
|
|
108
|
+
turnNumber = 0;
|
|
109
|
+
redactor;
|
|
110
|
+
constructor(wrapped, config, redactor) {
|
|
111
|
+
this.wrapped = wrapped;
|
|
112
|
+
this.config = config;
|
|
113
|
+
this.conversationId = this.generateConversationId();
|
|
114
|
+
this.redactor =
|
|
115
|
+
redactor || new ConfigBasedRedactor(config.getRedactionConfig());
|
|
116
|
+
}
|
|
117
|
+
/**
|
|
118
|
+
* Access to the wrapped provider for unwrapping if needed
|
|
119
|
+
*/
|
|
120
|
+
get wrappedProvider() {
|
|
121
|
+
return this.wrapped;
|
|
122
|
+
}
|
|
123
|
+
// Passthrough properties
|
|
124
|
+
get name() {
|
|
125
|
+
return this.wrapped.name;
|
|
126
|
+
}
|
|
127
|
+
get isDefault() {
|
|
128
|
+
return this.wrapped.isDefault;
|
|
129
|
+
}
|
|
130
|
+
// Passthrough methods - delegate everything to wrapped provider
|
|
131
|
+
async getModels() {
|
|
132
|
+
return this.wrapped.getModels();
|
|
133
|
+
}
|
|
134
|
+
// Only method that includes logging - everything else is passthrough
|
|
135
|
+
async *generateChatCompletion(messages, tools, toolFormat) {
|
|
136
|
+
const promptId = this.generatePromptId();
|
|
137
|
+
this.turnNumber++;
|
|
138
|
+
// Log request if logging is enabled
|
|
139
|
+
if (this.config.getConversationLoggingEnabled()) {
|
|
140
|
+
await this.logRequest(messages, tools, toolFormat, promptId);
|
|
141
|
+
}
|
|
142
|
+
// Get stream from wrapped provider
|
|
143
|
+
const stream = this.wrapped.generateChatCompletion(messages, tools, toolFormat);
|
|
144
|
+
// If logging not enabled, just pass through
|
|
145
|
+
if (!this.config.getConversationLoggingEnabled()) {
|
|
146
|
+
yield* stream;
|
|
147
|
+
return;
|
|
148
|
+
}
|
|
149
|
+
// Log the response stream
|
|
150
|
+
yield* this.logResponseStream(stream, promptId);
|
|
151
|
+
}
|
|
152
|
+
async logRequest(messages, tools, toolFormat, promptId) {
|
|
153
|
+
try {
|
|
154
|
+
// Apply redaction to messages and tools
|
|
155
|
+
const redactedMessages = messages.map((msg) => this.redactor.redactMessage(msg, this.wrapped.name));
|
|
156
|
+
const redactedTools = tools?.map((tool) => this.redactor.redactToolCall(tool));
|
|
157
|
+
const event = new ConversationRequestEvent(this.wrapped.name, this.conversationId, this.turnNumber, promptId || this.generatePromptId(), redactedMessages, redactedTools, toolFormat);
|
|
158
|
+
logConversationRequest(this.config, event);
|
|
159
|
+
// Also write to disk
|
|
160
|
+
const fileWriter = getConversationFileWriter(this.config.getConversationLogPath());
|
|
161
|
+
fileWriter.writeRequest(this.wrapped.name, redactedMessages, {
|
|
162
|
+
conversationId: this.conversationId,
|
|
163
|
+
turnNumber: this.turnNumber,
|
|
164
|
+
promptId: promptId || this.generatePromptId(),
|
|
165
|
+
tools: redactedTools,
|
|
166
|
+
toolFormat,
|
|
167
|
+
});
|
|
168
|
+
}
|
|
169
|
+
catch (error) {
|
|
170
|
+
// Log error but don't fail the request
|
|
171
|
+
console.warn('Failed to log conversation request:', error);
|
|
172
|
+
}
|
|
173
|
+
}
|
|
174
|
+
async *logResponseStream(stream, promptId) {
|
|
175
|
+
const startTime = performance.now();
|
|
176
|
+
let responseContent = '';
|
|
177
|
+
let responseComplete = false;
|
|
178
|
+
try {
|
|
179
|
+
for await (const chunk of stream) {
|
|
180
|
+
// Simple content extraction - just try to get text from common chunk formats
|
|
181
|
+
const content = this.extractSimpleContent(chunk);
|
|
182
|
+
if (content) {
|
|
183
|
+
responseContent += content;
|
|
184
|
+
}
|
|
185
|
+
yield chunk;
|
|
186
|
+
}
|
|
187
|
+
responseComplete = true;
|
|
188
|
+
}
|
|
189
|
+
catch (error) {
|
|
190
|
+
const errorTime = performance.now();
|
|
191
|
+
await this.logResponse('', promptId, errorTime - startTime, false, error);
|
|
192
|
+
throw error;
|
|
193
|
+
}
|
|
194
|
+
if (responseComplete) {
|
|
195
|
+
const totalTime = performance.now() - startTime;
|
|
196
|
+
await this.logResponse(responseContent, promptId, totalTime, true);
|
|
197
|
+
}
|
|
198
|
+
}
|
|
199
|
+
// Simple content extraction without complex provider-specific logic
|
|
200
|
+
extractSimpleContent(chunk) {
|
|
201
|
+
if (!chunk || typeof chunk !== 'object') {
|
|
202
|
+
return '';
|
|
203
|
+
}
|
|
204
|
+
const obj = chunk;
|
|
205
|
+
// Try common content paths
|
|
206
|
+
if (obj.choices && Array.isArray(obj.choices)) {
|
|
207
|
+
const choice = obj.choices[0];
|
|
208
|
+
if (choice?.delta && typeof choice.delta === 'object') {
|
|
209
|
+
const delta = choice.delta;
|
|
210
|
+
if (typeof delta.content === 'string') {
|
|
211
|
+
return delta.content;
|
|
212
|
+
}
|
|
213
|
+
}
|
|
214
|
+
}
|
|
215
|
+
return '';
|
|
216
|
+
}
|
|
217
|
+
async logResponse(content, promptId, duration, success, error) {
|
|
218
|
+
try {
|
|
219
|
+
const redactedContent = this.redactor.redactResponseContent(content, this.wrapped.name);
|
|
220
|
+
const event = new ConversationResponseEvent(this.wrapped.name, this.conversationId, this.turnNumber, promptId, redactedContent, duration, success, error ? String(error) : undefined);
|
|
221
|
+
logConversationResponse(this.config, event);
|
|
222
|
+
// Also write to disk
|
|
223
|
+
const fileWriter = getConversationFileWriter(this.config.getConversationLogPath());
|
|
224
|
+
fileWriter.writeResponse(this.wrapped.name, redactedContent, {
|
|
225
|
+
conversationId: this.conversationId,
|
|
226
|
+
turnNumber: this.turnNumber,
|
|
227
|
+
promptId,
|
|
228
|
+
duration,
|
|
229
|
+
success,
|
|
230
|
+
error: error ? String(error) : undefined,
|
|
231
|
+
});
|
|
232
|
+
}
|
|
233
|
+
catch (logError) {
|
|
234
|
+
console.warn('Failed to log conversation response:', logError);
|
|
235
|
+
}
|
|
236
|
+
}
|
|
237
|
+
generateConversationId() {
|
|
238
|
+
return `conv_${Date.now()}_${Math.random().toString(36).substr(2, 9)}`;
|
|
239
|
+
}
|
|
240
|
+
generatePromptId() {
|
|
241
|
+
return `prompt_${Date.now()}_${Math.random().toString(36).substr(2, 9)}`;
|
|
242
|
+
}
|
|
243
|
+
async logToolCall(toolName, params, result, startTime, success, error) {
|
|
244
|
+
try {
|
|
245
|
+
const endTime = Date.now();
|
|
246
|
+
const duration = endTime - startTime;
|
|
247
|
+
// Extract git stats from result metadata if available
|
|
248
|
+
let gitStats = null;
|
|
249
|
+
if (result && typeof result === 'object' && 'metadata' in result) {
|
|
250
|
+
const metadata = result
|
|
251
|
+
.metadata;
|
|
252
|
+
if (metadata && metadata.gitStats) {
|
|
253
|
+
gitStats = metadata.gitStats;
|
|
254
|
+
}
|
|
255
|
+
}
|
|
256
|
+
const _entry = {
|
|
257
|
+
type: 'tool_call',
|
|
258
|
+
tool: toolName,
|
|
259
|
+
timestamp: new Date(startTime).toISOString(),
|
|
260
|
+
duration,
|
|
261
|
+
success,
|
|
262
|
+
conversationId: this.conversationId,
|
|
263
|
+
turnNumber: this.turnNumber,
|
|
264
|
+
// Include git stats if present
|
|
265
|
+
gitStats,
|
|
266
|
+
error: error ? String(error) : undefined,
|
|
267
|
+
};
|
|
268
|
+
// Write to disk
|
|
269
|
+
const fileWriter = getConversationFileWriter(this.config.getConversationLogPath());
|
|
270
|
+
fileWriter.writeToolCall(this.wrapped.name, toolName, {
|
|
271
|
+
conversationId: this.conversationId,
|
|
272
|
+
turnNumber: this.turnNumber,
|
|
273
|
+
params: this.redactor.redactToolCall({
|
|
274
|
+
type: 'function',
|
|
275
|
+
function: { name: toolName, parameters: params },
|
|
276
|
+
}).function.parameters,
|
|
277
|
+
result,
|
|
278
|
+
duration,
|
|
279
|
+
success,
|
|
280
|
+
error: error ? String(error) : undefined,
|
|
281
|
+
gitStats,
|
|
282
|
+
});
|
|
283
|
+
}
|
|
284
|
+
catch (logError) {
|
|
285
|
+
console.warn('Failed to log tool call:', logError);
|
|
286
|
+
}
|
|
287
|
+
}
|
|
288
|
+
// All other methods are simple passthroughs to wrapped provider
|
|
289
|
+
setModel(modelId) {
|
|
290
|
+
this.wrapped.setModel?.(modelId);
|
|
291
|
+
}
|
|
292
|
+
getCurrentModel() {
|
|
293
|
+
return this.wrapped.getCurrentModel?.() ?? '';
|
|
294
|
+
}
|
|
295
|
+
setApiKey(apiKey) {
|
|
296
|
+
this.wrapped.setApiKey?.(apiKey);
|
|
297
|
+
}
|
|
298
|
+
setBaseUrl(baseUrl) {
|
|
299
|
+
this.wrapped.setBaseUrl?.(baseUrl);
|
|
300
|
+
}
|
|
301
|
+
getToolFormat() {
|
|
302
|
+
return this.wrapped.getToolFormat?.() ?? '';
|
|
303
|
+
}
|
|
304
|
+
setToolFormatOverride(format) {
|
|
305
|
+
this.wrapped.setToolFormatOverride?.(format);
|
|
306
|
+
}
|
|
307
|
+
isPaidMode() {
|
|
308
|
+
return this.wrapped.isPaidMode?.() ?? false;
|
|
309
|
+
}
|
|
310
|
+
clearState() {
|
|
311
|
+
this.wrapped.clearState?.();
|
|
312
|
+
// Reset conversation logging state
|
|
313
|
+
this.conversationId = this.generateConversationId();
|
|
314
|
+
this.turnNumber = 0;
|
|
315
|
+
}
|
|
316
|
+
setConfig(config) {
|
|
317
|
+
this.wrapped.setConfig?.(config);
|
|
318
|
+
}
|
|
319
|
+
getServerTools() {
|
|
320
|
+
return this.wrapped.getServerTools();
|
|
321
|
+
}
|
|
322
|
+
async invokeServerTool(toolName, params, config) {
|
|
323
|
+
const startTime = Date.now();
|
|
324
|
+
try {
|
|
325
|
+
const result = await this.wrapped.invokeServerTool(toolName, params, config);
|
|
326
|
+
// Log tool call if logging is enabled and result has metadata
|
|
327
|
+
if (this.config.getConversationLoggingEnabled()) {
|
|
328
|
+
await this.logToolCall(toolName, params, result, startTime, true);
|
|
329
|
+
}
|
|
330
|
+
return result;
|
|
331
|
+
}
|
|
332
|
+
catch (error) {
|
|
333
|
+
// Log failed tool call if logging is enabled
|
|
334
|
+
if (this.config.getConversationLoggingEnabled()) {
|
|
335
|
+
await this.logToolCall(toolName, params, null, startTime, false, error);
|
|
336
|
+
}
|
|
337
|
+
throw error;
|
|
338
|
+
}
|
|
339
|
+
}
|
|
340
|
+
setModelParams(params) {
|
|
341
|
+
this.wrapped.setModelParams?.(params);
|
|
342
|
+
}
|
|
343
|
+
getModelParams() {
|
|
344
|
+
return this.wrapped.getModelParams?.();
|
|
345
|
+
}
|
|
346
|
+
}
|
|
347
|
+
//# sourceMappingURL=LoggingProviderWrapper.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"LoggingProviderWrapper.js","sourceRoot":"","sources":["../../../src/providers/LoggingProviderWrapper.ts"],"names":[],"mappings":"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"}
|
|
@@ -6,11 +6,18 @@
|
|
|
6
6
|
import { IProvider } from './IProvider.js';
|
|
7
7
|
import { IModel } from './IModel.js';
|
|
8
8
|
import { IProviderManager } from './IProviderManager.js';
|
|
9
|
+
import { Config } from '../config/config.js';
|
|
10
|
+
import type { ProviderCapabilities, ProviderComparison } from './types.js';
|
|
9
11
|
export declare class ProviderManager implements IProviderManager {
|
|
10
12
|
private providers;
|
|
11
13
|
private activeProviderName;
|
|
12
14
|
private serverToolsProvider;
|
|
15
|
+
private config?;
|
|
16
|
+
private providerCapabilities;
|
|
17
|
+
private currentConversationId?;
|
|
13
18
|
constructor();
|
|
19
|
+
setConfig(config: Config): void;
|
|
20
|
+
private updateProviderWrapping;
|
|
14
21
|
registerProvider(provider: IProvider): void;
|
|
15
22
|
setActiveProvider(name: string): void;
|
|
16
23
|
clearActiveProvider(): void;
|
|
@@ -21,4 +28,17 @@ export declare class ProviderManager implements IProviderManager {
|
|
|
21
28
|
hasActiveProvider(): boolean;
|
|
22
29
|
getServerToolsProvider(): IProvider | null;
|
|
23
30
|
setServerToolsProvider(provider: IProvider | null): void;
|
|
31
|
+
private generateConversationId;
|
|
32
|
+
private isContextPreserved;
|
|
33
|
+
private captureProviderCapabilities;
|
|
34
|
+
private detectVisionSupport;
|
|
35
|
+
private getProviderMaxTokens;
|
|
36
|
+
private getSupportedToolFormats;
|
|
37
|
+
private createProviderContext;
|
|
38
|
+
private calculateCapabilityCompatibility;
|
|
39
|
+
getCurrentConversationId(): string;
|
|
40
|
+
resetConversationContext(): void;
|
|
41
|
+
getProviderCapabilities(providerName?: string): ProviderCapabilities | undefined;
|
|
42
|
+
compareProviders(provider1: string, provider2: string): ProviderComparison;
|
|
43
|
+
private generateProviderRecommendation;
|
|
24
44
|
}
|
|
@@ -3,17 +3,67 @@
|
|
|
3
3
|
* Copyright 2025 Vybestack LLC
|
|
4
4
|
* SPDX-License-Identifier: Apache-2.0
|
|
5
5
|
*/
|
|
6
|
+
import { LoggingProviderWrapper } from './LoggingProviderWrapper.js';
|
|
7
|
+
import { logProviderSwitch, logProviderCapability, } from '../telemetry/loggers.js';
|
|
8
|
+
import { ProviderSwitchEvent, ProviderCapabilityEvent, } from '../telemetry/types.js';
|
|
6
9
|
export class ProviderManager {
|
|
7
10
|
providers;
|
|
8
11
|
activeProviderName;
|
|
9
12
|
serverToolsProvider;
|
|
13
|
+
config;
|
|
14
|
+
providerCapabilities = new Map();
|
|
15
|
+
currentConversationId;
|
|
10
16
|
constructor() {
|
|
11
17
|
this.providers = new Map();
|
|
12
18
|
this.activeProviderName = ''; // No default provider
|
|
13
19
|
this.serverToolsProvider = null;
|
|
14
20
|
}
|
|
21
|
+
setConfig(config) {
|
|
22
|
+
const oldLoggingEnabled = this.config?.getConversationLoggingEnabled() ?? false;
|
|
23
|
+
const newLoggingEnabled = config.getConversationLoggingEnabled();
|
|
24
|
+
this.config = config;
|
|
25
|
+
// If logging state changed, update provider wrapping
|
|
26
|
+
if (oldLoggingEnabled !== newLoggingEnabled) {
|
|
27
|
+
this.updateProviderWrapping();
|
|
28
|
+
}
|
|
29
|
+
}
|
|
30
|
+
updateProviderWrapping() {
|
|
31
|
+
// Re-wrap all providers based on current logging state
|
|
32
|
+
const loggingEnabled = this.config?.getConversationLoggingEnabled() ?? false;
|
|
33
|
+
const providers = new Map(this.providers);
|
|
34
|
+
for (const [name, provider] of providers) {
|
|
35
|
+
// Unwrap if it's already wrapped
|
|
36
|
+
let baseProvider = provider;
|
|
37
|
+
if ('wrappedProvider' in provider && provider.wrappedProvider) {
|
|
38
|
+
baseProvider = provider.wrappedProvider;
|
|
39
|
+
}
|
|
40
|
+
// Re-wrap based on current logging state
|
|
41
|
+
let finalProvider = baseProvider;
|
|
42
|
+
if (loggingEnabled) {
|
|
43
|
+
finalProvider = new LoggingProviderWrapper(baseProvider, this.config);
|
|
44
|
+
}
|
|
45
|
+
this.providers.set(name, finalProvider);
|
|
46
|
+
// Update server tools provider reference if needed
|
|
47
|
+
if (this.serverToolsProvider && this.serverToolsProvider.name === name) {
|
|
48
|
+
this.serverToolsProvider = finalProvider;
|
|
49
|
+
}
|
|
50
|
+
}
|
|
51
|
+
}
|
|
15
52
|
registerProvider(provider) {
|
|
16
|
-
|
|
53
|
+
// Wrap provider with logging if conversation logging is enabled
|
|
54
|
+
let finalProvider = provider;
|
|
55
|
+
if (this.config?.getConversationLoggingEnabled()) {
|
|
56
|
+
finalProvider = new LoggingProviderWrapper(provider, this.config);
|
|
57
|
+
}
|
|
58
|
+
this.providers.set(provider.name, finalProvider);
|
|
59
|
+
// Capture provider capabilities
|
|
60
|
+
const capabilities = this.captureProviderCapabilities(provider);
|
|
61
|
+
this.providerCapabilities.set(provider.name, capabilities);
|
|
62
|
+
// Log provider capability information if logging enabled
|
|
63
|
+
if (this.config?.getConversationLoggingEnabled()) {
|
|
64
|
+
const context = this.createProviderContext(provider, capabilities);
|
|
65
|
+
logProviderCapability(this.config, new ProviderCapabilityEvent(provider.name, capabilities, context));
|
|
66
|
+
}
|
|
17
67
|
// If this is the default provider and no provider is active, set it as active
|
|
18
68
|
if (provider.isDefault && !this.activeProviderName) {
|
|
19
69
|
this.activeProviderName = provider.name;
|
|
@@ -44,6 +94,12 @@ export class ProviderManager {
|
|
|
44
94
|
}
|
|
45
95
|
}
|
|
46
96
|
}
|
|
97
|
+
// Log provider switch if conversation logging enabled
|
|
98
|
+
if (this.config?.getConversationLoggingEnabled() &&
|
|
99
|
+
previousProviderName &&
|
|
100
|
+
previousProviderName !== name) {
|
|
101
|
+
logProviderSwitch(this.config, new ProviderSwitchEvent(previousProviderName, name, this.generateConversationId(), this.isContextPreserved(previousProviderName, name)));
|
|
102
|
+
}
|
|
47
103
|
this.activeProviderName = name;
|
|
48
104
|
// If switching to Gemini, use it as both active and serverTools provider
|
|
49
105
|
// BUT only if we don't already have a Gemini serverToolsProvider with auth state
|
|
@@ -112,5 +168,162 @@ export class ProviderManager {
|
|
|
112
168
|
setServerToolsProvider(provider) {
|
|
113
169
|
this.serverToolsProvider = provider;
|
|
114
170
|
}
|
|
171
|
+
generateConversationId() {
|
|
172
|
+
// Generate unique conversation ID for session
|
|
173
|
+
return `conv_${Date.now()}_${Math.random().toString(36).substr(2, 9)}`;
|
|
174
|
+
}
|
|
175
|
+
isContextPreserved(fromProvider, toProvider) {
|
|
176
|
+
// Analyze whether context can be preserved between providers
|
|
177
|
+
const fromCapabilities = this.providerCapabilities.get(fromProvider);
|
|
178
|
+
const toCapabilities = this.providerCapabilities.get(toProvider);
|
|
179
|
+
if (!fromCapabilities || !toCapabilities) {
|
|
180
|
+
return false; // Can't analyze without capabilities
|
|
181
|
+
}
|
|
182
|
+
// Context is better preserved between providers with similar capabilities
|
|
183
|
+
const capabilityScore = this.calculateCapabilityCompatibility(fromCapabilities, toCapabilities);
|
|
184
|
+
// Context is considered preserved if compatibility is high
|
|
185
|
+
return capabilityScore > 0.7;
|
|
186
|
+
}
|
|
187
|
+
captureProviderCapabilities(provider) {
|
|
188
|
+
return {
|
|
189
|
+
supportsStreaming: true, // All current providers support streaming
|
|
190
|
+
supportsTools: provider.getServerTools().length > 0,
|
|
191
|
+
supportsVision: this.detectVisionSupport(provider),
|
|
192
|
+
maxTokens: this.getProviderMaxTokens(provider),
|
|
193
|
+
supportedFormats: this.getSupportedToolFormats(provider),
|
|
194
|
+
hasModelSelection: typeof provider.setModel === 'function',
|
|
195
|
+
hasApiKeyConfig: typeof provider.setApiKey === 'function',
|
|
196
|
+
hasBaseUrlConfig: typeof provider.setBaseUrl === 'function',
|
|
197
|
+
supportsPaidMode: typeof provider.isPaidMode === 'function',
|
|
198
|
+
};
|
|
199
|
+
}
|
|
200
|
+
detectVisionSupport(provider) {
|
|
201
|
+
// Provider-specific vision detection logic
|
|
202
|
+
switch (provider.name) {
|
|
203
|
+
case 'gemini': {
|
|
204
|
+
return true;
|
|
205
|
+
}
|
|
206
|
+
case 'openai': {
|
|
207
|
+
const model = provider.getCurrentModel?.() || '';
|
|
208
|
+
return model.includes('vision') || model.includes('gpt-4');
|
|
209
|
+
}
|
|
210
|
+
case 'anthropic': {
|
|
211
|
+
const claudeModel = provider.getCurrentModel?.() || '';
|
|
212
|
+
return claudeModel.includes('claude-3');
|
|
213
|
+
}
|
|
214
|
+
default:
|
|
215
|
+
return false;
|
|
216
|
+
}
|
|
217
|
+
}
|
|
218
|
+
getProviderMaxTokens(provider) {
|
|
219
|
+
const model = provider.getCurrentModel?.() || '';
|
|
220
|
+
switch (provider.name) {
|
|
221
|
+
case 'gemini':
|
|
222
|
+
if (model.includes('pro'))
|
|
223
|
+
return 32768;
|
|
224
|
+
if (model.includes('flash'))
|
|
225
|
+
return 8192;
|
|
226
|
+
return 8192;
|
|
227
|
+
case 'openai':
|
|
228
|
+
if (model.includes('gpt-4'))
|
|
229
|
+
return 8192;
|
|
230
|
+
if (model.includes('gpt-3.5'))
|
|
231
|
+
return 4096;
|
|
232
|
+
return 4096;
|
|
233
|
+
case 'anthropic':
|
|
234
|
+
if (model.includes('claude-3'))
|
|
235
|
+
return 200000;
|
|
236
|
+
return 100000;
|
|
237
|
+
default:
|
|
238
|
+
return 4096;
|
|
239
|
+
}
|
|
240
|
+
}
|
|
241
|
+
getSupportedToolFormats(provider) {
|
|
242
|
+
switch (provider.name) {
|
|
243
|
+
case 'gemini':
|
|
244
|
+
return ['function_calling', 'gemini_tools'];
|
|
245
|
+
case 'openai':
|
|
246
|
+
return ['function_calling', 'json_schema', 'hermes'];
|
|
247
|
+
case 'anthropic':
|
|
248
|
+
return ['xml_tools', 'anthropic_tools'];
|
|
249
|
+
default:
|
|
250
|
+
return [];
|
|
251
|
+
}
|
|
252
|
+
}
|
|
253
|
+
createProviderContext(provider, capabilities) {
|
|
254
|
+
return {
|
|
255
|
+
providerName: provider.name,
|
|
256
|
+
currentModel: provider.getCurrentModel?.() || 'unknown',
|
|
257
|
+
toolFormat: provider.getToolFormat?.() || 'unknown',
|
|
258
|
+
isPaidMode: provider.isPaidMode?.() || false,
|
|
259
|
+
capabilities,
|
|
260
|
+
sessionStartTime: Date.now(),
|
|
261
|
+
};
|
|
262
|
+
}
|
|
263
|
+
calculateCapabilityCompatibility(from, to) {
|
|
264
|
+
let score = 0;
|
|
265
|
+
let totalChecks = 0;
|
|
266
|
+
// Check tool support compatibility
|
|
267
|
+
totalChecks++;
|
|
268
|
+
if (from.supportsTools === to.supportsTools)
|
|
269
|
+
score++;
|
|
270
|
+
// Check vision support compatibility
|
|
271
|
+
totalChecks++;
|
|
272
|
+
if (from.supportsVision === to.supportsVision)
|
|
273
|
+
score++;
|
|
274
|
+
// Check streaming compatibility (all providers support streaming currently)
|
|
275
|
+
totalChecks++;
|
|
276
|
+
if (from.supportsStreaming === to.supportsStreaming)
|
|
277
|
+
score++;
|
|
278
|
+
// Check tool format compatibility
|
|
279
|
+
totalChecks++;
|
|
280
|
+
const hasCommonFormats = from.supportedFormats.some((format) => to.supportedFormats.includes(format));
|
|
281
|
+
if (hasCommonFormats)
|
|
282
|
+
score++;
|
|
283
|
+
return score / totalChecks;
|
|
284
|
+
}
|
|
285
|
+
// Public API methods for provider capabilities
|
|
286
|
+
getCurrentConversationId() {
|
|
287
|
+
if (!this.currentConversationId) {
|
|
288
|
+
this.currentConversationId = this.generateConversationId();
|
|
289
|
+
}
|
|
290
|
+
return this.currentConversationId;
|
|
291
|
+
}
|
|
292
|
+
resetConversationContext() {
|
|
293
|
+
this.currentConversationId = this.generateConversationId();
|
|
294
|
+
}
|
|
295
|
+
getProviderCapabilities(providerName) {
|
|
296
|
+
const name = providerName || this.activeProviderName;
|
|
297
|
+
return this.providerCapabilities.get(name);
|
|
298
|
+
}
|
|
299
|
+
compareProviders(provider1, provider2) {
|
|
300
|
+
const cap1 = this.providerCapabilities.get(provider1);
|
|
301
|
+
const cap2 = this.providerCapabilities.get(provider2);
|
|
302
|
+
if (!cap1 || !cap2) {
|
|
303
|
+
throw new Error('Cannot compare providers: capabilities not available');
|
|
304
|
+
}
|
|
305
|
+
return {
|
|
306
|
+
provider1,
|
|
307
|
+
provider2,
|
|
308
|
+
capabilities: {
|
|
309
|
+
[provider1]: cap1,
|
|
310
|
+
[provider2]: cap2,
|
|
311
|
+
},
|
|
312
|
+
compatibility: this.calculateCapabilityCompatibility(cap1, cap2),
|
|
313
|
+
recommendation: this.generateProviderRecommendation(provider1, provider2, cap1, cap2),
|
|
314
|
+
};
|
|
315
|
+
}
|
|
316
|
+
generateProviderRecommendation(provider1, provider2, cap1, cap2) {
|
|
317
|
+
if (cap1.maxTokens > cap2.maxTokens) {
|
|
318
|
+
return `${provider1} supports longer contexts (${cap1.maxTokens} vs ${cap2.maxTokens} tokens)`;
|
|
319
|
+
}
|
|
320
|
+
if (cap1.supportsVision && !cap2.supportsVision) {
|
|
321
|
+
return `${provider1} supports vision capabilities`;
|
|
322
|
+
}
|
|
323
|
+
if (cap1.supportedFormats.length > cap2.supportedFormats.length) {
|
|
324
|
+
return `${provider1} supports more tool formats`;
|
|
325
|
+
}
|
|
326
|
+
return 'Providers have similar capabilities';
|
|
327
|
+
}
|
|
115
328
|
}
|
|
116
329
|
//# sourceMappingURL=ProviderManager.js.map
|