@jaypie/llm 1.2.5 → 1.2.7
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/cjs/Llm.d.ts +15 -3
- package/dist/cjs/constants.d.ts +47 -47
- package/dist/cjs/index.cjs +172 -65
- package/dist/cjs/index.cjs.map +1 -1
- package/dist/cjs/index.d.ts +1 -1
- package/dist/cjs/operate/adapters/OpenAiAdapter.d.ts +1 -1
- package/dist/cjs/tools/Toolkit.class.d.ts +1 -1
- package/dist/cjs/types/LlmProvider.interface.d.ts +21 -0
- package/dist/esm/Llm.d.ts +15 -3
- package/dist/esm/constants.d.ts +47 -47
- package/dist/esm/index.d.ts +1 -1
- package/dist/esm/index.js +157 -50
- package/dist/esm/index.js.map +1 -1
- package/dist/esm/operate/adapters/OpenAiAdapter.d.ts +1 -1
- package/dist/esm/tools/Toolkit.class.d.ts +1 -1
- package/dist/esm/types/LlmProvider.interface.d.ts +21 -0
- package/package.json +5 -5
package/dist/cjs/Llm.d.ts
CHANGED
|
@@ -1,14 +1,25 @@
|
|
|
1
1
|
import { JsonObject } from "@jaypie/types";
|
|
2
2
|
import { LlmProviderName } from "./constants.js";
|
|
3
|
-
import { LlmHistory, LlmInputMessage, LlmMessageOptions, LlmOperateInput, LlmOperateOptions, LlmOperateResponse, LlmOptions, LlmProvider } from "./types/LlmProvider.interface.js";
|
|
3
|
+
import { LlmFallbackConfig, LlmHistory, LlmInputMessage, LlmMessageOptions, LlmOperateInput, LlmOperateOptions, LlmOperateResponse, LlmOptions, LlmProvider } from "./types/LlmProvider.interface.js";
|
|
4
4
|
import { LlmStreamChunk } from "./types/LlmStreamChunk.interface.js";
|
|
5
5
|
declare class Llm implements LlmProvider {
|
|
6
|
-
private
|
|
6
|
+
private _fallbackConfig?;
|
|
7
7
|
private _llm;
|
|
8
8
|
private _options;
|
|
9
|
+
private _provider;
|
|
9
10
|
constructor(providerName?: LlmProviderName | string, options?: LlmOptions);
|
|
10
11
|
private createProvider;
|
|
11
12
|
send(message: string, options?: LlmMessageOptions): Promise<string | JsonObject>;
|
|
13
|
+
/**
|
|
14
|
+
* Resolves the fallback chain from instance config and per-call options.
|
|
15
|
+
* Per-call options take precedence over instance config.
|
|
16
|
+
* Returns empty array if fallback is disabled.
|
|
17
|
+
*/
|
|
18
|
+
private resolveFallbackChain;
|
|
19
|
+
/**
|
|
20
|
+
* Creates a fallback Llm instance lazily when needed.
|
|
21
|
+
*/
|
|
22
|
+
private createFallbackInstance;
|
|
12
23
|
operate(input: string | LlmHistory | LlmInputMessage | LlmOperateInput, options?: LlmOperateOptions): Promise<LlmOperateResponse>;
|
|
13
24
|
stream(input: string | LlmHistory | LlmInputMessage | LlmOperateInput, options?: LlmOperateOptions): AsyncIterable<LlmStreamChunk>;
|
|
14
25
|
static send(message: string, options?: LlmMessageOptions & {
|
|
@@ -17,8 +28,9 @@ declare class Llm implements LlmProvider {
|
|
|
17
28
|
model?: string;
|
|
18
29
|
}): Promise<string | JsonObject>;
|
|
19
30
|
static operate(input: string | LlmHistory | LlmInputMessage | LlmOperateInput, options?: LlmOperateOptions & {
|
|
20
|
-
llm?: LlmProviderName;
|
|
21
31
|
apiKey?: string;
|
|
32
|
+
fallback?: LlmFallbackConfig[] | false;
|
|
33
|
+
llm?: LlmProviderName;
|
|
22
34
|
model?: string;
|
|
23
35
|
}): Promise<LlmOperateResponse>;
|
|
24
36
|
static stream(input: string | LlmHistory | LlmInputMessage | LlmOperateInput, options?: LlmOperateOptions & {
|
package/dist/cjs/constants.d.ts
CHANGED
|
@@ -1,19 +1,28 @@
|
|
|
1
1
|
export declare const PROVIDER: {
|
|
2
|
-
readonly
|
|
2
|
+
readonly ANTHROPIC: {
|
|
3
|
+
readonly MAX_TOKENS: {
|
|
4
|
+
readonly DEFAULT: 4096;
|
|
5
|
+
};
|
|
3
6
|
readonly MODEL: {
|
|
4
|
-
readonly DEFAULT: "
|
|
5
|
-
readonly
|
|
6
|
-
readonly
|
|
7
|
-
readonly TINY: "
|
|
7
|
+
readonly DEFAULT: "claude-sonnet-4-5";
|
|
8
|
+
readonly LARGE: "claude-opus-4-5";
|
|
9
|
+
readonly SMALL: "claude-sonnet-4-5";
|
|
10
|
+
readonly TINY: "claude-haiku-4-5";
|
|
11
|
+
};
|
|
12
|
+
readonly MODEL_MATCH_WORDS: readonly ["anthropic", "claude", "haiku", "opus", "sonnet"];
|
|
13
|
+
readonly NAME: "anthropic";
|
|
14
|
+
readonly PROMPT: {
|
|
15
|
+
readonly AI: "\n\nAssistant:";
|
|
16
|
+
readonly HUMAN: "\n\nHuman:";
|
|
8
17
|
};
|
|
9
|
-
readonly MODEL_MATCH_WORDS: readonly ["openrouter"];
|
|
10
|
-
readonly NAME: "openrouter";
|
|
11
18
|
readonly ROLE: {
|
|
12
19
|
readonly ASSISTANT: "assistant";
|
|
13
20
|
readonly SYSTEM: "system";
|
|
14
|
-
readonly TOOL: "tool";
|
|
15
21
|
readonly USER: "user";
|
|
16
22
|
};
|
|
23
|
+
readonly TOOLS: {
|
|
24
|
+
readonly SCHEMA_VERSION: "v2";
|
|
25
|
+
};
|
|
17
26
|
};
|
|
18
27
|
readonly GEMINI: {
|
|
19
28
|
readonly MODEL: {
|
|
@@ -29,65 +38,56 @@ export declare const PROVIDER: {
|
|
|
29
38
|
readonly USER: "user";
|
|
30
39
|
};
|
|
31
40
|
};
|
|
32
|
-
readonly
|
|
41
|
+
readonly OPENAI: {
|
|
33
42
|
readonly MODEL: {
|
|
34
|
-
readonly DEFAULT: "
|
|
35
|
-
readonly LARGE: "
|
|
36
|
-
readonly SMALL: "
|
|
37
|
-
readonly TINY: "
|
|
43
|
+
readonly DEFAULT: "gpt-5.2";
|
|
44
|
+
readonly LARGE: "gpt-5.2-pro";
|
|
45
|
+
readonly SMALL: "gpt-5-mini";
|
|
46
|
+
readonly TINY: "gpt-5-nano";
|
|
38
47
|
};
|
|
39
|
-
readonly MODEL_MATCH_WORDS: readonly ["
|
|
40
|
-
readonly NAME: "
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
48
|
+
readonly MODEL_MATCH_WORDS: readonly ["openai", "gpt", RegExp];
|
|
49
|
+
readonly NAME: "openai";
|
|
50
|
+
};
|
|
51
|
+
readonly OPENROUTER: {
|
|
52
|
+
readonly MODEL: {
|
|
53
|
+
readonly DEFAULT: "z-ai/glm-4.7";
|
|
54
|
+
readonly LARGE: "z-ai/glm-4.7";
|
|
55
|
+
readonly SMALL: "z-ai/glm-4.7";
|
|
56
|
+
readonly TINY: "z-ai/glm-4.7";
|
|
44
57
|
};
|
|
58
|
+
readonly MODEL_MATCH_WORDS: readonly ["openrouter"];
|
|
59
|
+
readonly NAME: "openrouter";
|
|
45
60
|
readonly ROLE: {
|
|
46
61
|
readonly ASSISTANT: "assistant";
|
|
47
62
|
readonly SYSTEM: "system";
|
|
63
|
+
readonly TOOL: "tool";
|
|
48
64
|
readonly USER: "user";
|
|
49
65
|
};
|
|
50
|
-
readonly MAX_TOKENS: {
|
|
51
|
-
readonly DEFAULT: 4096;
|
|
52
|
-
};
|
|
53
|
-
readonly TOOLS: {
|
|
54
|
-
readonly SCHEMA_VERSION: "v2";
|
|
55
|
-
};
|
|
56
|
-
};
|
|
57
|
-
readonly OPENAI: {
|
|
58
|
-
readonly MODEL: {
|
|
59
|
-
readonly DEFAULT: "gpt-5.1";
|
|
60
|
-
readonly LARGE: "gpt-5.1";
|
|
61
|
-
readonly SMALL: "gpt-5.1-mini";
|
|
62
|
-
readonly TINY: "gpt-5.1-nano";
|
|
63
|
-
};
|
|
64
|
-
readonly MODEL_MATCH_WORDS: readonly ["openai", "gpt", RegExp];
|
|
65
|
-
readonly NAME: "openai";
|
|
66
66
|
};
|
|
67
67
|
};
|
|
68
68
|
export type LlmProviderName = typeof PROVIDER.ANTHROPIC.NAME | typeof PROVIDER.GEMINI.NAME | typeof PROVIDER.OPENAI.NAME | typeof PROVIDER.OPENROUTER.NAME;
|
|
69
69
|
export declare const DEFAULT: {
|
|
70
70
|
readonly MODEL: {
|
|
71
|
-
readonly BASE: "gpt-5.
|
|
72
|
-
readonly LARGE: "gpt-5.
|
|
73
|
-
readonly SMALL: "gpt-5
|
|
74
|
-
readonly TINY: "gpt-5
|
|
71
|
+
readonly BASE: "gpt-5.2";
|
|
72
|
+
readonly LARGE: "gpt-5.2-pro";
|
|
73
|
+
readonly SMALL: "gpt-5-mini";
|
|
74
|
+
readonly TINY: "gpt-5-nano";
|
|
75
75
|
};
|
|
76
76
|
readonly PROVIDER: {
|
|
77
77
|
readonly MODEL: {
|
|
78
|
-
readonly DEFAULT: "gpt-5.
|
|
79
|
-
readonly LARGE: "gpt-5.
|
|
80
|
-
readonly SMALL: "gpt-5
|
|
81
|
-
readonly TINY: "gpt-5
|
|
78
|
+
readonly DEFAULT: "gpt-5.2";
|
|
79
|
+
readonly LARGE: "gpt-5.2-pro";
|
|
80
|
+
readonly SMALL: "gpt-5-mini";
|
|
81
|
+
readonly TINY: "gpt-5-nano";
|
|
82
82
|
};
|
|
83
83
|
readonly MODEL_MATCH_WORDS: readonly ["openai", "gpt", RegExp];
|
|
84
84
|
readonly NAME: "openai";
|
|
85
85
|
};
|
|
86
86
|
};
|
|
87
87
|
export declare const ALL: {
|
|
88
|
-
readonly BASE: readonly ["claude-sonnet-4-5", "gemini-3-pro-preview", "gpt-5.
|
|
89
|
-
readonly COMBINED: readonly ["claude-sonnet-4-5", "claude-opus-4-5", "claude-sonnet-4-5", "claude-haiku-4-5", "gemini-3-pro-preview", "gemini-3-pro-preview", "gemini-3-flash-preview", "gemini-3-flash-preview", "gpt-5.
|
|
90
|
-
readonly LARGE: readonly ["claude-opus-4-5", "gemini-3-pro-preview", "gpt-5.
|
|
91
|
-
readonly SMALL: readonly ["claude-sonnet-4-5", "gemini-3-flash-preview", "gpt-5
|
|
92
|
-
readonly TINY: readonly ["claude-haiku-4-5", "gemini-3-flash-preview", "gpt-5
|
|
88
|
+
readonly BASE: readonly ["claude-sonnet-4-5", "gemini-3-pro-preview", "gpt-5.2"];
|
|
89
|
+
readonly COMBINED: readonly ["claude-sonnet-4-5", "claude-opus-4-5", "claude-sonnet-4-5", "claude-haiku-4-5", "gemini-3-pro-preview", "gemini-3-pro-preview", "gemini-3-flash-preview", "gemini-3-flash-preview", "gpt-5.2", "gpt-5.2-pro", "gpt-5-mini", "gpt-5-nano"];
|
|
90
|
+
readonly LARGE: readonly ["claude-opus-4-5", "gemini-3-pro-preview", "gpt-5.2-pro"];
|
|
91
|
+
readonly SMALL: readonly ["claude-sonnet-4-5", "gemini-3-flash-preview", "gpt-5-mini"];
|
|
92
|
+
readonly TINY: readonly ["claude-haiku-4-5", "gemini-3-flash-preview", "gpt-5-nano"];
|
|
93
93
|
};
|
package/dist/cjs/index.cjs
CHANGED
|
@@ -1,9 +1,9 @@
|
|
|
1
1
|
'use strict';
|
|
2
2
|
|
|
3
3
|
var errors = require('@jaypie/errors');
|
|
4
|
+
var log$2 = require('@jaypie/logger');
|
|
4
5
|
var v4 = require('zod/v4');
|
|
5
6
|
var kit = require('@jaypie/kit');
|
|
6
|
-
var logger = require('@jaypie/logger');
|
|
7
7
|
var RandomLib = require('random');
|
|
8
8
|
var openai = require('openai');
|
|
9
9
|
var zod = require('openai/helpers/zod');
|
|
@@ -13,49 +13,43 @@ var path = require('path');
|
|
|
13
13
|
var aws = require('@jaypie/aws');
|
|
14
14
|
var openmeteo = require('openmeteo');
|
|
15
15
|
|
|
16
|
-
const
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
// Default uses env var OPENROUTER_MODEL if set, otherwise a reasonable default
|
|
23
|
-
DEFAULT: "z-ai/glm-4.7",
|
|
24
|
-
SMALL: "z-ai/glm-4.7",
|
|
25
|
-
LARGE: "z-ai/glm-4.7",
|
|
26
|
-
TINY: "z-ai/glm-4.7",
|
|
27
|
-
},
|
|
28
|
-
MODEL_MATCH_WORDS: ["openrouter"],
|
|
29
|
-
NAME: "openrouter",
|
|
30
|
-
ROLE: {
|
|
31
|
-
ASSISTANT: "assistant",
|
|
32
|
-
SYSTEM: "system",
|
|
33
|
-
TOOL: "tool",
|
|
34
|
-
USER: "user",
|
|
35
|
-
},
|
|
16
|
+
const FIRST_CLASS_PROVIDER = {
|
|
17
|
+
ANTHROPIC: {
|
|
18
|
+
DEFAULT: "claude-sonnet-4-5",
|
|
19
|
+
LARGE: "claude-opus-4-5",
|
|
20
|
+
SMALL: "claude-sonnet-4-5",
|
|
21
|
+
TINY: "claude-haiku-4-5",
|
|
36
22
|
},
|
|
37
23
|
GEMINI: {
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
24
|
+
DEFAULT: "gemini-3-pro-preview",
|
|
25
|
+
LARGE: "gemini-3-pro-preview",
|
|
26
|
+
SMALL: "gemini-3-flash-preview",
|
|
27
|
+
TINY: "gemini-3-flash-preview",
|
|
28
|
+
},
|
|
29
|
+
OPENAI: {
|
|
30
|
+
DEFAULT: "gpt-5.2",
|
|
31
|
+
LARGE: "gpt-5.2-pro",
|
|
32
|
+
SMALL: "gpt-5-mini",
|
|
33
|
+
TINY: "gpt-5-nano",
|
|
34
|
+
},
|
|
35
|
+
OPENROUTER: {
|
|
36
|
+
DEFAULT: "z-ai/glm-4.7",
|
|
37
|
+
LARGE: "z-ai/glm-4.7",
|
|
38
|
+
SMALL: "z-ai/glm-4.7",
|
|
39
|
+
TINY: "z-ai/glm-4.7",
|
|
51
40
|
},
|
|
41
|
+
};
|
|
42
|
+
const PROVIDER = {
|
|
52
43
|
ANTHROPIC: {
|
|
53
44
|
// https://docs.anthropic.com/en/docs/about-claude/models/overview
|
|
45
|
+
MAX_TOKENS: {
|
|
46
|
+
DEFAULT: 4096,
|
|
47
|
+
},
|
|
54
48
|
MODEL: {
|
|
55
|
-
DEFAULT:
|
|
56
|
-
LARGE:
|
|
57
|
-
SMALL:
|
|
58
|
-
TINY:
|
|
49
|
+
DEFAULT: FIRST_CLASS_PROVIDER.ANTHROPIC.DEFAULT,
|
|
50
|
+
LARGE: FIRST_CLASS_PROVIDER.ANTHROPIC.LARGE,
|
|
51
|
+
SMALL: FIRST_CLASS_PROVIDER.ANTHROPIC.SMALL,
|
|
52
|
+
TINY: FIRST_CLASS_PROVIDER.ANTHROPIC.TINY,
|
|
59
53
|
},
|
|
60
54
|
MODEL_MATCH_WORDS: [
|
|
61
55
|
"anthropic",
|
|
@@ -74,24 +68,56 @@ const PROVIDER = {
|
|
|
74
68
|
SYSTEM: "system",
|
|
75
69
|
USER: "user",
|
|
76
70
|
},
|
|
77
|
-
MAX_TOKENS: {
|
|
78
|
-
DEFAULT: 4096,
|
|
79
|
-
},
|
|
80
71
|
TOOLS: {
|
|
81
72
|
SCHEMA_VERSION: "v2",
|
|
82
73
|
},
|
|
83
74
|
},
|
|
75
|
+
GEMINI: {
|
|
76
|
+
// https://ai.google.dev/gemini-api/docs/models
|
|
77
|
+
MODEL: {
|
|
78
|
+
DEFAULT: FIRST_CLASS_PROVIDER.GEMINI.DEFAULT,
|
|
79
|
+
LARGE: FIRST_CLASS_PROVIDER.GEMINI.LARGE,
|
|
80
|
+
SMALL: FIRST_CLASS_PROVIDER.GEMINI.SMALL,
|
|
81
|
+
TINY: FIRST_CLASS_PROVIDER.GEMINI.TINY,
|
|
82
|
+
},
|
|
83
|
+
MODEL_MATCH_WORDS: ["gemini", "google"],
|
|
84
|
+
NAME: "gemini",
|
|
85
|
+
ROLE: {
|
|
86
|
+
MODEL: "model",
|
|
87
|
+
USER: "user",
|
|
88
|
+
},
|
|
89
|
+
},
|
|
84
90
|
OPENAI: {
|
|
85
91
|
// https://platform.openai.com/docs/models
|
|
86
92
|
MODEL: {
|
|
87
|
-
DEFAULT:
|
|
88
|
-
LARGE:
|
|
89
|
-
SMALL:
|
|
90
|
-
TINY:
|
|
93
|
+
DEFAULT: FIRST_CLASS_PROVIDER.OPENAI.DEFAULT,
|
|
94
|
+
LARGE: FIRST_CLASS_PROVIDER.OPENAI.LARGE,
|
|
95
|
+
SMALL: FIRST_CLASS_PROVIDER.OPENAI.SMALL,
|
|
96
|
+
TINY: FIRST_CLASS_PROVIDER.OPENAI.TINY,
|
|
91
97
|
},
|
|
92
98
|
MODEL_MATCH_WORDS: ["openai", "gpt", /^o\d/],
|
|
93
99
|
NAME: "openai",
|
|
94
100
|
},
|
|
101
|
+
OPENROUTER: {
|
|
102
|
+
// https://openrouter.ai/models
|
|
103
|
+
// OpenRouter provides access to hundreds of models from various providers
|
|
104
|
+
// The model format is: provider/model-name (e.g., "openai/gpt-4", "anthropic/claude-3-opus")
|
|
105
|
+
MODEL: {
|
|
106
|
+
// Default uses env var OPENROUTER_MODEL if set, otherwise a reasonable default
|
|
107
|
+
DEFAULT: FIRST_CLASS_PROVIDER.OPENROUTER.DEFAULT,
|
|
108
|
+
LARGE: FIRST_CLASS_PROVIDER.OPENROUTER.LARGE,
|
|
109
|
+
SMALL: FIRST_CLASS_PROVIDER.OPENROUTER.SMALL,
|
|
110
|
+
TINY: FIRST_CLASS_PROVIDER.OPENROUTER.TINY,
|
|
111
|
+
},
|
|
112
|
+
MODEL_MATCH_WORDS: ["openrouter"],
|
|
113
|
+
NAME: "openrouter",
|
|
114
|
+
ROLE: {
|
|
115
|
+
ASSISTANT: "assistant",
|
|
116
|
+
SYSTEM: "system",
|
|
117
|
+
TOOL: "tool",
|
|
118
|
+
USER: "user",
|
|
119
|
+
},
|
|
120
|
+
},
|
|
95
121
|
};
|
|
96
122
|
// Last: Defaults
|
|
97
123
|
const DEFAULT = {
|
|
@@ -481,7 +507,7 @@ function formatOperateInput(input, options) {
|
|
|
481
507
|
return [input];
|
|
482
508
|
}
|
|
483
509
|
|
|
484
|
-
const getLogger$4 = () =>
|
|
510
|
+
const getLogger$4 = () => log$2.log.lib({ lib: kit.JAYPIE.LIB.LLM });
|
|
485
511
|
const log$1 = getLogger$4();
|
|
486
512
|
|
|
487
513
|
// Turn policy constants
|
|
@@ -2368,16 +2394,16 @@ function convertContentToOpenRouter(content) {
|
|
|
2368
2394
|
}
|
|
2369
2395
|
// Image content - warn and discard
|
|
2370
2396
|
if (item.type === exports.LlmMessageType.InputImage) {
|
|
2371
|
-
|
|
2397
|
+
log$2.log.warn("OpenRouter does not support image uploads; image discarded");
|
|
2372
2398
|
continue;
|
|
2373
2399
|
}
|
|
2374
2400
|
// File/Document content - warn and discard
|
|
2375
2401
|
if (item.type === exports.LlmMessageType.InputFile) {
|
|
2376
|
-
|
|
2402
|
+
log$2.log.warn({ filename: item.filename }, "OpenRouter does not support file uploads; file discarded");
|
|
2377
2403
|
continue;
|
|
2378
2404
|
}
|
|
2379
2405
|
// Unknown type - warn and skip
|
|
2380
|
-
|
|
2406
|
+
log$2.log.warn({ item }, "Unknown content type for OpenRouter; discarded");
|
|
2381
2407
|
}
|
|
2382
2408
|
// If no text parts remain, return empty string to avoid empty array
|
|
2383
2409
|
if (parts.length === 0) {
|
|
@@ -2893,7 +2919,7 @@ class OpenRouterAdapter extends BaseProviderAdapter {
|
|
|
2893
2919
|
const openRouterAdapter = new OpenRouterAdapter();
|
|
2894
2920
|
|
|
2895
2921
|
const DEFAULT_TOOL_TYPE = "function";
|
|
2896
|
-
const log =
|
|
2922
|
+
const log = log$2.log.lib({ lib: kit.JAYPIE.LIB.LLM });
|
|
2897
2923
|
function logToolMessage(message, context) {
|
|
2898
2924
|
log.trace.var({ [context.name]: message });
|
|
2899
2925
|
}
|
|
@@ -4495,7 +4521,7 @@ async function loadSdk$2() {
|
|
|
4495
4521
|
}
|
|
4496
4522
|
}
|
|
4497
4523
|
// Logger
|
|
4498
|
-
const getLogger$3 = () =>
|
|
4524
|
+
const getLogger$3 = () => log$2.log.lib({ lib: kit.JAYPIE.LIB.LLM });
|
|
4499
4525
|
// Client initialization
|
|
4500
4526
|
async function initializeClient$3({ apiKey, } = {}) {
|
|
4501
4527
|
const logger = getLogger$3();
|
|
@@ -4534,7 +4560,7 @@ function prepareMessages$3(message, { data, placeholders } = {}) {
|
|
|
4534
4560
|
}
|
|
4535
4561
|
// Basic text completion
|
|
4536
4562
|
async function createTextCompletion$1(client, messages, model, systemMessage) {
|
|
4537
|
-
|
|
4563
|
+
log$2.log.trace("Using text output (unstructured)");
|
|
4538
4564
|
const params = {
|
|
4539
4565
|
model,
|
|
4540
4566
|
messages,
|
|
@@ -4543,17 +4569,17 @@ async function createTextCompletion$1(client, messages, model, systemMessage) {
|
|
|
4543
4569
|
// Add system instruction if provided
|
|
4544
4570
|
if (systemMessage) {
|
|
4545
4571
|
params.system = systemMessage;
|
|
4546
|
-
|
|
4572
|
+
log$2.log.trace(`System message: ${systemMessage.length} characters`);
|
|
4547
4573
|
}
|
|
4548
4574
|
const response = await client.messages.create(params);
|
|
4549
4575
|
const firstContent = response.content[0];
|
|
4550
4576
|
const text = firstContent && "text" in firstContent ? firstContent.text : "";
|
|
4551
|
-
|
|
4577
|
+
log$2.log.trace(`Assistant reply: ${text.length} characters`);
|
|
4552
4578
|
return text;
|
|
4553
4579
|
}
|
|
4554
4580
|
// Structured output completion
|
|
4555
4581
|
async function createStructuredCompletion$1(client, messages, model, responseSchema, systemMessage) {
|
|
4556
|
-
|
|
4582
|
+
log$2.log.trace("Using structured output");
|
|
4557
4583
|
// Get the JSON schema for the response
|
|
4558
4584
|
const schema = responseSchema instanceof v4.z.ZodType
|
|
4559
4585
|
? responseSchema
|
|
@@ -4586,7 +4612,7 @@ async function createStructuredCompletion$1(client, messages, model, responseSch
|
|
|
4586
4612
|
if (!schema.parse(result)) {
|
|
4587
4613
|
throw new Error(`JSON response from Anthropic does not match schema: ${responseText}`);
|
|
4588
4614
|
}
|
|
4589
|
-
|
|
4615
|
+
log$2.log.trace("Received structured response", { result });
|
|
4590
4616
|
return result;
|
|
4591
4617
|
}
|
|
4592
4618
|
catch {
|
|
@@ -4597,7 +4623,7 @@ async function createStructuredCompletion$1(client, messages, model, responseSch
|
|
|
4597
4623
|
throw new Error("Failed to parse structured response from Anthropic");
|
|
4598
4624
|
}
|
|
4599
4625
|
catch (error) {
|
|
4600
|
-
|
|
4626
|
+
log$2.log.error("Error creating structured completion", { error });
|
|
4601
4627
|
throw error;
|
|
4602
4628
|
}
|
|
4603
4629
|
}
|
|
@@ -4711,7 +4737,7 @@ async function loadSdk$1() {
|
|
|
4711
4737
|
}
|
|
4712
4738
|
}
|
|
4713
4739
|
// Logger
|
|
4714
|
-
const getLogger$2 = () =>
|
|
4740
|
+
const getLogger$2 = () => log$2.log.lib({ lib: kit.JAYPIE.LIB.LLM });
|
|
4715
4741
|
// Client initialization
|
|
4716
4742
|
async function initializeClient$2({ apiKey, } = {}) {
|
|
4717
4743
|
const logger = getLogger$2();
|
|
@@ -4851,7 +4877,7 @@ class GeminiProvider {
|
|
|
4851
4877
|
}
|
|
4852
4878
|
|
|
4853
4879
|
// Logger
|
|
4854
|
-
const getLogger$1 = () =>
|
|
4880
|
+
const getLogger$1 = () => log$2.log.lib({ lib: kit.JAYPIE.LIB.LLM });
|
|
4855
4881
|
// Client initialization
|
|
4856
4882
|
async function initializeClient$1({ apiKey, } = {}) {
|
|
4857
4883
|
const logger = getLogger$1();
|
|
@@ -5035,7 +5061,7 @@ async function loadSdk() {
|
|
|
5035
5061
|
}
|
|
5036
5062
|
}
|
|
5037
5063
|
// Logger
|
|
5038
|
-
const getLogger = () =>
|
|
5064
|
+
const getLogger = () => log$2.log.lib({ lib: kit.JAYPIE.LIB.LLM });
|
|
5039
5065
|
// Client initialization
|
|
5040
5066
|
async function initializeClient({ apiKey, } = {}) {
|
|
5041
5067
|
const logger = getLogger();
|
|
@@ -5185,7 +5211,7 @@ class OpenRouterProvider {
|
|
|
5185
5211
|
|
|
5186
5212
|
class Llm {
|
|
5187
5213
|
constructor(providerName = DEFAULT.PROVIDER.NAME, options = {}) {
|
|
5188
|
-
const { model } = options;
|
|
5214
|
+
const { fallback, model } = options;
|
|
5189
5215
|
let finalProvider = providerName;
|
|
5190
5216
|
let finalModel = model;
|
|
5191
5217
|
if (model) {
|
|
@@ -5214,6 +5240,7 @@ class Llm {
|
|
|
5214
5240
|
finalModel = undefined;
|
|
5215
5241
|
}
|
|
5216
5242
|
}
|
|
5243
|
+
this._fallbackConfig = fallback;
|
|
5217
5244
|
this._provider = finalProvider;
|
|
5218
5245
|
this._options = { ...options, model: finalModel };
|
|
5219
5246
|
this._llm = this.createProvider(finalProvider, this._options);
|
|
@@ -5242,11 +5269,81 @@ class Llm {
|
|
|
5242
5269
|
async send(message, options) {
|
|
5243
5270
|
return this._llm.send(message, options);
|
|
5244
5271
|
}
|
|
5272
|
+
/**
|
|
5273
|
+
* Resolves the fallback chain from instance config and per-call options.
|
|
5274
|
+
* Per-call options take precedence over instance config.
|
|
5275
|
+
* Returns empty array if fallback is disabled.
|
|
5276
|
+
*/
|
|
5277
|
+
resolveFallbackChain(options) {
|
|
5278
|
+
// Per-call `fallback: false` disables fallback entirely
|
|
5279
|
+
if (options.fallback === false) {
|
|
5280
|
+
return [];
|
|
5281
|
+
}
|
|
5282
|
+
// Per-call fallback array overrides instance config
|
|
5283
|
+
if (Array.isArray(options.fallback)) {
|
|
5284
|
+
return options.fallback;
|
|
5285
|
+
}
|
|
5286
|
+
// Use instance config if available
|
|
5287
|
+
return this._fallbackConfig || [];
|
|
5288
|
+
}
|
|
5289
|
+
/**
|
|
5290
|
+
* Creates a fallback Llm instance lazily when needed.
|
|
5291
|
+
*/
|
|
5292
|
+
createFallbackInstance(config) {
|
|
5293
|
+
return new Llm(config.provider, {
|
|
5294
|
+
apiKey: config.apiKey,
|
|
5295
|
+
model: config.model,
|
|
5296
|
+
});
|
|
5297
|
+
}
|
|
5245
5298
|
async operate(input, options = {}) {
|
|
5246
5299
|
if (!this._llm.operate) {
|
|
5247
5300
|
throw new errors.NotImplementedError(`Provider ${this._provider} does not support operate method`);
|
|
5248
5301
|
}
|
|
5249
|
-
|
|
5302
|
+
const fallbackChain = this.resolveFallbackChain(options);
|
|
5303
|
+
const optionsWithoutFallback = { ...options, fallback: false };
|
|
5304
|
+
let lastError;
|
|
5305
|
+
let attempts = 0;
|
|
5306
|
+
// Try primary provider first
|
|
5307
|
+
attempts++;
|
|
5308
|
+
try {
|
|
5309
|
+
const response = await this._llm.operate(input, optionsWithoutFallback);
|
|
5310
|
+
return {
|
|
5311
|
+
...response,
|
|
5312
|
+
fallbackAttempts: attempts,
|
|
5313
|
+
fallbackUsed: false,
|
|
5314
|
+
provider: response.provider || this._provider,
|
|
5315
|
+
};
|
|
5316
|
+
}
|
|
5317
|
+
catch (error) {
|
|
5318
|
+
lastError = error;
|
|
5319
|
+
log$2.warn(`Provider ${this._provider} failed`, {
|
|
5320
|
+
error: lastError.message,
|
|
5321
|
+
fallbacksRemaining: fallbackChain.length,
|
|
5322
|
+
});
|
|
5323
|
+
}
|
|
5324
|
+
// Try fallback providers
|
|
5325
|
+
for (const fallbackConfig of fallbackChain) {
|
|
5326
|
+
attempts++;
|
|
5327
|
+
try {
|
|
5328
|
+
const fallbackInstance = this.createFallbackInstance(fallbackConfig);
|
|
5329
|
+
const response = await fallbackInstance.operate(input, optionsWithoutFallback);
|
|
5330
|
+
return {
|
|
5331
|
+
...response,
|
|
5332
|
+
fallbackAttempts: attempts,
|
|
5333
|
+
fallbackUsed: true,
|
|
5334
|
+
provider: response.provider || fallbackConfig.provider,
|
|
5335
|
+
};
|
|
5336
|
+
}
|
|
5337
|
+
catch (error) {
|
|
5338
|
+
lastError = error;
|
|
5339
|
+
log$2.warn(`Fallback provider ${fallbackConfig.provider} failed`, {
|
|
5340
|
+
error: lastError.message,
|
|
5341
|
+
fallbacksRemaining: fallbackChain.length - attempts + 1,
|
|
5342
|
+
});
|
|
5343
|
+
}
|
|
5344
|
+
}
|
|
5345
|
+
// All providers failed, throw the last error
|
|
5346
|
+
throw lastError;
|
|
5250
5347
|
}
|
|
5251
5348
|
async *stream(input, options = {}) {
|
|
5252
5349
|
if (!this._llm.stream) {
|
|
@@ -5260,7 +5357,7 @@ class Llm {
|
|
|
5260
5357
|
return instance.send(message, messageOptions);
|
|
5261
5358
|
}
|
|
5262
5359
|
static async operate(input, options) {
|
|
5263
|
-
const {
|
|
5360
|
+
const { apiKey, fallback, llm, model, ...operateOptions } = options || {};
|
|
5264
5361
|
let finalLlm = llm;
|
|
5265
5362
|
let finalModel = model;
|
|
5266
5363
|
if (!llm && model) {
|
|
@@ -5277,8 +5374,18 @@ class Llm {
|
|
|
5277
5374
|
finalModel = undefined;
|
|
5278
5375
|
}
|
|
5279
5376
|
}
|
|
5280
|
-
|
|
5281
|
-
|
|
5377
|
+
// Resolve fallback for static method: pass to instance if array, pass to operate options if false
|
|
5378
|
+
const instanceFallback = Array.isArray(fallback) ? fallback : undefined;
|
|
5379
|
+
const operateFallback = fallback === false ? false : undefined;
|
|
5380
|
+
const instance = new Llm(finalLlm, {
|
|
5381
|
+
apiKey,
|
|
5382
|
+
fallback: instanceFallback,
|
|
5383
|
+
model: finalModel,
|
|
5384
|
+
});
|
|
5385
|
+
return instance.operate(input, {
|
|
5386
|
+
...operateOptions,
|
|
5387
|
+
...(operateFallback !== undefined && { fallback: operateFallback }),
|
|
5388
|
+
});
|
|
5282
5389
|
}
|
|
5283
5390
|
static stream(input, options) {
|
|
5284
5391
|
const { llm, apiKey, model, ...streamOptions } = options || {};
|