@haisto/opencode-mem 2.14.3-beta.0
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/README.md +165 -0
- package/dist/config.d.ts +62 -0
- package/dist/config.d.ts.map +1 -0
- package/dist/config.js +457 -0
- package/dist/index.d.ts +3 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +486 -0
- package/dist/plugin.d.ts +9 -0
- package/dist/plugin.d.ts.map +1 -0
- package/dist/plugin.js +5 -0
- package/dist/services/ai/ai-provider-factory.d.ts +8 -0
- package/dist/services/ai/ai-provider-factory.d.ts.map +1 -0
- package/dist/services/ai/ai-provider-factory.js +28 -0
- package/dist/services/ai/opencode-provider.d.ts +36 -0
- package/dist/services/ai/opencode-provider.d.ts.map +1 -0
- package/dist/services/ai/opencode-provider.js +92 -0
- package/dist/services/ai/provider-config.d.ts +17 -0
- package/dist/services/ai/provider-config.d.ts.map +1 -0
- package/dist/services/ai/provider-config.js +14 -0
- package/dist/services/ai/providers/anthropic-messages.d.ts +12 -0
- package/dist/services/ai/providers/anthropic-messages.d.ts.map +1 -0
- package/dist/services/ai/providers/anthropic-messages.js +184 -0
- package/dist/services/ai/providers/base-provider.d.ts +25 -0
- package/dist/services/ai/providers/base-provider.d.ts.map +1 -0
- package/dist/services/ai/providers/base-provider.js +23 -0
- package/dist/services/ai/providers/google-gemini.d.ts +16 -0
- package/dist/services/ai/providers/google-gemini.d.ts.map +1 -0
- package/dist/services/ai/providers/google-gemini.js +228 -0
- package/dist/services/ai/providers/openai-chat-completion.d.ts +14 -0
- package/dist/services/ai/providers/openai-chat-completion.d.ts.map +1 -0
- package/dist/services/ai/providers/openai-chat-completion.js +318 -0
- package/dist/services/ai/providers/openai-responses.d.ts +14 -0
- package/dist/services/ai/providers/openai-responses.d.ts.map +1 -0
- package/dist/services/ai/providers/openai-responses.js +182 -0
- package/dist/services/ai/session/ai-session-manager.d.ts +21 -0
- package/dist/services/ai/session/ai-session-manager.d.ts.map +1 -0
- package/dist/services/ai/session/ai-session-manager.js +166 -0
- package/dist/services/ai/session/session-types.d.ts +43 -0
- package/dist/services/ai/session/session-types.d.ts.map +1 -0
- package/dist/services/ai/session/session-types.js +1 -0
- package/dist/services/ai/tools/tool-schema.d.ts +41 -0
- package/dist/services/ai/tools/tool-schema.d.ts.map +1 -0
- package/dist/services/ai/tools/tool-schema.js +24 -0
- package/dist/services/ai/validators/user-profile-validator.d.ts +13 -0
- package/dist/services/ai/validators/user-profile-validator.d.ts.map +1 -0
- package/dist/services/ai/validators/user-profile-validator.js +111 -0
- package/dist/services/api-handlers.d.ts +164 -0
- package/dist/services/api-handlers.d.ts.map +1 -0
- package/dist/services/api-handlers.js +927 -0
- package/dist/services/auto-capture.d.ts +3 -0
- package/dist/services/auto-capture.d.ts.map +1 -0
- package/dist/services/auto-capture.js +309 -0
- package/dist/services/cleanup-service.d.ts +23 -0
- package/dist/services/cleanup-service.d.ts.map +1 -0
- package/dist/services/cleanup-service.js +102 -0
- package/dist/services/client.d.ts +119 -0
- package/dist/services/client.d.ts.map +1 -0
- package/dist/services/client.js +257 -0
- package/dist/services/context.d.ts +11 -0
- package/dist/services/context.d.ts.map +1 -0
- package/dist/services/context.js +34 -0
- package/dist/services/deduplication-service.d.ts +30 -0
- package/dist/services/deduplication-service.d.ts.map +1 -0
- package/dist/services/deduplication-service.js +124 -0
- package/dist/services/embedding.d.ts +15 -0
- package/dist/services/embedding.d.ts.map +1 -0
- package/dist/services/embedding.js +127 -0
- package/dist/services/jsonc.d.ts +7 -0
- package/dist/services/jsonc.d.ts.map +1 -0
- package/dist/services/jsonc.js +76 -0
- package/dist/services/language-detector.d.ts +3 -0
- package/dist/services/language-detector.d.ts.map +1 -0
- package/dist/services/language-detector.js +33 -0
- package/dist/services/logger.d.ts +11 -0
- package/dist/services/logger.d.ts.map +1 -0
- package/dist/services/logger.js +97 -0
- package/dist/services/migration-service.d.ts +42 -0
- package/dist/services/migration-service.d.ts.map +1 -0
- package/dist/services/migration-service.js +250 -0
- package/dist/services/privacy.d.ts +3 -0
- package/dist/services/privacy.d.ts.map +1 -0
- package/dist/services/privacy.js +7 -0
- package/dist/services/secret-resolver.d.ts +2 -0
- package/dist/services/secret-resolver.d.ts.map +1 -0
- package/dist/services/secret-resolver.js +55 -0
- package/dist/services/sqlite/connection-manager.d.ts +13 -0
- package/dist/services/sqlite/connection-manager.d.ts.map +1 -0
- package/dist/services/sqlite/connection-manager.js +74 -0
- package/dist/services/sqlite/shard-manager.d.ts +23 -0
- package/dist/services/sqlite/shard-manager.d.ts.map +1 -0
- package/dist/services/sqlite/shard-manager.js +288 -0
- package/dist/services/sqlite/sqlite-bootstrap.d.ts +2 -0
- package/dist/services/sqlite/sqlite-bootstrap.d.ts.map +1 -0
- package/dist/services/sqlite/sqlite-bootstrap.js +8 -0
- package/dist/services/sqlite/types.d.ts +42 -0
- package/dist/services/sqlite/types.d.ts.map +1 -0
- package/dist/services/sqlite/types.js +1 -0
- package/dist/services/sqlite/vector-search.d.ts +29 -0
- package/dist/services/sqlite/vector-search.d.ts.map +1 -0
- package/dist/services/sqlite/vector-search.js +279 -0
- package/dist/services/tags.d.ts +24 -0
- package/dist/services/tags.d.ts.map +1 -0
- package/dist/services/tags.js +145 -0
- package/dist/services/user-memory-learning.d.ts +3 -0
- package/dist/services/user-memory-learning.d.ts.map +1 -0
- package/dist/services/user-memory-learning.js +235 -0
- package/dist/services/user-profile/profile-context.d.ts +2 -0
- package/dist/services/user-profile/profile-context.d.ts.map +1 -0
- package/dist/services/user-profile/profile-context.js +40 -0
- package/dist/services/user-profile/profile-utils.d.ts +3 -0
- package/dist/services/user-profile/profile-utils.d.ts.map +1 -0
- package/dist/services/user-profile/profile-utils.js +45 -0
- package/dist/services/user-profile/types.d.ts +46 -0
- package/dist/services/user-profile/types.d.ts.map +1 -0
- package/dist/services/user-profile/types.js +1 -0
- package/dist/services/user-profile/user-profile-manager.d.ts +23 -0
- package/dist/services/user-profile/user-profile-manager.d.ts.map +1 -0
- package/dist/services/user-profile/user-profile-manager.js +337 -0
- package/dist/services/user-prompt/user-prompt-manager.d.ts +41 -0
- package/dist/services/user-prompt/user-prompt-manager.d.ts.map +1 -0
- package/dist/services/user-prompt/user-prompt-manager.js +192 -0
- package/dist/services/vector-backends/backend-factory.d.ts +3 -0
- package/dist/services/vector-backends/backend-factory.d.ts.map +1 -0
- package/dist/services/vector-backends/backend-factory.js +104 -0
- package/dist/services/vector-backends/exact-scan-backend.d.ts +39 -0
- package/dist/services/vector-backends/exact-scan-backend.d.ts.map +1 -0
- package/dist/services/vector-backends/exact-scan-backend.js +63 -0
- package/dist/services/vector-backends/types.d.ts +51 -0
- package/dist/services/vector-backends/types.d.ts.map +1 -0
- package/dist/services/vector-backends/types.js +1 -0
- package/dist/services/vector-backends/usearch-backend.d.ts +47 -0
- package/dist/services/vector-backends/usearch-backend.d.ts.map +1 -0
- package/dist/services/vector-backends/usearch-backend.js +174 -0
- package/dist/services/web-server-worker.d.ts +2 -0
- package/dist/services/web-server-worker.d.ts.map +1 -0
- package/dist/services/web-server-worker.js +283 -0
- package/dist/services/web-server.d.ts +31 -0
- package/dist/services/web-server.d.ts.map +1 -0
- package/dist/services/web-server.js +356 -0
- package/dist/types/index.d.ts +19 -0
- package/dist/types/index.d.ts.map +1 -0
- package/dist/types/index.js +1 -0
- package/dist/web/app.d.ts +2 -0
- package/dist/web/app.d.ts.map +1 -0
- package/dist/web/app.js +1238 -0
- package/dist/web/favicon.ico +0 -0
- package/dist/web/i18n.d.ts +2 -0
- package/dist/web/i18n.d.ts.map +1 -0
- package/dist/web/i18n.js +312 -0
- package/dist/web/index.html +293 -0
- package/dist/web/styles.css +1786 -0
- package/package.json +78 -0
|
@@ -0,0 +1,92 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* SDK-based structured output via opencode v2 session.prompt.
|
|
3
|
+
*
|
|
4
|
+
* Replaces the old auth.json/OAuth-juggling flow. Instead of forging requests
|
|
5
|
+
* to provider HTTP endpoints ourselves, we delegate to the running opencode
|
|
6
|
+
* server: it already owns the user's auth (any provider, including
|
|
7
|
+
* github-copilot personal/business), token refresh, and provider routing.
|
|
8
|
+
*
|
|
9
|
+
* Per call we create a transient session, prompt with a JSON schema, then
|
|
10
|
+
* delete the session so it does not pollute the user's TUI session list.
|
|
11
|
+
*/
|
|
12
|
+
import { createOpencodeClient } from "@opencode-ai/sdk/v2/client";
|
|
13
|
+
let _connectedProviders = new Set();
|
|
14
|
+
let _v2Client;
|
|
15
|
+
export function setConnectedProviders(providers) {
|
|
16
|
+
_connectedProviders = new Set(providers);
|
|
17
|
+
}
|
|
18
|
+
export function isProviderConnected(providerName) {
|
|
19
|
+
return _connectedProviders.has(providerName);
|
|
20
|
+
}
|
|
21
|
+
export function setV2Client(client) {
|
|
22
|
+
_v2Client = client;
|
|
23
|
+
}
|
|
24
|
+
export function getV2Client() {
|
|
25
|
+
return _v2Client;
|
|
26
|
+
}
|
|
27
|
+
export function createV2Client(serverUrl) {
|
|
28
|
+
const baseUrl = typeof serverUrl === "string" ? serverUrl : serverUrl.toString();
|
|
29
|
+
return createOpencodeClient({ baseUrl });
|
|
30
|
+
}
|
|
31
|
+
/**
|
|
32
|
+
* Generate one structured-output completion via opencode's v2 API.
|
|
33
|
+
* Throws on: session.create failure, prompt failure, AssistantMessage.error
|
|
34
|
+
* (StructuredOutputError / ApiError / ...), missing `info.structured`,
|
|
35
|
+
* or final Zod validation failure.
|
|
36
|
+
*/
|
|
37
|
+
export async function generateStructuredOutput(opts) {
|
|
38
|
+
const { client, providerID, modelID, systemPrompt, userPrompt, schema, directory, retryCount } = opts;
|
|
39
|
+
// zod v4 exposes JSON Schema export natively (instance `.toJSONSchema()`
|
|
40
|
+
// and global `z.toJSONSchema()`); we prefer instance, fall back to global.
|
|
41
|
+
// This avoids pulling in a separate `zod-to-json-schema` dependency.
|
|
42
|
+
const jsonSchema = schema.toJSONSchema?.() ?? (await import("zod")).z.toJSONSchema(schema);
|
|
43
|
+
const created = await client.session.create({
|
|
44
|
+
title: "opencode-mem capture",
|
|
45
|
+
...(directory ? { directory } : {}),
|
|
46
|
+
});
|
|
47
|
+
const sessionID = created?.data?.id;
|
|
48
|
+
if (!sessionID) {
|
|
49
|
+
throw new Error("opencode-mem: session.create returned no session id; cannot generate structured output");
|
|
50
|
+
}
|
|
51
|
+
try {
|
|
52
|
+
const promptResult = await client.session.prompt({
|
|
53
|
+
sessionID,
|
|
54
|
+
...(directory ? { directory } : {}),
|
|
55
|
+
model: { providerID, modelID },
|
|
56
|
+
system: systemPrompt,
|
|
57
|
+
parts: [{ type: "text", text: userPrompt }],
|
|
58
|
+
format: {
|
|
59
|
+
type: "json_schema",
|
|
60
|
+
schema: jsonSchema,
|
|
61
|
+
...(retryCount !== undefined ? { retryCount } : {}),
|
|
62
|
+
},
|
|
63
|
+
noReply: true,
|
|
64
|
+
});
|
|
65
|
+
const data = promptResult.data;
|
|
66
|
+
const info = data?.info;
|
|
67
|
+
if (!info) {
|
|
68
|
+
throw new Error("opencode-mem: prompt response missing `info`");
|
|
69
|
+
}
|
|
70
|
+
if (info.error) {
|
|
71
|
+
const msg = info.error.data?.message ?? info.error.name;
|
|
72
|
+
throw new Error(`opencode-mem: opencode reported ${info.error.name}: ${msg}`);
|
|
73
|
+
}
|
|
74
|
+
if (info.structured === undefined || info.structured === null) {
|
|
75
|
+
throw new Error("opencode-mem: opencode returned no structured output (info.structured was empty)");
|
|
76
|
+
}
|
|
77
|
+
return schema.parse(info.structured);
|
|
78
|
+
}
|
|
79
|
+
finally {
|
|
80
|
+
// Best-effort: leaving a transient session behind is cosmetic, not
|
|
81
|
+
// worth failing a successful capture if cleanup itself errors.
|
|
82
|
+
try {
|
|
83
|
+
await client.session.delete({
|
|
84
|
+
sessionID,
|
|
85
|
+
...(directory ? { directory } : {}),
|
|
86
|
+
});
|
|
87
|
+
}
|
|
88
|
+
catch {
|
|
89
|
+
// intentionally swallowed
|
|
90
|
+
}
|
|
91
|
+
}
|
|
92
|
+
}
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
import type { ProviderConfig } from "./providers/base-provider.js";
|
|
2
|
+
interface MemoryProviderRuntimeConfig {
|
|
3
|
+
memoryModel?: string;
|
|
4
|
+
memoryApiUrl?: string;
|
|
5
|
+
memoryApiKey?: string;
|
|
6
|
+
memoryTemperature?: number | false;
|
|
7
|
+
memoryExtraParams?: Record<string, unknown>;
|
|
8
|
+
autoCaptureMaxIterations?: number;
|
|
9
|
+
autoCaptureIterationTimeout?: number;
|
|
10
|
+
}
|
|
11
|
+
interface ProviderConfigOverrides {
|
|
12
|
+
maxIterations?: number;
|
|
13
|
+
iterationTimeout?: number;
|
|
14
|
+
}
|
|
15
|
+
export declare function buildMemoryProviderConfig(config: MemoryProviderRuntimeConfig, overrides?: ProviderConfigOverrides): ProviderConfig;
|
|
16
|
+
export {};
|
|
17
|
+
//# sourceMappingURL=provider-config.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"provider-config.d.ts","sourceRoot":"","sources":["../../../src/services/ai/provider-config.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,8BAA8B,CAAC;AAEnE,UAAU,2BAA2B;IACnC,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,YAAY,CAAC,EAAE,MAAM,CAAC;IACtB,YAAY,CAAC,EAAE,MAAM,CAAC;IACtB,iBAAiB,CAAC,EAAE,MAAM,GAAG,KAAK,CAAC;IACnC,iBAAiB,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;IAC5C,wBAAwB,CAAC,EAAE,MAAM,CAAC;IAClC,2BAA2B,CAAC,EAAE,MAAM,CAAC;CACtC;AAED,UAAU,uBAAuB;IAC/B,aAAa,CAAC,EAAE,MAAM,CAAC;IACvB,gBAAgB,CAAC,EAAE,MAAM,CAAC;CAC3B;AAED,wBAAgB,yBAAyB,CACvC,MAAM,EAAE,2BAA2B,EACnC,SAAS,GAAE,uBAA4B,GACtC,cAAc,CAchB"}
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
export function buildMemoryProviderConfig(config, overrides = {}) {
|
|
2
|
+
if (!config.memoryModel || !config.memoryApiUrl) {
|
|
3
|
+
throw new Error("External API not configured for memory provider");
|
|
4
|
+
}
|
|
5
|
+
return {
|
|
6
|
+
model: config.memoryModel,
|
|
7
|
+
apiUrl: config.memoryApiUrl,
|
|
8
|
+
apiKey: config.memoryApiKey,
|
|
9
|
+
memoryTemperature: config.memoryTemperature,
|
|
10
|
+
extraParams: config.memoryExtraParams,
|
|
11
|
+
maxIterations: overrides.maxIterations ?? config.autoCaptureMaxIterations,
|
|
12
|
+
iterationTimeout: overrides.iterationTimeout ?? config.autoCaptureIterationTimeout,
|
|
13
|
+
};
|
|
14
|
+
}
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
import { BaseAIProvider, type ToolCallResult } from "./base-provider.js";
|
|
2
|
+
import { AISessionManager } from "../session/ai-session-manager.js";
|
|
3
|
+
import { type ChatCompletionTool } from "../tools/tool-schema.js";
|
|
4
|
+
export declare class AnthropicMessagesProvider extends BaseAIProvider {
|
|
5
|
+
private aiSessionManager;
|
|
6
|
+
constructor(config: any, aiSessionManager: AISessionManager);
|
|
7
|
+
getProviderName(): string;
|
|
8
|
+
supportsSession(): boolean;
|
|
9
|
+
executeToolCall(systemPrompt: string, userPrompt: string, toolSchema: ChatCompletionTool, sessionId: string): Promise<ToolCallResult>;
|
|
10
|
+
private extractToolUse;
|
|
11
|
+
}
|
|
12
|
+
//# sourceMappingURL=anthropic-messages.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"anthropic-messages.d.ts","sourceRoot":"","sources":["../../../../src/services/ai/providers/anthropic-messages.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,cAAc,EAAE,KAAK,cAAc,EAAE,MAAM,oBAAoB,CAAC;AACzE,OAAO,EAAE,gBAAgB,EAAE,MAAM,kCAAkC,CAAC;AACpE,OAAO,EAAuB,KAAK,kBAAkB,EAAE,MAAM,yBAAyB,CAAC;AA4BvF,qBAAa,yBAA0B,SAAQ,cAAc;IAC3D,OAAO,CAAC,gBAAgB,CAAmB;gBAE/B,MAAM,EAAE,GAAG,EAAE,gBAAgB,EAAE,gBAAgB;IAK3D,eAAe,IAAI,MAAM;IAIzB,eAAe,IAAI,OAAO;IAIpB,eAAe,CACnB,YAAY,EAAE,MAAM,EACpB,UAAU,EAAE,MAAM,EAClB,UAAU,EAAE,kBAAkB,EAC9B,SAAS,EAAE,MAAM,GAChB,OAAO,CAAC,cAAc,CAAC;IAoL1B,OAAO,CAAC,cAAc;CAavB"}
|
|
@@ -0,0 +1,184 @@
|
|
|
1
|
+
import { BaseAIProvider } from "./base-provider.js";
|
|
2
|
+
import { AISessionManager } from "../session/ai-session-manager.js";
|
|
3
|
+
import { ToolSchemaConverter } from "../tools/tool-schema.js";
|
|
4
|
+
import { log } from "../../logger.js";
|
|
5
|
+
import { UserProfileValidator } from "../validators/user-profile-validator.js";
|
|
6
|
+
export class AnthropicMessagesProvider extends BaseAIProvider {
|
|
7
|
+
aiSessionManager;
|
|
8
|
+
constructor(config, aiSessionManager) {
|
|
9
|
+
super(config);
|
|
10
|
+
this.aiSessionManager = aiSessionManager;
|
|
11
|
+
}
|
|
12
|
+
getProviderName() {
|
|
13
|
+
return "anthropic";
|
|
14
|
+
}
|
|
15
|
+
supportsSession() {
|
|
16
|
+
return true;
|
|
17
|
+
}
|
|
18
|
+
async executeToolCall(systemPrompt, userPrompt, toolSchema, sessionId) {
|
|
19
|
+
let session = this.aiSessionManager.getSession(sessionId, "anthropic");
|
|
20
|
+
if (!session) {
|
|
21
|
+
session = this.aiSessionManager.createSession({
|
|
22
|
+
provider: "anthropic",
|
|
23
|
+
sessionId,
|
|
24
|
+
metadata: { systemPrompt },
|
|
25
|
+
});
|
|
26
|
+
}
|
|
27
|
+
const storedMessages = this.aiSessionManager.getMessages(session.id);
|
|
28
|
+
const messages = [];
|
|
29
|
+
for (const msg of storedMessages) {
|
|
30
|
+
if (msg.role === "system")
|
|
31
|
+
continue;
|
|
32
|
+
const anthropicMsg = {
|
|
33
|
+
role: msg.role,
|
|
34
|
+
content: msg.contentBlocks || msg.content,
|
|
35
|
+
};
|
|
36
|
+
messages.push(anthropicMsg);
|
|
37
|
+
}
|
|
38
|
+
const userSequence = this.aiSessionManager.getLastSequence(session.id) + 1;
|
|
39
|
+
this.aiSessionManager.addMessage({
|
|
40
|
+
aiSessionId: session.id,
|
|
41
|
+
sequence: userSequence,
|
|
42
|
+
role: "user",
|
|
43
|
+
content: userPrompt,
|
|
44
|
+
});
|
|
45
|
+
messages.push({ role: "user", content: userPrompt });
|
|
46
|
+
let iterations = 0;
|
|
47
|
+
const maxIterations = this.config.maxIterations ?? 5;
|
|
48
|
+
const iterationTimeout = this.config.iterationTimeout ?? 30000;
|
|
49
|
+
while (iterations < maxIterations) {
|
|
50
|
+
iterations++;
|
|
51
|
+
const controller = new AbortController();
|
|
52
|
+
const timeout = setTimeout(() => controller.abort(), iterationTimeout);
|
|
53
|
+
try {
|
|
54
|
+
const tool = ToolSchemaConverter.toAnthropic(toolSchema);
|
|
55
|
+
const requestBody = {
|
|
56
|
+
model: this.config.model,
|
|
57
|
+
max_tokens: this.config.maxTokens ?? 4096,
|
|
58
|
+
system: systemPrompt,
|
|
59
|
+
messages,
|
|
60
|
+
tools: [tool],
|
|
61
|
+
};
|
|
62
|
+
const headers = {
|
|
63
|
+
"Content-Type": "application/json",
|
|
64
|
+
"anthropic-version": "2023-06-01",
|
|
65
|
+
};
|
|
66
|
+
if (this.config.apiKey) {
|
|
67
|
+
headers["x-api-key"] = this.config.apiKey;
|
|
68
|
+
}
|
|
69
|
+
const response = await fetch(`${this.config.apiUrl}/messages`, {
|
|
70
|
+
method: "POST",
|
|
71
|
+
headers,
|
|
72
|
+
body: JSON.stringify(requestBody),
|
|
73
|
+
signal: controller.signal,
|
|
74
|
+
});
|
|
75
|
+
clearTimeout(timeout);
|
|
76
|
+
if (!response.ok) {
|
|
77
|
+
const errorText = await response.text().catch(() => response.statusText);
|
|
78
|
+
log("Anthropic Messages API error", {
|
|
79
|
+
provider: this.getProviderName(),
|
|
80
|
+
model: this.config.model,
|
|
81
|
+
status: response.status,
|
|
82
|
+
error: errorText,
|
|
83
|
+
iteration: iterations,
|
|
84
|
+
});
|
|
85
|
+
return {
|
|
86
|
+
success: false,
|
|
87
|
+
error: `API error: ${response.status} - ${errorText}`,
|
|
88
|
+
iterations,
|
|
89
|
+
};
|
|
90
|
+
}
|
|
91
|
+
const data = (await response.json());
|
|
92
|
+
const assistantSequence = this.aiSessionManager.getLastSequence(session.id) + 1;
|
|
93
|
+
this.aiSessionManager.addMessage({
|
|
94
|
+
aiSessionId: session.id,
|
|
95
|
+
sequence: assistantSequence,
|
|
96
|
+
role: "assistant",
|
|
97
|
+
content: JSON.stringify(data.content),
|
|
98
|
+
contentBlocks: data.content,
|
|
99
|
+
});
|
|
100
|
+
messages.push({
|
|
101
|
+
role: "assistant",
|
|
102
|
+
content: data.content,
|
|
103
|
+
});
|
|
104
|
+
const toolUse = this.extractToolUse(data, toolSchema.function.name);
|
|
105
|
+
if (toolUse) {
|
|
106
|
+
try {
|
|
107
|
+
const result = UserProfileValidator.validate(toolUse);
|
|
108
|
+
if (!result.valid) {
|
|
109
|
+
throw new Error(result.errors.join(", "));
|
|
110
|
+
}
|
|
111
|
+
return {
|
|
112
|
+
success: true,
|
|
113
|
+
data: result.data,
|
|
114
|
+
iterations,
|
|
115
|
+
};
|
|
116
|
+
}
|
|
117
|
+
catch (validationError) {
|
|
118
|
+
const errorStack = validationError instanceof Error ? validationError.stack : undefined;
|
|
119
|
+
log("Anthropic tool response validation failed", {
|
|
120
|
+
error: String(validationError),
|
|
121
|
+
stack: errorStack,
|
|
122
|
+
errorType: validationError instanceof Error
|
|
123
|
+
? validationError.constructor.name
|
|
124
|
+
: typeof validationError,
|
|
125
|
+
toolName: toolSchema.function.name,
|
|
126
|
+
iteration: iterations,
|
|
127
|
+
rawData: JSON.stringify(toolUse).slice(0, 500),
|
|
128
|
+
});
|
|
129
|
+
return {
|
|
130
|
+
success: false,
|
|
131
|
+
error: `Validation failed: ${String(validationError)}`,
|
|
132
|
+
iterations,
|
|
133
|
+
};
|
|
134
|
+
}
|
|
135
|
+
}
|
|
136
|
+
if (data.stop_reason === "end_turn") {
|
|
137
|
+
const retrySequence = this.aiSessionManager.getLastSequence(session.id) + 1;
|
|
138
|
+
const retryPrompt = "Please use the save_memories tool to extract and save the memories from the conversation as instructed.";
|
|
139
|
+
this.aiSessionManager.addMessage({
|
|
140
|
+
aiSessionId: session.id,
|
|
141
|
+
sequence: retrySequence,
|
|
142
|
+
role: "user",
|
|
143
|
+
content: retryPrompt,
|
|
144
|
+
});
|
|
145
|
+
messages.push({ role: "user", content: retryPrompt });
|
|
146
|
+
}
|
|
147
|
+
else {
|
|
148
|
+
break;
|
|
149
|
+
}
|
|
150
|
+
}
|
|
151
|
+
catch (error) {
|
|
152
|
+
clearTimeout(timeout);
|
|
153
|
+
if (error instanceof Error && error.name === "AbortError") {
|
|
154
|
+
return {
|
|
155
|
+
success: false,
|
|
156
|
+
error: `API request timeout (${this.config.iterationTimeout}ms)`,
|
|
157
|
+
iterations,
|
|
158
|
+
};
|
|
159
|
+
}
|
|
160
|
+
return {
|
|
161
|
+
success: false,
|
|
162
|
+
error: String(error),
|
|
163
|
+
iterations,
|
|
164
|
+
};
|
|
165
|
+
}
|
|
166
|
+
}
|
|
167
|
+
return {
|
|
168
|
+
success: false,
|
|
169
|
+
error: `Max iterations (${maxIterations}) reached without tool use`,
|
|
170
|
+
iterations,
|
|
171
|
+
};
|
|
172
|
+
}
|
|
173
|
+
extractToolUse(data, expectedToolName) {
|
|
174
|
+
if (!data.content || !Array.isArray(data.content)) {
|
|
175
|
+
return null;
|
|
176
|
+
}
|
|
177
|
+
for (const block of data.content) {
|
|
178
|
+
if (block.type === "tool_use" && block.name === expectedToolName && block.input) {
|
|
179
|
+
return block.input;
|
|
180
|
+
}
|
|
181
|
+
}
|
|
182
|
+
return null;
|
|
183
|
+
}
|
|
184
|
+
}
|
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
export interface ToolCallResult {
|
|
2
|
+
success: boolean;
|
|
3
|
+
data?: any;
|
|
4
|
+
error?: string;
|
|
5
|
+
iterations?: number;
|
|
6
|
+
}
|
|
7
|
+
export interface ProviderConfig {
|
|
8
|
+
model: string;
|
|
9
|
+
apiUrl: string;
|
|
10
|
+
apiKey?: string;
|
|
11
|
+
maxIterations?: number;
|
|
12
|
+
iterationTimeout?: number;
|
|
13
|
+
maxTokens?: number;
|
|
14
|
+
memoryTemperature?: number | false;
|
|
15
|
+
extraParams?: Record<string, unknown>;
|
|
16
|
+
}
|
|
17
|
+
export declare function applySafeExtraParams(requestBody: Record<string, any>, extraParams: Record<string, unknown>): void;
|
|
18
|
+
export declare abstract class BaseAIProvider {
|
|
19
|
+
protected config: ProviderConfig;
|
|
20
|
+
constructor(config: ProviderConfig);
|
|
21
|
+
abstract executeToolCall(systemPrompt: string, userPrompt: string, toolSchema: any, sessionId: string): Promise<ToolCallResult>;
|
|
22
|
+
abstract getProviderName(): string;
|
|
23
|
+
abstract supportsSession(): boolean;
|
|
24
|
+
}
|
|
25
|
+
//# sourceMappingURL=base-provider.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"base-provider.d.ts","sourceRoot":"","sources":["../../../../src/services/ai/providers/base-provider.ts"],"names":[],"mappings":"AAAA,MAAM,WAAW,cAAc;IAC7B,OAAO,EAAE,OAAO,CAAC;IACjB,IAAI,CAAC,EAAE,GAAG,CAAC;IACX,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,UAAU,CAAC,EAAE,MAAM,CAAC;CACrB;AAED,MAAM,WAAW,cAAc;IAC7B,KAAK,EAAE,MAAM,CAAC;IACd,MAAM,EAAE,MAAM,CAAC;IACf,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,aAAa,CAAC,EAAE,MAAM,CAAC;IACvB,gBAAgB,CAAC,EAAE,MAAM,CAAC;IAC1B,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,iBAAiB,CAAC,EAAE,MAAM,GAAG,KAAK,CAAC;IACnC,WAAW,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;CACvC;AAaD,wBAAgB,oBAAoB,CAClC,WAAW,EAAE,MAAM,CAAC,MAAM,EAAE,GAAG,CAAC,EAChC,WAAW,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GACnC,IAAI,CAMN;AAED,8BAAsB,cAAc;IAClC,SAAS,CAAC,MAAM,EAAE,cAAc,CAAC;gBAErB,MAAM,EAAE,cAAc;IAIlC,QAAQ,CAAC,eAAe,CACtB,YAAY,EAAE,MAAM,EACpB,UAAU,EAAE,MAAM,EAClB,UAAU,EAAE,GAAG,EACf,SAAS,EAAE,MAAM,GAChB,OAAO,CAAC,cAAc,CAAC;IAE1B,QAAQ,CAAC,eAAe,IAAI,MAAM;IAElC,QAAQ,CAAC,eAAe,IAAI,OAAO;CACpC"}
|
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
const PROTECTED_KEYS = new Set([
|
|
2
|
+
"model",
|
|
3
|
+
"messages",
|
|
4
|
+
"tools",
|
|
5
|
+
"tool_choice",
|
|
6
|
+
"temperature",
|
|
7
|
+
"input",
|
|
8
|
+
"instructions",
|
|
9
|
+
"conversation",
|
|
10
|
+
]);
|
|
11
|
+
export function applySafeExtraParams(requestBody, extraParams) {
|
|
12
|
+
for (const [key, value] of Object.entries(extraParams)) {
|
|
13
|
+
if (!PROTECTED_KEYS.has(key)) {
|
|
14
|
+
requestBody[key] = value;
|
|
15
|
+
}
|
|
16
|
+
}
|
|
17
|
+
}
|
|
18
|
+
export class BaseAIProvider {
|
|
19
|
+
config;
|
|
20
|
+
constructor(config) {
|
|
21
|
+
this.config = config;
|
|
22
|
+
}
|
|
23
|
+
}
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
import { BaseAIProvider, type ToolCallResult } from "./base-provider.js";
|
|
2
|
+
import { AISessionManager } from "../session/ai-session-manager.js";
|
|
3
|
+
import type { ChatCompletionTool } from "../tools/tool-schema.js";
|
|
4
|
+
/**
|
|
5
|
+
* Google Gemini Provider
|
|
6
|
+
* Supports Google's Gemini models (e.g. gemini-1.5-flash) via Google AI Studio API.
|
|
7
|
+
*/
|
|
8
|
+
export declare class GoogleGeminiProvider extends BaseAIProvider {
|
|
9
|
+
private aiSessionManager;
|
|
10
|
+
constructor(config: any, aiSessionManager: AISessionManager);
|
|
11
|
+
getProviderName(): string;
|
|
12
|
+
supportsSession(): boolean;
|
|
13
|
+
private addToolResponse;
|
|
14
|
+
executeToolCall(systemPrompt: string, userPrompt: string, toolSchema: ChatCompletionTool, sessionId: string): Promise<ToolCallResult>;
|
|
15
|
+
}
|
|
16
|
+
//# sourceMappingURL=google-gemini.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"google-gemini.d.ts","sourceRoot":"","sources":["../../../../src/services/ai/providers/google-gemini.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,cAAc,EAAE,KAAK,cAAc,EAAE,MAAM,oBAAoB,CAAC;AACzE,OAAO,EAAE,gBAAgB,EAAE,MAAM,kCAAkC,CAAC;AACpE,OAAO,KAAK,EAAE,kBAAkB,EAAE,MAAM,yBAAyB,CAAC;AAIlE;;;GAGG;AACH,qBAAa,oBAAqB,SAAQ,cAAc;IACtD,OAAO,CAAC,gBAAgB,CAAmB;gBAE/B,MAAM,EAAE,GAAG,EAAE,gBAAgB,EAAE,gBAAgB;IAK3D,eAAe,IAAI,MAAM;IAIzB,eAAe,IAAI,OAAO;IAI1B,OAAO,CAAC,eAAe;IA4BjB,eAAe,CACnB,YAAY,EAAE,MAAM,EACpB,UAAU,EAAE,MAAM,EAClB,UAAU,EAAE,kBAAkB,EAC9B,SAAS,EAAE,MAAM,GAChB,OAAO,CAAC,cAAc,CAAC;CA2N3B"}
|
|
@@ -0,0 +1,228 @@
|
|
|
1
|
+
import { BaseAIProvider } from "./base-provider.js";
|
|
2
|
+
import { AISessionManager } from "../session/ai-session-manager.js";
|
|
3
|
+
import { log } from "../../logger.js";
|
|
4
|
+
import { UserProfileValidator } from "../validators/user-profile-validator.js";
|
|
5
|
+
/**
|
|
6
|
+
* Google Gemini Provider
|
|
7
|
+
* Supports Google's Gemini models (e.g. gemini-1.5-flash) via Google AI Studio API.
|
|
8
|
+
*/
|
|
9
|
+
export class GoogleGeminiProvider extends BaseAIProvider {
|
|
10
|
+
aiSessionManager;
|
|
11
|
+
constructor(config, aiSessionManager) {
|
|
12
|
+
super(config);
|
|
13
|
+
this.aiSessionManager = aiSessionManager;
|
|
14
|
+
}
|
|
15
|
+
getProviderName() {
|
|
16
|
+
return "google-gemini";
|
|
17
|
+
}
|
|
18
|
+
supportsSession() {
|
|
19
|
+
return true;
|
|
20
|
+
}
|
|
21
|
+
addToolResponse(sessionId, messages, toolCallId, content) {
|
|
22
|
+
const sequence = this.aiSessionManager.getLastSequence(sessionId) + 1;
|
|
23
|
+
this.aiSessionManager.addMessage({
|
|
24
|
+
aiSessionId: sessionId,
|
|
25
|
+
sequence,
|
|
26
|
+
role: "tool",
|
|
27
|
+
content,
|
|
28
|
+
toolCallId,
|
|
29
|
+
});
|
|
30
|
+
// Gemini tool response format
|
|
31
|
+
messages.push({
|
|
32
|
+
role: "function",
|
|
33
|
+
parts: [
|
|
34
|
+
{
|
|
35
|
+
functionResponse: {
|
|
36
|
+
name: toolCallId.split(":")[0], // Gemini expects the name of the function
|
|
37
|
+
response: JSON.parse(content),
|
|
38
|
+
},
|
|
39
|
+
},
|
|
40
|
+
],
|
|
41
|
+
});
|
|
42
|
+
}
|
|
43
|
+
async executeToolCall(systemPrompt, userPrompt, toolSchema, sessionId) {
|
|
44
|
+
let session = this.aiSessionManager.getSession(sessionId, "google-gemini");
|
|
45
|
+
if (!session) {
|
|
46
|
+
session = this.aiSessionManager.createSession({
|
|
47
|
+
provider: "google-gemini",
|
|
48
|
+
sessionId,
|
|
49
|
+
});
|
|
50
|
+
}
|
|
51
|
+
const existingMessages = this.aiSessionManager.getMessages(session.id);
|
|
52
|
+
const contents = [];
|
|
53
|
+
// System instruction is separate in Gemini API
|
|
54
|
+
const geminiSystemInstruction = {
|
|
55
|
+
parts: [{ text: systemPrompt }],
|
|
56
|
+
};
|
|
57
|
+
// Convert existing messages to Gemini format
|
|
58
|
+
for (const msg of existingMessages) {
|
|
59
|
+
if (msg.role === "system")
|
|
60
|
+
continue; // Skip system as it's passed separately
|
|
61
|
+
const role = msg.role === "assistant" ? "model" : "user";
|
|
62
|
+
const parts = [];
|
|
63
|
+
if (msg.content) {
|
|
64
|
+
parts.push({ text: msg.content });
|
|
65
|
+
}
|
|
66
|
+
if (msg.toolCalls) {
|
|
67
|
+
for (const tc of msg.toolCalls) {
|
|
68
|
+
parts.push({
|
|
69
|
+
functionCall: {
|
|
70
|
+
name: tc.function.name,
|
|
71
|
+
args: JSON.parse(tc.function.arguments),
|
|
72
|
+
},
|
|
73
|
+
});
|
|
74
|
+
}
|
|
75
|
+
}
|
|
76
|
+
if (msg.role === "tool") {
|
|
77
|
+
contents.push({
|
|
78
|
+
role: "function",
|
|
79
|
+
parts: [
|
|
80
|
+
{
|
|
81
|
+
functionResponse: {
|
|
82
|
+
name: (msg.toolCallId || "").split(":")[0],
|
|
83
|
+
response: JSON.parse(msg.content),
|
|
84
|
+
},
|
|
85
|
+
},
|
|
86
|
+
],
|
|
87
|
+
});
|
|
88
|
+
continue;
|
|
89
|
+
}
|
|
90
|
+
contents.push({ role, parts });
|
|
91
|
+
}
|
|
92
|
+
if (contents.length === 0 || contents[contents.length - 1].role !== "user") {
|
|
93
|
+
const userSequence = this.aiSessionManager.getLastSequence(session.id) + 1;
|
|
94
|
+
this.aiSessionManager.addMessage({
|
|
95
|
+
aiSessionId: session.id,
|
|
96
|
+
sequence: userSequence,
|
|
97
|
+
role: "user",
|
|
98
|
+
content: userPrompt,
|
|
99
|
+
});
|
|
100
|
+
contents.push({ role: "user", parts: [{ text: userPrompt }] });
|
|
101
|
+
}
|
|
102
|
+
let iterations = 0;
|
|
103
|
+
const maxIterations = this.config.maxIterations ?? 5;
|
|
104
|
+
const iterationTimeout = this.config.iterationTimeout ?? 30000;
|
|
105
|
+
// Gemini API expects the tool name as a function declaration
|
|
106
|
+
const tools = [
|
|
107
|
+
{
|
|
108
|
+
functionDeclarations: [
|
|
109
|
+
{
|
|
110
|
+
name: toolSchema.function.name,
|
|
111
|
+
description: toolSchema.function.description,
|
|
112
|
+
parameters: toolSchema.function.parameters,
|
|
113
|
+
},
|
|
114
|
+
],
|
|
115
|
+
},
|
|
116
|
+
];
|
|
117
|
+
while (iterations < maxIterations) {
|
|
118
|
+
iterations++;
|
|
119
|
+
const controller = new AbortController();
|
|
120
|
+
const timeout = setTimeout(() => controller.abort(), iterationTimeout);
|
|
121
|
+
try {
|
|
122
|
+
const baseUrl = this.config.apiUrl || "https://generativelanguage.googleapis.com/v1beta";
|
|
123
|
+
const url = `${baseUrl}/models/${this.config.model}:generateContent?key=${this.config.apiKey}`;
|
|
124
|
+
const requestBody = {
|
|
125
|
+
contents,
|
|
126
|
+
systemInstruction: geminiSystemInstruction,
|
|
127
|
+
tools,
|
|
128
|
+
toolConfig: {
|
|
129
|
+
functionCallingConfig: {
|
|
130
|
+
mode: "ANY", // Force function calling
|
|
131
|
+
allowedFunctionNames: [toolSchema.function.name],
|
|
132
|
+
},
|
|
133
|
+
},
|
|
134
|
+
generationConfig: {
|
|
135
|
+
temperature: this.config.memoryTemperature ?? 0.3,
|
|
136
|
+
},
|
|
137
|
+
};
|
|
138
|
+
const response = await fetch(url, {
|
|
139
|
+
method: "POST",
|
|
140
|
+
headers: { "Content-Type": "application/json" },
|
|
141
|
+
body: JSON.stringify(requestBody),
|
|
142
|
+
signal: controller.signal,
|
|
143
|
+
});
|
|
144
|
+
clearTimeout(timeout);
|
|
145
|
+
if (!response.ok) {
|
|
146
|
+
const errorText = await response.text().catch(() => response.statusText);
|
|
147
|
+
log("Gemini API error", {
|
|
148
|
+
provider: this.getProviderName(),
|
|
149
|
+
model: this.config.model,
|
|
150
|
+
status: response.status,
|
|
151
|
+
error: errorText,
|
|
152
|
+
iteration: iterations,
|
|
153
|
+
});
|
|
154
|
+
return {
|
|
155
|
+
success: false,
|
|
156
|
+
error: `Gemini API error: ${response.status} - ${errorText}`,
|
|
157
|
+
iterations,
|
|
158
|
+
};
|
|
159
|
+
}
|
|
160
|
+
const data = (await response.json());
|
|
161
|
+
const candidate = data.candidates?.[0];
|
|
162
|
+
if (!candidate || !candidate.content) {
|
|
163
|
+
return { success: false, error: "Invalid Gemini API response format", iterations };
|
|
164
|
+
}
|
|
165
|
+
const modelMsg = candidate.content;
|
|
166
|
+
const assistantSequence = this.aiSessionManager.getLastSequence(session.id) + 1;
|
|
167
|
+
// Map Gemini response back to our internal message format
|
|
168
|
+
const assistantMsg = {
|
|
169
|
+
aiSessionId: session.id,
|
|
170
|
+
sequence: assistantSequence,
|
|
171
|
+
role: "assistant",
|
|
172
|
+
content: "",
|
|
173
|
+
toolCalls: [],
|
|
174
|
+
};
|
|
175
|
+
for (const part of modelMsg.parts) {
|
|
176
|
+
if (part.text)
|
|
177
|
+
assistantMsg.content += part.text;
|
|
178
|
+
if (part.functionCall) {
|
|
179
|
+
assistantMsg.toolCalls.push({
|
|
180
|
+
id: `${part.functionCall.name}:${Date.now()}`,
|
|
181
|
+
type: "function",
|
|
182
|
+
function: {
|
|
183
|
+
name: part.functionCall.name,
|
|
184
|
+
arguments: JSON.stringify(part.functionCall.args),
|
|
185
|
+
},
|
|
186
|
+
});
|
|
187
|
+
}
|
|
188
|
+
}
|
|
189
|
+
this.aiSessionManager.addMessage(assistantMsg);
|
|
190
|
+
contents.push(modelMsg);
|
|
191
|
+
if (assistantMsg.toolCalls.length > 0) {
|
|
192
|
+
for (const toolCall of assistantMsg.toolCalls) {
|
|
193
|
+
if (toolCall.function.name === toolSchema.function.name) {
|
|
194
|
+
try {
|
|
195
|
+
const parsed = JSON.parse(toolCall.function.arguments);
|
|
196
|
+
const result = UserProfileValidator.validate(parsed);
|
|
197
|
+
if (!result.valid)
|
|
198
|
+
throw new Error(result.errors.join(", "));
|
|
199
|
+
this.addToolResponse(session.id, contents, toolCall.id, JSON.stringify({ success: true }));
|
|
200
|
+
return { success: true, data: result.data, iterations };
|
|
201
|
+
}
|
|
202
|
+
catch (validationError) {
|
|
203
|
+
const errorMessage = `Validation failed: ${String(validationError)}`;
|
|
204
|
+
this.addToolResponse(session.id, contents, toolCall.id, JSON.stringify({ success: false, error: errorMessage }));
|
|
205
|
+
return { success: false, error: errorMessage, iterations };
|
|
206
|
+
}
|
|
207
|
+
}
|
|
208
|
+
}
|
|
209
|
+
}
|
|
210
|
+
// Retry if no tool call was made
|
|
211
|
+
const retryPrompt = "Please use the save_memories tool as instructed.";
|
|
212
|
+
const retrySequence = this.aiSessionManager.getLastSequence(session.id) + 1;
|
|
213
|
+
this.aiSessionManager.addMessage({
|
|
214
|
+
aiSessionId: session.id,
|
|
215
|
+
sequence: retrySequence,
|
|
216
|
+
role: "user",
|
|
217
|
+
content: retryPrompt,
|
|
218
|
+
});
|
|
219
|
+
contents.push({ role: "user", parts: [{ text: retryPrompt }] });
|
|
220
|
+
}
|
|
221
|
+
catch (error) {
|
|
222
|
+
clearTimeout(timeout);
|
|
223
|
+
return { success: false, error: String(error), iterations };
|
|
224
|
+
}
|
|
225
|
+
}
|
|
226
|
+
return { success: false, error: `Max iterations (${maxIterations}) reached`, iterations };
|
|
227
|
+
}
|
|
228
|
+
}
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
import { BaseAIProvider, type ProviderConfig, type ToolCallResult } from "./base-provider.js";
|
|
2
|
+
import type { AISessionManager } from "../session/ai-session-manager.js";
|
|
3
|
+
import type { AIMessage } from "../session/session-types.js";
|
|
4
|
+
import type { ChatCompletionTool } from "../tools/tool-schema.js";
|
|
5
|
+
export declare class OpenAIChatCompletionProvider extends BaseAIProvider {
|
|
6
|
+
private readonly aiSessionManager;
|
|
7
|
+
constructor(config: ProviderConfig, aiSessionManager: AISessionManager);
|
|
8
|
+
getProviderName(): string;
|
|
9
|
+
supportsSession(): boolean;
|
|
10
|
+
private addToolResponse;
|
|
11
|
+
protected filterIncompleteToolCallSequences(messages: AIMessage[]): AIMessage[];
|
|
12
|
+
executeToolCall(systemPrompt: string, userPrompt: string, toolSchema: ChatCompletionTool, sessionId: string): Promise<ToolCallResult>;
|
|
13
|
+
}
|
|
14
|
+
//# sourceMappingURL=openai-chat-completion.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"openai-chat-completion.d.ts","sourceRoot":"","sources":["../../../../src/services/ai/providers/openai-chat-completion.ts"],"names":[],"mappings":"AAAA,OAAO,EACL,cAAc,EACd,KAAK,cAAc,EACnB,KAAK,cAAc,EAEpB,MAAM,oBAAoB,CAAC;AAC5B,OAAO,KAAK,EAAE,gBAAgB,EAAE,MAAM,kCAAkC,CAAC;AACzE,OAAO,KAAK,EAAE,SAAS,EAAE,MAAM,6BAA6B,CAAC;AAC7D,OAAO,KAAK,EAAE,kBAAkB,EAAE,MAAM,yBAAyB,CAAC;AAgElE,qBAAa,4BAA6B,SAAQ,cAAc;IAC9D,OAAO,CAAC,QAAQ,CAAC,gBAAgB,CAAmB;gBAExC,MAAM,EAAE,cAAc,EAAE,gBAAgB,EAAE,gBAAgB;IAKtE,eAAe,IAAI,MAAM;IAIzB,eAAe,IAAI,OAAO;IAI1B,OAAO,CAAC,eAAe;IAqBvB,SAAS,CAAC,iCAAiC,CAAC,QAAQ,EAAE,SAAS,EAAE,GAAG,SAAS,EAAE;IAwCzE,eAAe,CACnB,YAAY,EAAE,MAAM,EACpB,UAAU,EAAE,MAAM,EAClB,UAAU,EAAE,kBAAkB,EAC9B,SAAS,EAAE,MAAM,GAChB,OAAO,CAAC,cAAc,CAAC;CAmS3B"}
|