call-ai 0.10.2 → 0.11.0-dev-preview3
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 +60 -58
- package/api-core.d.ts +13 -0
- package/{dist/api-core.js → api-core.js} +51 -126
- package/api-core.js.map +1 -0
- package/api.d.ts +4 -0
- package/api.js +364 -0
- package/api.js.map +1 -0
- package/api.ts.off +595 -0
- package/{dist/error-handling.d.ts → error-handling.d.ts} +4 -2
- package/{dist/error-handling.js → error-handling.js} +34 -70
- package/error-handling.js.map +1 -0
- package/image.d.ts +2 -0
- package/{dist/image.js → image.js} +10 -33
- package/image.js.map +1 -0
- package/index.d.ts +6 -0
- package/index.js +7 -0
- package/index.js.map +1 -0
- package/index.ts.bak +16 -0
- package/key-management.d.ts +29 -0
- package/key-management.js +189 -0
- package/key-management.js.map +1 -0
- package/{dist/non-streaming.d.ts → non-streaming.d.ts} +5 -8
- package/{dist/non-streaming.js → non-streaming.js} +28 -87
- package/non-streaming.js.map +1 -0
- package/package.json +15 -31
- package/response-metadata.d.ts +6 -0
- package/response-metadata.js +22 -0
- package/response-metadata.js.map +1 -0
- package/strategies/index.d.ts +2 -0
- package/strategies/index.js +3 -0
- package/strategies/index.js.map +1 -0
- package/strategies/model-strategies.d.ts +6 -0
- package/{dist/strategies → strategies}/model-strategies.js +26 -72
- package/strategies/model-strategies.js.map +1 -0
- package/strategies/strategy-selector.d.ts +2 -0
- package/strategies/strategy-selector.js +66 -0
- package/strategies/strategy-selector.js.map +1 -0
- package/streaming.d.ts +4 -0
- package/{dist/streaming.js → streaming.js} +66 -184
- package/streaming.js.map +1 -0
- package/streaming.ts.off +571 -0
- package/tsconfig.json +18 -0
- package/types.d.ts +226 -0
- package/types.js +33 -0
- package/types.js.map +1 -0
- package/utils.d.ts +32 -0
- package/utils.js +129 -0
- package/utils.js.map +1 -0
- package/version.d.ts +1 -0
- package/version.js +2 -0
- package/version.js.map +1 -0
- package/dist/api-core.d.ts +0 -40
- package/dist/api.d.ts +0 -15
- package/dist/api.js +0 -498
- package/dist/image.d.ts +0 -12
- package/dist/index.d.ts +0 -7
- package/dist/index.js +0 -32
- package/dist/key-management.d.ts +0 -43
- package/dist/key-management.js +0 -312
- package/dist/response-metadata.d.ts +0 -18
- package/dist/response-metadata.js +0 -44
- package/dist/strategies/index.d.ts +0 -5
- package/dist/strategies/index.js +0 -21
- package/dist/strategies/model-strategies.d.ts +0 -24
- package/dist/strategies/strategy-selector.d.ts +0 -8
- package/dist/strategies/strategy-selector.js +0 -79
- package/dist/streaming.d.ts +0 -7
- package/dist/types.d.ts +0 -226
- package/dist/types.js +0 -5
- package/dist/utils.d.ts +0 -8
- package/dist/utils.js +0 -52
|
@@ -1,25 +1,12 @@
|
|
|
1
|
-
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
/**
|
|
6
|
-
* Error handling utilities for call-ai
|
|
7
|
-
*/
|
|
8
|
-
const key_management_1 = require("./key-management");
|
|
9
|
-
// Standardized API error handler
|
|
10
|
-
// @param error The error object
|
|
11
|
-
// @param context Context description for error messages
|
|
12
|
-
// @param debug Whether to log debug information
|
|
13
|
-
// @param options Options for error handling including key refresh control
|
|
14
|
-
async function handleApiError(error, context, debug = key_management_1.globalDebug, options = {}) {
|
|
15
|
-
// Extract error details
|
|
1
|
+
import { keyStore, globalDebug, isNewKeyError, refreshApiKey } from "./key-management.js";
|
|
2
|
+
import { CallAIError } from "./types.js";
|
|
3
|
+
async function handleApiError(ierror, context, debug = globalDebug, options = {}) {
|
|
4
|
+
const error = ierror;
|
|
16
5
|
const errorMessage = error?.message || String(error);
|
|
17
6
|
const status = error?.status ||
|
|
18
7
|
error?.statusCode ||
|
|
19
8
|
error?.response?.status ||
|
|
20
|
-
(errorMessage.match(/status: (\d+)/i)?.[1] &&
|
|
21
|
-
parseInt(errorMessage.match(/status: (\d+)/i)[1]));
|
|
22
|
-
// Check if this is a missing API key error
|
|
9
|
+
(errorMessage.match(/status: (\d+)/i)?.[1] && parseInt(errorMessage.match(/status: (\d+)/i)?.[1] ?? "500"));
|
|
23
10
|
const isMissingKeyError = errorMessage.includes("API key is required");
|
|
24
11
|
if (debug) {
|
|
25
12
|
console.error(`[callAi:error] ${context} error:`, {
|
|
@@ -30,68 +17,53 @@ async function handleApiError(error, context, debug = key_management_1.globalDeb
|
|
|
30
17
|
isMissingKey: isMissingKeyError,
|
|
31
18
|
});
|
|
32
19
|
}
|
|
33
|
-
// Don't attempt API key refresh if explicitly skipped
|
|
34
20
|
if (options.skipRefresh) {
|
|
35
21
|
throw error;
|
|
36
22
|
}
|
|
37
|
-
|
|
38
|
-
// Either it's a specific key error OR we have no key at all
|
|
39
|
-
const needsNewKey = (0, key_management_1.isNewKeyError)(error, debug) || isMissingKeyError;
|
|
40
|
-
// If the error suggests an API key issue, try to refresh the key
|
|
23
|
+
const needsNewKey = isNewKeyError(error, debug) || isMissingKeyError;
|
|
41
24
|
if (needsNewKey) {
|
|
42
25
|
if (debug) {
|
|
43
26
|
console.log(`[callAi:key-refresh] Error suggests API key issue, attempting refresh...`);
|
|
44
27
|
}
|
|
45
28
|
try {
|
|
46
|
-
|
|
47
|
-
const
|
|
48
|
-
const
|
|
49
|
-
let refreshToken = options.refreshToken || key_management_1.keyStore.refreshToken;
|
|
50
|
-
// First attempt to refresh the API key
|
|
29
|
+
const currentKey = options.apiKey || keyStore().current;
|
|
30
|
+
const endpoint = options.endpoint || keyStore().refreshEndpoint;
|
|
31
|
+
const refreshToken = options.refreshToken || keyStore().refreshToken;
|
|
51
32
|
try {
|
|
52
|
-
const { apiKey, topup } = await (
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
key_management_1.keyStore.current = apiKey;
|
|
33
|
+
const { apiKey, topup } = await refreshApiKey(options, currentKey, endpoint, refreshToken, debug);
|
|
34
|
+
if (keyStore().current !== apiKey) {
|
|
35
|
+
keyStore().current = apiKey;
|
|
56
36
|
}
|
|
57
37
|
if (debug) {
|
|
58
38
|
console.log(`[callAi:key-refresh] ${topup ? "Topped up" : "Refreshed"} API key successfully`);
|
|
59
39
|
}
|
|
60
|
-
// Return without throwing since we've successfully recovered
|
|
61
40
|
return;
|
|
62
41
|
}
|
|
63
42
|
catch (initialRefreshError) {
|
|
64
|
-
// If there's an updateRefreshToken callback and the error was due to token issue
|
|
65
43
|
if (options.updateRefreshToken && refreshToken) {
|
|
66
44
|
if (debug) {
|
|
67
45
|
console.log(`[callAi:key-refresh] Initial refresh failed, attempting to update refresh token`);
|
|
68
46
|
}
|
|
69
47
|
try {
|
|
70
|
-
// Get a new refresh token using the callback
|
|
71
48
|
const newRefreshToken = await options.updateRefreshToken(refreshToken);
|
|
72
49
|
if (newRefreshToken && newRefreshToken !== refreshToken) {
|
|
73
50
|
if (debug) {
|
|
74
51
|
console.log(`[callAi:key-refresh] Got new refresh token, retrying key refresh`);
|
|
75
52
|
}
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
// Update the key in the store
|
|
81
|
-
if (key_management_1.keyStore.current !== apiKey) {
|
|
82
|
-
key_management_1.keyStore.current = apiKey;
|
|
53
|
+
keyStore().refreshToken = newRefreshToken;
|
|
54
|
+
const { apiKey, topup } = await refreshApiKey(options, currentKey, endpoint, newRefreshToken, debug);
|
|
55
|
+
if (keyStore().current !== apiKey) {
|
|
56
|
+
keyStore().current = apiKey;
|
|
83
57
|
}
|
|
84
58
|
if (debug) {
|
|
85
59
|
console.log(`[callAi:key-refresh] ${topup ? "Topped up" : "Refreshed"} API key successfully with new refresh token`);
|
|
86
60
|
}
|
|
87
|
-
// Return without throwing since we've successfully recovered
|
|
88
61
|
return;
|
|
89
62
|
}
|
|
90
63
|
else {
|
|
91
64
|
if (debug) {
|
|
92
65
|
console.log(`[callAi:key-refresh] No new refresh token provided or same token returned, cannot retry`);
|
|
93
66
|
}
|
|
94
|
-
// Continue to error handling
|
|
95
67
|
throw initialRefreshError;
|
|
96
68
|
}
|
|
97
69
|
}
|
|
@@ -99,66 +71,56 @@ async function handleApiError(error, context, debug = key_management_1.globalDeb
|
|
|
99
71
|
if (debug) {
|
|
100
72
|
console.error(`[callAi:key-refresh] Failed to update refresh token:`, tokenUpdateError);
|
|
101
73
|
}
|
|
102
|
-
// Continue to error handling with the original refresh error
|
|
103
74
|
throw initialRefreshError;
|
|
104
75
|
}
|
|
105
76
|
}
|
|
106
77
|
else {
|
|
107
|
-
// No updateRefreshToken callback or no token, rethrow the initial error
|
|
108
78
|
throw initialRefreshError;
|
|
109
79
|
}
|
|
110
80
|
}
|
|
111
81
|
}
|
|
112
82
|
catch (refreshError) {
|
|
113
|
-
// Log refresh failure but throw the original error
|
|
114
83
|
if (debug) {
|
|
115
84
|
console.error(`[callAi:key-refresh] API key refresh failed:`, refreshError);
|
|
116
85
|
}
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
|
|
86
|
+
const detailedError = new CallAIError({
|
|
87
|
+
message: `${errorMessage} (Key refresh failed: ${refreshError instanceof Error ? refreshError.message : String(refreshError)})`,
|
|
88
|
+
originalError: error,
|
|
89
|
+
refreshError,
|
|
90
|
+
status: status || 401,
|
|
91
|
+
contentType: "text/plain",
|
|
92
|
+
});
|
|
123
93
|
throw detailedError;
|
|
124
94
|
}
|
|
125
95
|
}
|
|
126
|
-
|
|
127
|
-
|
|
128
|
-
|
|
129
|
-
|
|
130
|
-
|
|
96
|
+
const detailedError = new CallAIError({
|
|
97
|
+
message: `${context}: ${errorMessage}`,
|
|
98
|
+
originalError: error,
|
|
99
|
+
status: status || 500,
|
|
100
|
+
errorType: error.name || "Error",
|
|
101
|
+
});
|
|
131
102
|
throw detailedError;
|
|
132
103
|
}
|
|
133
|
-
|
|
134
|
-
async function checkForInvalidModelError(response, model, debug = key_management_1.globalDebug) {
|
|
135
|
-
// Only check 4xx errors (which could indicate invalid model)
|
|
104
|
+
async function checkForInvalidModelError(response, model, debug = globalDebug) {
|
|
136
105
|
if (response.status < 400 || response.status >= 500) {
|
|
137
106
|
return { isInvalidModel: false };
|
|
138
107
|
}
|
|
139
|
-
// Clone the response so we can still use the original later if needed
|
|
140
108
|
const responseClone = response.clone();
|
|
141
|
-
// Try to parse the response as JSON
|
|
142
109
|
let errorData;
|
|
143
110
|
try {
|
|
144
111
|
errorData = await responseClone.json();
|
|
145
112
|
}
|
|
146
113
|
catch (e) {
|
|
147
|
-
// If it's not JSON, get the text
|
|
148
114
|
try {
|
|
149
115
|
const text = await responseClone.text();
|
|
150
116
|
errorData = { error: text };
|
|
151
117
|
}
|
|
152
|
-
catch (
|
|
118
|
+
catch (e) {
|
|
153
119
|
errorData = { error: `Error ${response.status}: ${response.statusText}` };
|
|
154
120
|
}
|
|
155
121
|
}
|
|
156
|
-
|
|
157
|
-
const isInvalidModelError =
|
|
158
|
-
// Status checks
|
|
159
|
-
response.status === 404 ||
|
|
122
|
+
const isInvalidModelError = response.status === 404 ||
|
|
160
123
|
response.status === 400 ||
|
|
161
|
-
// Response content checks
|
|
162
124
|
(errorData &&
|
|
163
125
|
((typeof errorData.error === "string" &&
|
|
164
126
|
(errorData.error.toLowerCase().includes("model") ||
|
|
@@ -178,3 +140,5 @@ async function checkForInvalidModelError(response, model, debug = key_management
|
|
|
178
140
|
}
|
|
179
141
|
return { isInvalidModel: isInvalidModelError, errorData };
|
|
180
142
|
}
|
|
143
|
+
export { handleApiError, checkForInvalidModelError };
|
|
144
|
+
//# sourceMappingURL=error-handling.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"error-handling.js","sourceRoot":"","sources":["../jsr/error-handling.ts"],"names":[],"mappings":"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"}
|
package/image.d.ts
ADDED
|
@@ -1,36 +1,17 @@
|
|
|
1
|
-
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
// eslint-disable-next-line @typescript-eslint/no-var-requires
|
|
6
|
-
const PACKAGE_VERSION = require("../package.json").version;
|
|
7
|
-
/**
|
|
8
|
-
* Generate images using a custom API that mimics OpenAI's image generation capabilities
|
|
9
|
-
* @param prompt Text prompt describing the image to generate
|
|
10
|
-
* @param options Configuration options for the image generation request
|
|
11
|
-
* @returns A Promise that resolves to the image response containing base64 encoded image data
|
|
12
|
-
*/
|
|
13
|
-
async function imageGen(prompt, options = {}) {
|
|
14
|
-
const { model = "gpt-image-1", apiKey = "VIBES_DIY", debug = false, size = "1024x1024", } = options;
|
|
1
|
+
import { callAiEnv, callAiFetch } from "./utils.js";
|
|
2
|
+
import { PACKAGE_VERSION } from "./version.js";
|
|
3
|
+
export async function imageGen(prompt, options = {}) {
|
|
4
|
+
const { model = "gpt-image-1", apiKey = "VIBES_DIY", debug = false, size = "1024x1024" } = options;
|
|
15
5
|
if (debug) {
|
|
16
6
|
console.log(`[imageGen:${PACKAGE_VERSION}] Generating image with prompt: ${prompt.substring(0, 50)}...`);
|
|
17
7
|
console.log(`[imageGen:${PACKAGE_VERSION}] Using model: ${model}`);
|
|
18
8
|
}
|
|
19
|
-
|
|
20
|
-
const customOrigin = options.imgUrl ||
|
|
21
|
-
(typeof window !== "undefined" ? window.CALLAI_IMG_URL : null) ||
|
|
22
|
-
(typeof process !== "undefined" && process.env
|
|
23
|
-
? process.env.CALLAI_IMG_URL
|
|
24
|
-
: null);
|
|
9
|
+
const customOrigin = options.imgUrl || callAiEnv.CALLAI_IMG_URL;
|
|
25
10
|
try {
|
|
26
|
-
// Handle image generation
|
|
27
11
|
if (!options.images || options.images.length === 0) {
|
|
28
|
-
|
|
29
|
-
// Use custom origin or document.location.origin
|
|
30
|
-
const origin = customOrigin ||
|
|
31
|
-
(typeof document !== "undefined" ? document.location.origin : "");
|
|
12
|
+
const origin = customOrigin || (typeof document !== "undefined" ? document.location.origin : "");
|
|
32
13
|
const generateEndpoint = `${origin}/api/openai-image/generate`;
|
|
33
|
-
const response = await
|
|
14
|
+
const response = await callAiFetch(options)(generateEndpoint, {
|
|
34
15
|
method: "POST",
|
|
35
16
|
headers: {
|
|
36
17
|
Authorization: `Bearer ${apiKey}`,
|
|
@@ -52,25 +33,20 @@ async function imageGen(prompt, options = {}) {
|
|
|
52
33
|
return result;
|
|
53
34
|
}
|
|
54
35
|
else {
|
|
55
|
-
// Image editing with multiple input images
|
|
56
36
|
const formData = new FormData();
|
|
57
37
|
formData.append("model", model);
|
|
58
38
|
formData.append("prompt", prompt);
|
|
59
|
-
// Add each image to the form data
|
|
60
39
|
options.images.forEach((image, index) => {
|
|
61
40
|
formData.append(`image_${index}`, image);
|
|
62
41
|
});
|
|
63
|
-
// Add parameters
|
|
64
42
|
formData.append("size", size);
|
|
65
43
|
if (options.quality)
|
|
66
44
|
formData.append("quality", options.quality);
|
|
67
45
|
if (options.style)
|
|
68
46
|
formData.append("style", options.style);
|
|
69
|
-
|
|
70
|
-
const origin = customOrigin ||
|
|
71
|
-
(typeof document !== "undefined" ? document.location.origin : "");
|
|
47
|
+
const origin = customOrigin || (typeof document !== "undefined" ? document.location.origin : "");
|
|
72
48
|
const editEndpoint = `${origin}/api/openai-image/edit`;
|
|
73
|
-
const response = await
|
|
49
|
+
const response = await callAiFetch(options)(editEndpoint, {
|
|
74
50
|
method: "POST",
|
|
75
51
|
headers: {
|
|
76
52
|
Authorization: `Bearer ${apiKey}`,
|
|
@@ -92,3 +68,4 @@ async function imageGen(prompt, options = {}) {
|
|
|
92
68
|
throw error;
|
|
93
69
|
}
|
|
94
70
|
}
|
|
71
|
+
//# sourceMappingURL=image.js.map
|
package/image.js.map
ADDED
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"image.js","sourceRoot":"","sources":["../jsr/image.ts"],"names":[],"mappings":"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"}
|
package/index.d.ts
ADDED
package/index.js
ADDED
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
export * from "./types.js";
|
|
2
|
+
export { callAi } from "./api.js";
|
|
3
|
+
export { callAi as callAI } from "./api.js";
|
|
4
|
+
export { getMeta } from "./response-metadata.js";
|
|
5
|
+
export { imageGen } from "./image.js";
|
|
6
|
+
export { callAiEnv, entriesHeaders } from "./utils.js";
|
|
7
|
+
//# sourceMappingURL=index.js.map
|
package/index.js.map
ADDED
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../jsr/index.ts"],"names":[],"mappings":"AAKA,cAAc,YAAY,CAAC;AAG3B,OAAO,EAAE,MAAM,EAAE,MAAM,UAAU,CAAC;AAElC,OAAO,EAAE,MAAM,IAAI,MAAM,EAAE,MAAM,UAAU,CAAC;AAE5C,OAAO,EAAE,OAAO,EAAE,MAAM,wBAAwB,CAAC;AAGjD,OAAO,EAAE,QAAQ,EAAE,MAAM,YAAY,CAAC;AAEtC,OAAO,EAAE,SAAS,EAAE,cAAc,EAAE,MAAM,YAAY,CAAC"}
|
package/index.ts.bak
ADDED
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* call-ai: A lightweight library for making AI API calls
|
|
3
|
+
*/
|
|
4
|
+
|
|
5
|
+
// Export public types
|
|
6
|
+
export * from "./types";
|
|
7
|
+
|
|
8
|
+
// Export API functions
|
|
9
|
+
export { callAi, getMeta } from "./api";
|
|
10
|
+
|
|
11
|
+
// Export image generation function
|
|
12
|
+
export { imageGen } from "./image";
|
|
13
|
+
|
|
14
|
+
// Export strategies and utilities for advanced use cases
|
|
15
|
+
export * from "./strategies";
|
|
16
|
+
export * from "./utils";
|
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
import { Falsy, Mocks } from "./types.js";
|
|
2
|
+
export interface KeyMetadata {
|
|
3
|
+
key: string;
|
|
4
|
+
hash: string;
|
|
5
|
+
created: Date;
|
|
6
|
+
expires: Date;
|
|
7
|
+
remaining: number;
|
|
8
|
+
limit: number;
|
|
9
|
+
}
|
|
10
|
+
export declare function keyStore(): {
|
|
11
|
+
current: string | undefined;
|
|
12
|
+
refreshEndpoint: string;
|
|
13
|
+
refreshToken: string | 0 | false | null | undefined;
|
|
14
|
+
isRefreshing: boolean;
|
|
15
|
+
lastRefreshAttempt: number;
|
|
16
|
+
metadata: Record<string, Partial<KeyMetadata>>;
|
|
17
|
+
};
|
|
18
|
+
declare let globalDebug: boolean;
|
|
19
|
+
declare function initKeyStore(): void;
|
|
20
|
+
declare function isNewKeyError(ierror: unknown, debug?: boolean): boolean;
|
|
21
|
+
declare function refreshApiKey(options: {
|
|
22
|
+
mock?: Mocks;
|
|
23
|
+
}, currentKey: string | Falsy, endpoint: string | Falsy, refreshToken: string | Falsy, debug?: boolean): Promise<{
|
|
24
|
+
apiKey: string;
|
|
25
|
+
topup: boolean;
|
|
26
|
+
}>;
|
|
27
|
+
declare function getHashFromKey(key: string): string | null;
|
|
28
|
+
declare function storeKeyMetadata(data: KeyMetadata): void;
|
|
29
|
+
export { globalDebug, initKeyStore, isNewKeyError, refreshApiKey, getHashFromKey, storeKeyMetadata };
|
|
@@ -0,0 +1,189 @@
|
|
|
1
|
+
import { callAiEnv, callAiFetch, entriesHeaders } from "./utils.js";
|
|
2
|
+
export function keyStore() {
|
|
3
|
+
return {
|
|
4
|
+
current: undefined,
|
|
5
|
+
refreshEndpoint: "https://vibecode.garden",
|
|
6
|
+
refreshToken: "use-vibes",
|
|
7
|
+
isRefreshing: false,
|
|
8
|
+
lastRefreshAttempt: 0,
|
|
9
|
+
metadata: {},
|
|
10
|
+
};
|
|
11
|
+
}
|
|
12
|
+
let globalDebug = false;
|
|
13
|
+
function initKeyStore() {
|
|
14
|
+
keyStore().current = callAiEnv.CALLAI_API_KEY;
|
|
15
|
+
keyStore().refreshEndpoint = callAiEnv.CALLAI_REFRESH_ENDPOINT ?? "https://vibecode.garden";
|
|
16
|
+
keyStore().refreshToken = callAiEnv.CALL_AI_REFRESH_TOKEN ?? "use-vibes";
|
|
17
|
+
globalDebug = !!callAiEnv.CALLAI_DEBUG;
|
|
18
|
+
}
|
|
19
|
+
function isNewKeyError(ierror, debug = false) {
|
|
20
|
+
const error = ierror;
|
|
21
|
+
let status = error?.status || error?.statusCode || error?.response?.status || 450;
|
|
22
|
+
const errorMessage = String(error || "").toLowerCase();
|
|
23
|
+
if (!status && errorMessage.includes("status:")) {
|
|
24
|
+
const statusMatch = errorMessage.match(/status:\\s*(\\d+)/i);
|
|
25
|
+
if (statusMatch && statusMatch[1]) {
|
|
26
|
+
status = parseInt(statusMatch[1], 10);
|
|
27
|
+
}
|
|
28
|
+
}
|
|
29
|
+
const is4xx = status >= 400 && status < 500;
|
|
30
|
+
const isAuthError = status === 401 ||
|
|
31
|
+
status === 403 ||
|
|
32
|
+
errorMessage.includes("unauthorized") ||
|
|
33
|
+
errorMessage.includes("forbidden") ||
|
|
34
|
+
errorMessage.includes("authentication") ||
|
|
35
|
+
errorMessage.includes("api key") ||
|
|
36
|
+
errorMessage.includes("apikey") ||
|
|
37
|
+
errorMessage.includes("auth");
|
|
38
|
+
const isInvalidKeyError = errorMessage.includes("invalid api key") ||
|
|
39
|
+
errorMessage.includes("invalid key") ||
|
|
40
|
+
errorMessage.includes("incorrect api key") ||
|
|
41
|
+
errorMessage.includes("incorrect key") ||
|
|
42
|
+
errorMessage.includes("authentication failed") ||
|
|
43
|
+
errorMessage.includes("not authorized");
|
|
44
|
+
const isOpenAIKeyError = errorMessage.includes("openai") && (errorMessage.includes("api key") || errorMessage.includes("authentication"));
|
|
45
|
+
const isRateLimitError = status === 429 ||
|
|
46
|
+
errorMessage.includes("rate limit") ||
|
|
47
|
+
errorMessage.includes("too many requests") ||
|
|
48
|
+
errorMessage.includes("quota") ||
|
|
49
|
+
errorMessage.includes("exceed");
|
|
50
|
+
const isBillingError = errorMessage.includes("billing") ||
|
|
51
|
+
errorMessage.includes("payment") ||
|
|
52
|
+
errorMessage.includes("subscription") ||
|
|
53
|
+
errorMessage.includes("account");
|
|
54
|
+
const needsNewKey = is4xx && (isAuthError || isInvalidKeyError || isOpenAIKeyError || isRateLimitError || isBillingError);
|
|
55
|
+
if (debug && needsNewKey) {
|
|
56
|
+
console.log(`[callAi:key-refresh] Detected error requiring key refresh: ${errorMessage}`);
|
|
57
|
+
}
|
|
58
|
+
return needsNewKey;
|
|
59
|
+
}
|
|
60
|
+
async function refreshApiKey(options, currentKey, endpoint, refreshToken, debug = globalDebug) {
|
|
61
|
+
if (!endpoint) {
|
|
62
|
+
throw new Error("No API key refresh endpoint specified");
|
|
63
|
+
}
|
|
64
|
+
if (!refreshToken) {
|
|
65
|
+
throw new Error("No API key refresh token specified");
|
|
66
|
+
}
|
|
67
|
+
if (keyStore().isRefreshing) {
|
|
68
|
+
if (debug) {
|
|
69
|
+
console.log("API key refresh already in progress, waiting...");
|
|
70
|
+
}
|
|
71
|
+
return new Promise((resolve) => {
|
|
72
|
+
const checkInterval = setInterval(() => {
|
|
73
|
+
if (!keyStore().isRefreshing && keyStore().current) {
|
|
74
|
+
clearInterval(checkInterval);
|
|
75
|
+
const ck = keyStore().current;
|
|
76
|
+
if (!ck) {
|
|
77
|
+
throw new Error("API key refresh failed");
|
|
78
|
+
}
|
|
79
|
+
resolve({ apiKey: ck, topup: false });
|
|
80
|
+
}
|
|
81
|
+
}, 100);
|
|
82
|
+
});
|
|
83
|
+
}
|
|
84
|
+
const now = Date.now();
|
|
85
|
+
const timeSinceLastRefresh = now - keyStore().lastRefreshAttempt;
|
|
86
|
+
const minRefreshInterval = 2000;
|
|
87
|
+
if (timeSinceLastRefresh < minRefreshInterval) {
|
|
88
|
+
if (debug) {
|
|
89
|
+
console.log(`Rate limiting key refresh, last attempt was ${timeSinceLastRefresh}ms ago`);
|
|
90
|
+
}
|
|
91
|
+
await new Promise((resolve) => setTimeout(resolve, minRefreshInterval - timeSinceLastRefresh));
|
|
92
|
+
}
|
|
93
|
+
keyStore().isRefreshing = true;
|
|
94
|
+
keyStore().lastRefreshAttempt = Date.now();
|
|
95
|
+
const apiPath = "/api/keys";
|
|
96
|
+
const baseUrl = endpoint.endsWith("/") ? endpoint.slice(0, -1) : endpoint;
|
|
97
|
+
const url = `${baseUrl}${apiPath}`;
|
|
98
|
+
if (debug) {
|
|
99
|
+
console.log(`Refreshing API key from: ${url}`);
|
|
100
|
+
}
|
|
101
|
+
try {
|
|
102
|
+
const requestPayload = {
|
|
103
|
+
key: currentKey,
|
|
104
|
+
hash: currentKey ? getHashFromKey(currentKey) : null,
|
|
105
|
+
name: "call-ai-client",
|
|
106
|
+
};
|
|
107
|
+
if (debug) {
|
|
108
|
+
console.log(`[callAi:key-refresh] Request URL: ${url}`);
|
|
109
|
+
console.log(`[callAi:key-refresh] Request headers:`, {
|
|
110
|
+
"Content-Type": "application/json",
|
|
111
|
+
Authorization: `Bearer ${refreshToken}`,
|
|
112
|
+
});
|
|
113
|
+
console.log(`[callAi:key-refresh] Request payload:`, requestPayload);
|
|
114
|
+
}
|
|
115
|
+
const response = await callAiFetch(options)(url, {
|
|
116
|
+
method: "POST",
|
|
117
|
+
headers: {
|
|
118
|
+
"Content-Type": "application/json",
|
|
119
|
+
Authorization: `Bearer ${refreshToken}`,
|
|
120
|
+
},
|
|
121
|
+
body: JSON.stringify(requestPayload),
|
|
122
|
+
});
|
|
123
|
+
if (debug) {
|
|
124
|
+
console.log(`[callAi:key-refresh] Response status: ${response.status} ${response.statusText}`);
|
|
125
|
+
console.log(`[callAi:key-refresh] Response headers:`, Object.fromEntries([...entriesHeaders(response.headers)]));
|
|
126
|
+
}
|
|
127
|
+
if (!response.ok) {
|
|
128
|
+
const errorText = await response.text();
|
|
129
|
+
if (debug) {
|
|
130
|
+
console.log(`[callAi:key-refresh] Error response body: ${errorText}`);
|
|
131
|
+
}
|
|
132
|
+
throw new Error(`API key refresh failed: ${response.status} ${response.statusText}${errorText ? ` - ${errorText}` : ""}`);
|
|
133
|
+
}
|
|
134
|
+
const data = await response.json();
|
|
135
|
+
if (debug) {
|
|
136
|
+
console.log(`[callAi:key-refresh] Full response structure:`, JSON.stringify(data, null, 2));
|
|
137
|
+
}
|
|
138
|
+
let newKey;
|
|
139
|
+
if (data.key && typeof data.key === "object" && data.key.key) {
|
|
140
|
+
newKey = data.key.key;
|
|
141
|
+
}
|
|
142
|
+
// Check for old format where data.key is the string key directly
|
|
143
|
+
else if (data.key && typeof data.key === "string") {
|
|
144
|
+
newKey = data.key;
|
|
145
|
+
}
|
|
146
|
+
// Handle error case
|
|
147
|
+
else {
|
|
148
|
+
throw new Error("Invalid response from key refresh endpoint: missing or malformed key");
|
|
149
|
+
}
|
|
150
|
+
if (debug) {
|
|
151
|
+
console.log(`API key refreshed successfully: ${newKey.substring(0, 10)}...`);
|
|
152
|
+
}
|
|
153
|
+
if (data.metadata || (data.key && typeof data.key === "object" && data.key.metadata)) {
|
|
154
|
+
const metadata = data.metadata || data.key.metadata;
|
|
155
|
+
storeKeyMetadata(metadata);
|
|
156
|
+
}
|
|
157
|
+
keyStore().current = newKey;
|
|
158
|
+
const hashValue = data.hash || (data.key && typeof data.key === "object" && data.key.hash);
|
|
159
|
+
const isTopup = currentKey && hashValue && hashValue === getHashFromKey(currentKey);
|
|
160
|
+
keyStore().isRefreshing = false;
|
|
161
|
+
return {
|
|
162
|
+
apiKey: newKey, // Return the string key, not the object
|
|
163
|
+
topup: isTopup,
|
|
164
|
+
};
|
|
165
|
+
}
|
|
166
|
+
catch (error) {
|
|
167
|
+
keyStore().isRefreshing = false;
|
|
168
|
+
throw error;
|
|
169
|
+
}
|
|
170
|
+
}
|
|
171
|
+
function getHashFromKey(key) {
|
|
172
|
+
if (!key)
|
|
173
|
+
return null;
|
|
174
|
+
const metaKey = Object.keys(keyStore().metadata).find((k) => k === key);
|
|
175
|
+
return metaKey ? keyStore().metadata[metaKey].hash || null : null;
|
|
176
|
+
}
|
|
177
|
+
function storeKeyMetadata(data) {
|
|
178
|
+
if (!data || !data.key)
|
|
179
|
+
return;
|
|
180
|
+
keyStore().metadata[data.key] = {
|
|
181
|
+
hash: data.hash,
|
|
182
|
+
created: data.created || Date.now(),
|
|
183
|
+
expires: data.expires,
|
|
184
|
+
remaining: data.remaining,
|
|
185
|
+
limit: data.limit,
|
|
186
|
+
};
|
|
187
|
+
}
|
|
188
|
+
export { globalDebug, initKeyStore, isNewKeyError, refreshApiKey, getHashFromKey, storeKeyMetadata };
|
|
189
|
+
//# sourceMappingURL=key-management.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"key-management.js","sourceRoot":"","sources":["../jsr/key-management.ts"],"names":[],"mappings":"AAKA,OAAO,EAAE,SAAS,EAAE,WAAW,EAAE,cAAc,EAAE,MAAM,YAAY,CAAC;AAYpE,MAAM,UAAU,QAAQ,GAAG;IACzB,OAAO;QAEL,OAAO,EAAE,SAA+B;QAExC,eAAe,EAAE,yBAAyB;QAE1C,YAAY,EAAE,WAA6B;QAE3C,YAAY,EAAE,KAAK;QAEnB,kBAAkB,EAAE,CAAC;QAErB,QAAQ,EAAE,EAA0C;KACrD,CAAC;AAAA,CACH;AAGD,IAAI,WAAW,GAAG,KAAK,CAAC;AAKxB,SAAS,YAAY,GAAG;IAEtB,QAAQ,EAAE,CAAC,OAAO,GAAG,SAAS,CAAC,cAAc,CAAC;IAC9C,QAAQ,EAAE,CAAC,eAAe,GAAG,SAAS,CAAC,uBAAuB,IAAI,yBAAyB,CAAC;IAC5F,QAAQ,EAAE,CAAC,YAAY,GAAG,SAAS,CAAC,qBAAqB,IAAI,WAAW,CAAC;IACzE,WAAW,GAAG,CAAC,CAAC,SAAS,CAAC,YAAY,CAAC;AAAA,CACxC;AAWD,SAAS,aAAa,CAAC,MAAe,EAAE,KAAK,GAAG,KAAK,EAAW;IAC9D,MAAM,KAAK,GAAG,MAA2B,CAAC;IAE1C,IAAI,MAAM,GAAG,KAAK,EAAE,MAAM,IAAI,KAAK,EAAE,UAAU,IAAI,KAAK,EAAE,QAAQ,EAAE,MAAM,IAAI,GAAG,CAAC;IAClF,MAAM,YAAY,GAAG,MAAM,CAAC,KAAK,IAAI,EAAE,CAAC,CAAC,WAAW,EAAE,CAAC;IAIvD,IAAI,CAAC,MAAM,IAAI,YAAY,CAAC,QAAQ,CAAC,SAAS,CAAC,EAAE,CAAC;QAChD,MAAM,WAAW,GAAG,YAAY,CAAC,KAAK,CAAC,oBAAoB,CAAC,CAAC;QAC7D,IAAI,WAAW,IAAI,WAAW,CAAC,CAAC,CAAC,EAAE,CAAC;YAClC,MAAM,GAAG,QAAQ,CAAC,WAAW,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC;QACxC,CAAC;IACH,CAAC;IAED,MAAM,KAAK,GAAG,MAAM,IAAI,GAAG,IAAI,MAAM,GAAG,GAAG,CAAC;IAG5C,MAAM,WAAW,GACf,MAAM,KAAK,GAAG;QACd,MAAM,KAAK,GAAG;QACd,YAAY,CAAC,QAAQ,CAAC,cAAc,CAAC;QACrC,YAAY,CAAC,QAAQ,CAAC,WAAW,CAAC;QAClC,YAAY,CAAC,QAAQ,CAAC,gBAAgB,CAAC;QACvC,YAAY,CAAC,QAAQ,CAAC,SAAS,CAAC;QAChC,YAAY,CAAC,QAAQ,CAAC,QAAQ,CAAC;QAC/B,YAAY,CAAC,QAAQ,CAAC,MAAM,CAAC,CAAC;IAGhC,MAAM,iBAAiB,GACrB,YAAY,CAAC,QAAQ,CAAC,iBAAiB,CAAC;QACxC,YAAY,CAAC,QAAQ,CAAC,aAAa,CAAC;QACpC,YAAY,CAAC,QAAQ,CAAC,mBAAmB,CAAC;QAC1C,YAAY,CAAC,QAAQ,CAAC,eAAe,CAAC;QACtC,YAAY,CAAC,QAAQ,CAAC,uBAAuB,CAAC;QAC9C,YAAY,CAAC,QAAQ,CAAC,gBAAgB,CAAC,CAAC;IAG1C,MAAM,gBAAgB,GACpB,YAAY,CAAC,QAAQ,CAAC,QAAQ,CAAC,IAAI,CAAC,YAAY,CAAC,QAAQ,CAAC,SAAS,CAAC,IAAI,YAAY,CAAC,QAAQ,CAAC,gBAAgB,CAAC,CAAC,CAAC;IAGnH,MAAM,gBAAgB,GACpB,MAAM,KAAK,GAAG;QACd,YAAY,CAAC,QAAQ,CAAC,YAAY,CAAC;QACnC,YAAY,CAAC,QAAQ,CAAC,mBAAmB,CAAC;QAC1C,YAAY,CAAC,QAAQ,CAAC,OAAO,CAAC;QAC9B,YAAY,CAAC,QAAQ,CAAC,QAAQ,CAAC,CAAC;IAGlC,MAAM,cAAc,GAClB,YAAY,CAAC,QAAQ,CAAC,SAAS,CAAC;QAChC,YAAY,CAAC,QAAQ,CAAC,SAAS,CAAC;QAChC,YAAY,CAAC,QAAQ,CAAC,cAAc,CAAC;QACrC,YAAY,CAAC,QAAQ,CAAC,SAAS,CAAC,CAAC;IAGnC,MAAM,WAAW,GAAG,KAAK,IAAI,CAAC,WAAW,IAAI,iBAAiB,IAAI,gBAAgB,IAAI,gBAAgB,IAAI,cAAc,CAAC,CAAC;IAE1H,IAAI,KAAK,IAAI,WAAW,EAAE,CAAC;QACzB,OAAO,CAAC,GAAG,CAAC,8DAA8D,YAAY,EAAE,CAAC,CAAC;IAC5F,CAAC;IAED,OAAO,WAAW,CAAC;AAAA,CACpB;AASD,KAAK,UAAU,aAAa,CAC1B,OAAyB,EACzB,UAA0B,EAC1B,QAAwB,EACxB,YAA4B,EAC5B,KAAK,GAAY,WAAW,EACiB;IAE7C,IAAI,CAAC,QAAQ,EAAE,CAAC;QACd,MAAM,IAAI,KAAK,CAAC,uCAAuC,CAAC,CAAC;IAC3D,CAAC;IAED,IAAI,CAAC,YAAY,EAAE,CAAC;QAClB,MAAM,IAAI,KAAK,CAAC,oCAAoC,CAAC,CAAC;IACxD,CAAC;IAGD,IAAI,QAAQ,EAAE,CAAC,YAAY,EAAE,CAAC;QAC5B,IAAI,KAAK,EAAE,CAAC;YACV,OAAO,CAAC,GAAG,CAAC,iDAAiD,CAAC,CAAC;QACjE,CAAC;QAED,OAAO,IAAI,OAAO,CAAC,CAAC,OAAO,EAAE,EAAE,CAAC;YAC9B,MAAM,aAAa,GAAG,WAAW,CAAC,GAAG,EAAE,CAAC;gBACtC,IAAI,CAAC,QAAQ,EAAE,CAAC,YAAY,IAAI,QAAQ,EAAE,CAAC,OAAO,EAAE,CAAC;oBACnD,aAAa,CAAC,aAAa,CAAC,CAAC;oBAC7B,MAAM,EAAE,GAAG,QAAQ,EAAE,CAAC,OAAO,CAAC;oBAC9B,IAAI,CAAC,EAAE,EAAE,CAAC;wBACR,MAAM,IAAI,KAAK,CAAC,wBAAwB,CAAC,CAAC;oBAC5C,CAAC;oBACD,OAAO,CAAC,EAAE,MAAM,EAAE,EAAE,EAAE,KAAK,EAAE,KAAK,EAAE,CAAC,CAAC;gBACxC,CAAC;YAAA,CACF,EAAE,GAAG,CAAC,CAAC;QAAA,CACT,CAAC,CAAC;IACL,CAAC;IAGD,MAAM,GAAG,GAAG,IAAI,CAAC,GAAG,EAAE,CAAC;IACvB,MAAM,oBAAoB,GAAG,GAAG,GAAG,QAAQ,EAAE,CAAC,kBAAkB,CAAC;IACjE,MAAM,kBAAkB,GAAG,IAAI,CAAC;IAEhC,IAAI,oBAAoB,GAAG,kBAAkB,EAAE,CAAC;QAC9C,IAAI,KAAK,EAAE,CAAC;YACV,OAAO,CAAC,GAAG,CAAC,+CAA+C,oBAAoB,QAAQ,CAAC,CAAC;QAC3F,CAAC;QAED,MAAM,IAAI,OAAO,CAAC,CAAC,OAAO,EAAE,EAAE,CAAC,UAAU,CAAC,OAAO,EAAE,kBAAkB,GAAG,oBAAoB,CAAC,CAAC,CAAC;IACjG,CAAC;IAGD,QAAQ,EAAE,CAAC,YAAY,GAAG,IAAI,CAAC;IAC/B,QAAQ,EAAE,CAAC,kBAAkB,GAAG,IAAI,CAAC,GAAG,EAAE,CAAC;IAG3C,MAAM,OAAO,GAAG,WAAW,CAAC;IAG5B,MAAM,OAAO,GAAG,QAAQ,CAAC,QAAQ,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,QAAQ,CAAC,KAAK,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,QAAQ,CAAC;IAG1E,MAAM,GAAG,GAAG,GAAG,OAAO,GAAG,OAAO,EAAE,CAAC;IAEnC,IAAI,KAAK,EAAE,CAAC;QACV,OAAO,CAAC,GAAG,CAAC,4BAA4B,GAAG,EAAE,CAAC,CAAC;IACjD,CAAC;IAED,IAAI,CAAC;QAEH,MAAM,cAAc,GAAG;YACrB,GAAG,EAAE,UAAU;YACf,IAAI,EAAE,UAAU,CAAC,CAAC,CAAC,cAAc,CAAC,UAAU,CAAC,CAAC,CAAC,CAAC,IAAI;YACpD,IAAI,EAAE,gBAAgB;SACvB,CAAC;QAEF,IAAI,KAAK,EAAE,CAAC;YACV,OAAO,CAAC,GAAG,CAAC,qCAAqC,GAAG,EAAE,CAAC,CAAC;YACxD,OAAO,CAAC,GAAG,CAAC,uCAAuC,EAAE;gBACnD,cAAc,EAAE,kBAAkB;gBAClC,aAAa,EAAE,UAAU,YAAY,EAAE;aACxC,CAAC,CAAC;YACH,OAAO,CAAC,GAAG,CAAC,uCAAuC,EAAE,cAAc,CAAC,CAAC;QACvE,CAAC;QAGD,MAAM,QAAQ,GAAG,MAAM,WAAW,CAAC,OAAO,CAAC,CAAC,GAAG,EAAE;YAC/C,MAAM,EAAE,MAAM;YACd,OAAO,EAAE;gBACP,cAAc,EAAE,kBAAkB;gBAClC,aAAa,EAAE,UAAU,YAAY,EAAE;aACxC;YACD,IAAI,EAAE,IAAI,CAAC,SAAS,CAAC,cAAc,CAAC;SACrC,CAAC,CAAC;QAEH,IAAI,KAAK,EAAE,CAAC;YACV,OAAO,CAAC,GAAG,CAAC,yCAAyC,QAAQ,CAAC,MAAM,IAAI,QAAQ,CAAC,UAAU,EAAE,CAAC,CAAC;YAE/F,OAAO,CAAC,GAAG,CAAC,wCAAwC,EAAE,MAAM,CAAC,WAAW,CAAC,CAAC,GAAG,cAAc,CAAC,QAAQ,CAAC,OAAO,CAAC,CAAC,CAAC,CAAC,CAAC;QACnH,CAAC;QAED,IAAI,CAAC,QAAQ,CAAC,EAAE,EAAE,CAAC;YAEjB,MAAM,SAAS,GAAG,MAAM,QAAQ,CAAC,IAAI,EAAE,CAAC;YACxC,IAAI,KAAK,EAAE,CAAC;gBACV,OAAO,CAAC,GAAG,CAAC,6CAA6C,SAAS,EAAE,CAAC,CAAC;YACxE,CAAC;YACD,MAAM,IAAI,KAAK,CAAC,2BAA2B,QAAQ,CAAC,MAAM,IAAI,QAAQ,CAAC,UAAU,GAAG,SAAS,CAAC,CAAC,CAAC,MAAM,SAAS,EAAE,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC;QAC5H,CAAC;QAGD,MAAM,IAAI,GAAG,MAAM,QAAQ,CAAC,IAAI,EAAE,CAAC;QAGnC,IAAI,KAAK,EAAE,CAAC;YACV,OAAO,CAAC,GAAG,CAAC,+CAA+C,EAAE,IAAI,CAAC,SAAS,CAAC,IAAI,EAAE,IAAI,EAAE,CAAC,CAAC,CAAC,CAAC;QAC9F,CAAC;QAGD,IAAI,MAAc,CAAC;QAGnB,IAAI,IAAI,CAAC,GAAG,IAAI,OAAO,IAAI,CAAC,GAAG,KAAK,QAAQ,IAAI,IAAI,CAAC,GAAG,CAAC,GAAG,EAAE,CAAC;YAC7D,MAAM,GAAG,IAAI,CAAC,GAAG,CAAC,GAAG,CAAC;QACxB,CAAC;QACD,iEAAiE;aAC5D,IAAI,IAAI,CAAC,GAAG,IAAI,OAAO,IAAI,CAAC,GAAG,KAAK,QAAQ,EAAE,CAAC;YAClD,MAAM,GAAG,IAAI,CAAC,GAAG,CAAC;QACpB,CAAC;QACD,oBAAoB;aACf,CAAC;YACJ,MAAM,IAAI,KAAK,CAAC,sEAAsE,CAAC,CAAC;QAC1F,CAAC;QAED,IAAI,KAAK,EAAE,CAAC;YACV,OAAO,CAAC,GAAG,CAAC,mCAAmC,MAAM,CAAC,SAAS,CAAC,CAAC,EAAE,EAAE,CAAC,KAAK,CAAC,CAAC;QAC/E,CAAC;QAGD,IAAI,IAAI,CAAC,QAAQ,IAAI,CAAC,IAAI,CAAC,GAAG,IAAI,OAAO,IAAI,CAAC,GAAG,KAAK,QAAQ,IAAI,IAAI,CAAC,GAAG,CAAC,QAAQ,CAAC,EAAE,CAAC;YACrF,MAAM,QAAQ,GAAG,IAAI,CAAC,QAAQ,IAAI,IAAI,CAAC,GAAG,CAAC,QAAQ,CAAC;YACpD,gBAAgB,CAAC,QAAQ,CAAC,CAAC;QAC7B,CAAC;QAGD,QAAQ,EAAE,CAAC,OAAO,GAAG,MAAM,CAAC;QAI5B,MAAM,SAAS,GAAG,IAAI,CAAC,IAAI,IAAI,CAAC,IAAI,CAAC,GAAG,IAAI,OAAO,IAAI,CAAC,GAAG,KAAK,QAAQ,IAAI,IAAI,CAAC,GAAG,CAAC,IAAI,CAAC,CAAC;QAC3F,MAAM,OAAO,GAAG,UAAU,IAAI,SAAS,IAAI,SAAS,KAAK,cAAc,CAAC,UAAU,CAAC,CAAC;QAGpF,QAAQ,EAAE,CAAC,YAAY,GAAG,KAAK,CAAC;QAEhC,OAAO;YACL,MAAM,EAAE,MAAM,EAAE,wCAAwC;YACxD,KAAK,EAAE,OAAO;SACf,CAAC;IACJ,CAAC;IAAC,OAAO,KAAK,EAAE,CAAC;QAEf,QAAQ,EAAE,CAAC,YAAY,GAAG,KAAK,CAAC;QAChC,MAAM,KAAK,CAAC;IACd,CAAC;AAAA,CACF;AAKD,SAAS,cAAc,CAAC,GAAW,EAAiB;IAClD,IAAI,CAAC,GAAG;QAAE,OAAO,IAAI,CAAC;IAEtB,MAAM,OAAO,GAAG,MAAM,CAAC,IAAI,CAAC,QAAQ,EAAE,CAAC,QAAQ,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,KAAK,GAAG,CAAC,CAAC;IACxE,OAAO,OAAO,CAAC,CAAC,CAAC,QAAQ,EAAE,CAAC,QAAQ,CAAC,OAAO,CAAC,CAAC,IAAI,IAAI,IAAI,CAAC,CAAC,CAAC,IAAI,CAAC;AAAA,CACnE;AAKD,SAAS,gBAAgB,CAAC,IAAiB,EAAQ;IACjD,IAAI,CAAC,IAAI,IAAI,CAAC,IAAI,CAAC,GAAG;QAAE,OAAO;IAG/B,QAAQ,EAAE,CAAC,QAAQ,CAAC,IAAI,CAAC,GAAG,CAAC,GAAG;QAC9B,IAAI,EAAE,IAAI,CAAC,IAAI;QACf,OAAO,EAAE,IAAI,CAAC,OAAO,IAAI,IAAI,CAAC,GAAG,EAAE;QACnC,OAAO,EAAE,IAAI,CAAC,OAAO;QACrB,SAAS,EAAE,IAAI,CAAC,SAAS;QACzB,KAAK,EAAE,IAAI,CAAC,KAAK;KAClB,CAAC;AAAA,CACH;AAED,OAAO,EAAE,WAAW,EAAE,YAAY,EAAE,aAAa,EAAE,aAAa,EAAE,cAAc,EAAE,gBAAgB,EAAE,CAAC"}
|
|
@@ -1,10 +1,7 @@
|
|
|
1
|
-
|
|
2
|
-
|
|
3
|
-
*/
|
|
4
|
-
import { CallAIOptions, Message, SchemaStrategy } from "./types";
|
|
5
|
-
declare const PACKAGE_VERSION: any;
|
|
1
|
+
import { AIResult, CallAIOptions, Message, SchemaStrategy } from "./types.js";
|
|
2
|
+
import { PACKAGE_VERSION } from "./version.js";
|
|
6
3
|
declare const FALLBACK_MODEL = "openrouter/auto";
|
|
7
4
|
declare function callAINonStreaming(prompt: string | Message[], options?: CallAIOptions, isRetry?: boolean): Promise<string>;
|
|
8
|
-
declare function extractContent(result:
|
|
9
|
-
declare function extractClaudeResponse(response: Response): Promise<
|
|
10
|
-
export { callAINonStreaming, extractContent, extractClaudeResponse, PACKAGE_VERSION, FALLBACK_MODEL
|
|
5
|
+
declare function extractContent(result: AIResult, schemaStrategy: SchemaStrategy): string;
|
|
6
|
+
declare function extractClaudeResponse(response: Response): Promise<NonNullable<unknown>>;
|
|
7
|
+
export { callAINonStreaming, extractContent, extractClaudeResponse, PACKAGE_VERSION, FALLBACK_MODEL };
|