lynkr 7.2.5 → 8.0.1
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 +3 -3
- package/config/model-tiers.json +89 -0
- package/install.sh +6 -1
- package/package.json +4 -2
- package/scripts/setup.js +0 -1
- package/src/agents/executor.js +14 -6
- package/src/api/middleware/session.js +15 -2
- package/src/api/openai-router.js +162 -37
- package/src/api/providers-handler.js +15 -1
- package/src/api/router.js +107 -2
- package/src/budget/index.js +4 -3
- package/src/clients/databricks.js +431 -234
- package/src/clients/gpt-utils.js +181 -0
- package/src/clients/ollama-utils.js +66 -140
- package/src/clients/routing.js +0 -1
- package/src/clients/standard-tools.js +99 -3
- package/src/config/index.js +133 -35
- package/src/context/toon.js +173 -0
- package/src/logger/index.js +23 -0
- package/src/orchestrator/index.js +688 -213
- package/src/routing/agentic-detector.js +320 -0
- package/src/routing/complexity-analyzer.js +202 -2
- package/src/routing/cost-optimizer.js +305 -0
- package/src/routing/index.js +168 -159
- package/src/routing/model-tiers.js +365 -0
- package/src/server.js +4 -14
- package/src/sessions/cleanup.js +3 -3
- package/src/sessions/record.js +10 -1
- package/src/sessions/store.js +7 -2
- package/src/tools/agent-task.js +48 -1
- package/src/tools/index.js +19 -2
- package/src/tools/lazy-loader.js +7 -0
- package/src/tools/tinyfish.js +358 -0
- package/src/tools/truncate.js +1 -0
- package/.github/FUNDING.yml +0 -15
- package/.github/workflows/README.md +0 -215
- package/.github/workflows/ci.yml +0 -69
- package/.github/workflows/index.yml +0 -62
- package/.github/workflows/web-tools-tests.yml +0 -56
- package/CITATIONS.bib +0 -6
- package/CLAWROUTER_ROUTING_PLAN.md +0 -910
- package/DEPLOYMENT.md +0 -1001
- package/LYNKR-TUI-PLAN.md +0 -984
- package/PERFORMANCE-REPORT.md +0 -866
- package/PLAN-per-client-model-routing.md +0 -252
- package/ROUTER_COMPARISON.md +0 -173
- package/TIER_ROUTING_PLAN.md +0 -771
- package/docs/42642f749da6234f41b6b425c3bb07c9.txt +0 -1
- package/docs/BingSiteAuth.xml +0 -4
- package/docs/docs-style.css +0 -478
- package/docs/docs.html +0 -197
- package/docs/google5be250e608e6da39.html +0 -1
- package/docs/index.html +0 -577
- package/docs/index.md +0 -577
- package/docs/robots.txt +0 -4
- package/docs/sitemap.xml +0 -44
- package/docs/style.css +0 -1223
- package/documentation/README.md +0 -100
- package/documentation/api.md +0 -806
- package/documentation/claude-code-cli.md +0 -672
- package/documentation/codex-cli.md +0 -397
- package/documentation/contributing.md +0 -571
- package/documentation/cursor-integration.md +0 -731
- package/documentation/docker.md +0 -867
- package/documentation/embeddings.md +0 -760
- package/documentation/faq.md +0 -659
- package/documentation/features.md +0 -396
- package/documentation/headroom.md +0 -519
- package/documentation/installation.md +0 -706
- package/documentation/memory-system.md +0 -476
- package/documentation/production.md +0 -601
- package/documentation/providers.md +0 -906
- package/documentation/testing.md +0 -629
- package/documentation/token-optimization.md +0 -323
- package/documentation/tools.md +0 -697
- package/documentation/troubleshooting.md +0 -893
- package/final-test.js +0 -33
- package/headroom-sidecar/config.py +0 -93
- package/headroom-sidecar/requirements.txt +0 -14
- package/headroom-sidecar/server.py +0 -451
- package/monitor-agents.sh +0 -31
- package/scripts/audit-log-reader.js +0 -399
- package/scripts/compact-dictionary.js +0 -204
- package/scripts/test-deduplication.js +0 -448
- package/src/db/database.sqlite +0 -0
- package/test/README.md +0 -212
- package/test/azure-openai-config.test.js +0 -204
- package/test/azure-openai-error-resilience.test.js +0 -238
- package/test/azure-openai-format-conversion.test.js +0 -354
- package/test/azure-openai-integration.test.js +0 -281
- package/test/azure-openai-routing.test.js +0 -177
- package/test/azure-openai-streaming.test.js +0 -171
- package/test/bedrock-integration.test.js +0 -471
- package/test/comprehensive-test-suite.js +0 -928
- package/test/config-validation.test.js +0 -207
- package/test/cursor-integration.test.js +0 -484
- package/test/format-conversion.test.js +0 -578
- package/test/hybrid-routing-integration.test.js +0 -254
- package/test/hybrid-routing-performance.test.js +0 -418
- package/test/llamacpp-integration.test.js +0 -863
- package/test/lmstudio-integration.test.js +0 -335
- package/test/memory/extractor.test.js +0 -398
- package/test/memory/retriever.test.js +0 -613
- package/test/memory/retriever.test.js.bak +0 -585
- package/test/memory/search.test.js +0 -537
- package/test/memory/search.test.js.bak +0 -389
- package/test/memory/store.test.js +0 -344
- package/test/memory/store.test.js.bak +0 -312
- package/test/memory/surprise.test.js +0 -300
- package/test/memory-performance.test.js +0 -472
- package/test/openai-integration.test.js +0 -686
- package/test/openrouter-error-resilience.test.js +0 -418
- package/test/passthrough-mode.test.js +0 -385
- package/test/performance-benchmark.js +0 -351
- package/test/performance-tests.js +0 -528
- package/test/routing.test.js +0 -219
- package/test/web-tools.test.js +0 -329
- package/test-agents-simple.js +0 -43
- package/test-cli-connection.sh +0 -33
- package/test-learning-unit.js +0 -126
- package/test-learning.js +0 -112
- package/test-parallel-agents.sh +0 -124
- package/test-parallel-direct.js +0 -155
- package/test-subagents.sh +0 -117
|
@@ -1,471 +0,0 @@
|
|
|
1
|
-
const assert = require("assert");
|
|
2
|
-
const { describe, it, beforeEach, afterEach } = require("node:test");
|
|
3
|
-
|
|
4
|
-
describe("AWS Bedrock Integration", () => {
|
|
5
|
-
let originalEnv;
|
|
6
|
-
|
|
7
|
-
beforeEach(() => {
|
|
8
|
-
originalEnv = { ...process.env };
|
|
9
|
-
|
|
10
|
-
// Clear module cache
|
|
11
|
-
delete require.cache[require.resolve("../src/config")];
|
|
12
|
-
delete require.cache[require.resolve("../src/clients/routing")];
|
|
13
|
-
delete require.cache[require.resolve("../src/clients/bedrock-utils")];
|
|
14
|
-
});
|
|
15
|
-
|
|
16
|
-
afterEach(() => {
|
|
17
|
-
process.env = originalEnv;
|
|
18
|
-
});
|
|
19
|
-
|
|
20
|
-
describe("Configuration", () => {
|
|
21
|
-
it("should accept bedrock as a valid MODEL_PROVIDER", () => {
|
|
22
|
-
process.env.MODEL_PROVIDER = "bedrock";
|
|
23
|
-
process.env.AWS_ACCESS_KEY_ID = "AKIATEST123";
|
|
24
|
-
process.env.AWS_SECRET_ACCESS_KEY = "testSecretKey123";
|
|
25
|
-
|
|
26
|
-
const config = require("../src/config");
|
|
27
|
-
assert.strictEqual(config.modelProvider.type, "bedrock");
|
|
28
|
-
});
|
|
29
|
-
|
|
30
|
-
it("should throw error when AWS credentials are missing", () => {
|
|
31
|
-
process.env.MODEL_PROVIDER = "bedrock";
|
|
32
|
-
// Set to empty string to override .env file values
|
|
33
|
-
process.env.AWS_ACCESS_KEY_ID = "";
|
|
34
|
-
process.env.AWS_SECRET_ACCESS_KEY = "";
|
|
35
|
-
|
|
36
|
-
assert.throws(
|
|
37
|
-
() => require("../src/config"),
|
|
38
|
-
/AWS Bedrock requires AWS_ACCESS_KEY_ID and AWS_SECRET_ACCESS_KEY/
|
|
39
|
-
);
|
|
40
|
-
});
|
|
41
|
-
|
|
42
|
-
it("should use default region (us-east-1)", () => {
|
|
43
|
-
process.env.MODEL_PROVIDER = "bedrock";
|
|
44
|
-
process.env.AWS_ACCESS_KEY_ID = "AKIATEST123";
|
|
45
|
-
process.env.AWS_SECRET_ACCESS_KEY = "testSecretKey123";
|
|
46
|
-
process.env.AWS_BEDROCK_REGION = ""; // Override .env value
|
|
47
|
-
process.env.AWS_REGION = ""; // Override .env value
|
|
48
|
-
|
|
49
|
-
const config = require("../src/config");
|
|
50
|
-
assert.strictEqual(config.bedrock.region, "us-east-1");
|
|
51
|
-
});
|
|
52
|
-
|
|
53
|
-
it("should use custom region when AWS_BEDROCK_REGION is set", () => {
|
|
54
|
-
process.env.MODEL_PROVIDER = "bedrock";
|
|
55
|
-
process.env.AWS_ACCESS_KEY_ID = "AKIATEST123";
|
|
56
|
-
process.env.AWS_SECRET_ACCESS_KEY = "testSecretKey123";
|
|
57
|
-
process.env.AWS_BEDROCK_REGION = "us-west-2";
|
|
58
|
-
|
|
59
|
-
const config = require("../src/config");
|
|
60
|
-
assert.strictEqual(config.bedrock.region, "us-west-2");
|
|
61
|
-
});
|
|
62
|
-
|
|
63
|
-
it("should use AWS_REGION as fallback for region", () => {
|
|
64
|
-
process.env.MODEL_PROVIDER = "bedrock";
|
|
65
|
-
process.env.AWS_ACCESS_KEY_ID = "AKIATEST123";
|
|
66
|
-
process.env.AWS_SECRET_ACCESS_KEY = "testSecretKey123";
|
|
67
|
-
process.env.AWS_BEDROCK_REGION = ""; // Override .env value
|
|
68
|
-
process.env.AWS_REGION = "ap-southeast-1";
|
|
69
|
-
|
|
70
|
-
const config = require("../src/config");
|
|
71
|
-
assert.strictEqual(config.bedrock.region, "ap-southeast-1");
|
|
72
|
-
});
|
|
73
|
-
|
|
74
|
-
it("should use default model ID", () => {
|
|
75
|
-
process.env.MODEL_PROVIDER = "bedrock";
|
|
76
|
-
process.env.AWS_ACCESS_KEY_ID = "AKIATEST123";
|
|
77
|
-
process.env.AWS_SECRET_ACCESS_KEY = "testSecretKey123";
|
|
78
|
-
process.env.AWS_BEDROCK_MODEL_ID = ""; // Override .env value
|
|
79
|
-
|
|
80
|
-
const config = require("../src/config");
|
|
81
|
-
assert.strictEqual(config.bedrock.modelId, "anthropic.claude-3-5-sonnet-20241022-v2:0");
|
|
82
|
-
});
|
|
83
|
-
|
|
84
|
-
it("should use custom model ID when AWS_BEDROCK_MODEL_ID is set", () => {
|
|
85
|
-
process.env.MODEL_PROVIDER = "bedrock";
|
|
86
|
-
process.env.AWS_ACCESS_KEY_ID = "AKIATEST123";
|
|
87
|
-
process.env.AWS_SECRET_ACCESS_KEY = "testSecretKey123";
|
|
88
|
-
process.env.AWS_BEDROCK_MODEL_ID = "anthropic.claude-3-opus-20240229-v1:0";
|
|
89
|
-
|
|
90
|
-
const config = require("../src/config");
|
|
91
|
-
assert.strictEqual(config.bedrock.modelId, "anthropic.claude-3-opus-20240229-v1:0");
|
|
92
|
-
});
|
|
93
|
-
});
|
|
94
|
-
|
|
95
|
-
describe("Model Family Detection", () => {
|
|
96
|
-
it("should detect claude family", () => {
|
|
97
|
-
process.env.MODEL_PROVIDER = "databricks";
|
|
98
|
-
process.env.DATABRICKS_API_KEY = "test";
|
|
99
|
-
process.env.DATABRICKS_API_BASE = "http://test.com";
|
|
100
|
-
|
|
101
|
-
const { detectModelFamily } = require("../src/clients/bedrock-utils");
|
|
102
|
-
assert.strictEqual(
|
|
103
|
-
detectModelFamily("anthropic.claude-3-5-sonnet-20241022-v2:0"),
|
|
104
|
-
"claude"
|
|
105
|
-
);
|
|
106
|
-
});
|
|
107
|
-
|
|
108
|
-
it("should detect claude family from global inference profile", () => {
|
|
109
|
-
process.env.MODEL_PROVIDER = "databricks";
|
|
110
|
-
process.env.DATABRICKS_API_KEY = "test";
|
|
111
|
-
process.env.DATABRICKS_API_BASE = "http://test.com";
|
|
112
|
-
|
|
113
|
-
const { detectModelFamily } = require("../src/clients/bedrock-utils");
|
|
114
|
-
assert.strictEqual(
|
|
115
|
-
detectModelFamily("global.anthropic.claude-sonnet-4-5-20250929-v1:0"),
|
|
116
|
-
"claude"
|
|
117
|
-
);
|
|
118
|
-
});
|
|
119
|
-
|
|
120
|
-
it("should detect claude family from US inference profile", () => {
|
|
121
|
-
process.env.MODEL_PROVIDER = "databricks";
|
|
122
|
-
process.env.DATABRICKS_API_KEY = "test";
|
|
123
|
-
process.env.DATABRICKS_API_BASE = "http://test.com";
|
|
124
|
-
|
|
125
|
-
const { detectModelFamily } = require("../src/clients/bedrock-utils");
|
|
126
|
-
assert.strictEqual(
|
|
127
|
-
detectModelFamily("us.anthropic.claude-sonnet-4-5-20250929-v1:0"),
|
|
128
|
-
"claude"
|
|
129
|
-
);
|
|
130
|
-
});
|
|
131
|
-
|
|
132
|
-
it("should detect titan family", () => {
|
|
133
|
-
process.env.MODEL_PROVIDER = "databricks";
|
|
134
|
-
process.env.DATABRICKS_API_KEY = "test";
|
|
135
|
-
process.env.DATABRICKS_API_BASE = "http://test.com";
|
|
136
|
-
|
|
137
|
-
const { detectModelFamily } = require("../src/clients/bedrock-utils");
|
|
138
|
-
assert.strictEqual(
|
|
139
|
-
detectModelFamily("amazon.titan-text-express-v1"),
|
|
140
|
-
"titan"
|
|
141
|
-
);
|
|
142
|
-
});
|
|
143
|
-
|
|
144
|
-
it("should detect llama family", () => {
|
|
145
|
-
process.env.MODEL_PROVIDER = "databricks";
|
|
146
|
-
process.env.DATABRICKS_API_KEY = "test";
|
|
147
|
-
process.env.DATABRICKS_API_BASE = "http://test.com";
|
|
148
|
-
|
|
149
|
-
const { detectModelFamily } = require("../src/clients/bedrock-utils");
|
|
150
|
-
assert.strictEqual(
|
|
151
|
-
detectModelFamily("meta.llama3-70b-instruct-v1:0"),
|
|
152
|
-
"llama"
|
|
153
|
-
);
|
|
154
|
-
});
|
|
155
|
-
|
|
156
|
-
it("should detect jurassic family", () => {
|
|
157
|
-
process.env.MODEL_PROVIDER = "databricks";
|
|
158
|
-
process.env.DATABRICKS_API_KEY = "test";
|
|
159
|
-
process.env.DATABRICKS_API_BASE = "http://test.com";
|
|
160
|
-
|
|
161
|
-
const { detectModelFamily } = require("../src/clients/bedrock-utils");
|
|
162
|
-
assert.strictEqual(
|
|
163
|
-
detectModelFamily("ai21.j2-ultra-v1"),
|
|
164
|
-
"jurassic"
|
|
165
|
-
);
|
|
166
|
-
});
|
|
167
|
-
|
|
168
|
-
it("should detect cohere family", () => {
|
|
169
|
-
process.env.MODEL_PROVIDER = "databricks";
|
|
170
|
-
process.env.DATABRICKS_API_KEY = "test";
|
|
171
|
-
process.env.DATABRICKS_API_BASE = "http://test.com";
|
|
172
|
-
|
|
173
|
-
const { detectModelFamily } = require("../src/clients/bedrock-utils");
|
|
174
|
-
assert.strictEqual(
|
|
175
|
-
detectModelFamily("cohere.command-text-v14"),
|
|
176
|
-
"cohere"
|
|
177
|
-
);
|
|
178
|
-
});
|
|
179
|
-
|
|
180
|
-
it("should detect mistral family", () => {
|
|
181
|
-
process.env.MODEL_PROVIDER = "databricks";
|
|
182
|
-
process.env.DATABRICKS_API_KEY = "test";
|
|
183
|
-
process.env.DATABRICKS_API_BASE = "http://test.com";
|
|
184
|
-
|
|
185
|
-
const { detectModelFamily } = require("../src/clients/bedrock-utils");
|
|
186
|
-
assert.strictEqual(
|
|
187
|
-
detectModelFamily("mistral.mistral-7b-instruct-v0:2"),
|
|
188
|
-
"mistral"
|
|
189
|
-
);
|
|
190
|
-
});
|
|
191
|
-
|
|
192
|
-
it("should throw error for unsupported model", () => {
|
|
193
|
-
process.env.MODEL_PROVIDER = "databricks";
|
|
194
|
-
process.env.DATABRICKS_API_KEY = "test";
|
|
195
|
-
process.env.DATABRICKS_API_BASE = "http://test.com";
|
|
196
|
-
|
|
197
|
-
const { detectModelFamily } = require("../src/clients/bedrock-utils");
|
|
198
|
-
assert.throws(
|
|
199
|
-
() => detectModelFamily("unknown.model-v1"),
|
|
200
|
-
/Unsupported Bedrock model/
|
|
201
|
-
);
|
|
202
|
-
});
|
|
203
|
-
});
|
|
204
|
-
|
|
205
|
-
describe("Format Conversion - Request", () => {
|
|
206
|
-
it("should keep Claude requests in Anthropic format", () => {
|
|
207
|
-
process.env.MODEL_PROVIDER = "databricks";
|
|
208
|
-
process.env.DATABRICKS_API_KEY = "test";
|
|
209
|
-
process.env.DATABRICKS_API_BASE = "http://test.com";
|
|
210
|
-
|
|
211
|
-
const { convertAnthropicToBedrockFormat } = require("../src/clients/bedrock-utils");
|
|
212
|
-
|
|
213
|
-
const anthropicBody = {
|
|
214
|
-
messages: [{ role: "user", content: "Hello" }],
|
|
215
|
-
max_tokens: 1024,
|
|
216
|
-
temperature: 0.7,
|
|
217
|
-
};
|
|
218
|
-
|
|
219
|
-
const result = convertAnthropicToBedrockFormat(anthropicBody, "claude");
|
|
220
|
-
|
|
221
|
-
assert.strictEqual(result.anthropic_version, "bedrock-2023-05-31");
|
|
222
|
-
assert.strictEqual(result.max_tokens, 1024);
|
|
223
|
-
assert.strictEqual(result.temperature, 0.7);
|
|
224
|
-
assert.deepStrictEqual(result.messages, anthropicBody.messages);
|
|
225
|
-
});
|
|
226
|
-
|
|
227
|
-
it("should convert to Titan format", () => {
|
|
228
|
-
process.env.MODEL_PROVIDER = "databricks";
|
|
229
|
-
process.env.DATABRICKS_API_KEY = "test";
|
|
230
|
-
process.env.DATABRICKS_API_BASE = "http://test.com";
|
|
231
|
-
|
|
232
|
-
const { convertAnthropicToBedrockFormat } = require("../src/clients/bedrock-utils");
|
|
233
|
-
|
|
234
|
-
const anthropicBody = {
|
|
235
|
-
messages: [{ role: "user", content: "Hello" }],
|
|
236
|
-
max_tokens: 1024,
|
|
237
|
-
temperature: 0.8,
|
|
238
|
-
};
|
|
239
|
-
|
|
240
|
-
const result = convertAnthropicToBedrockFormat(anthropicBody, "titan");
|
|
241
|
-
|
|
242
|
-
assert.strictEqual(result.textGenerationConfig.maxTokenCount, 1024);
|
|
243
|
-
assert.strictEqual(result.textGenerationConfig.temperature, 0.8);
|
|
244
|
-
assert.ok(result.inputText.includes("Human: Hello"));
|
|
245
|
-
});
|
|
246
|
-
|
|
247
|
-
it("should convert to Llama format", () => {
|
|
248
|
-
process.env.MODEL_PROVIDER = "databricks";
|
|
249
|
-
process.env.DATABRICKS_API_KEY = "test";
|
|
250
|
-
process.env.DATABRICKS_API_BASE = "http://test.com";
|
|
251
|
-
|
|
252
|
-
const { convertAnthropicToBedrockFormat } = require("../src/clients/bedrock-utils");
|
|
253
|
-
|
|
254
|
-
const anthropicBody = {
|
|
255
|
-
messages: [{ role: "user", content: "Test" }],
|
|
256
|
-
max_tokens: 512,
|
|
257
|
-
temperature: 0.9,
|
|
258
|
-
};
|
|
259
|
-
|
|
260
|
-
const result = convertAnthropicToBedrockFormat(anthropicBody, "llama");
|
|
261
|
-
|
|
262
|
-
assert.strictEqual(result.max_gen_len, 512);
|
|
263
|
-
assert.strictEqual(result.temperature, 0.9);
|
|
264
|
-
assert.ok(result.prompt.includes("Human: Test"));
|
|
265
|
-
});
|
|
266
|
-
|
|
267
|
-
it("should convert to Jurassic format", () => {
|
|
268
|
-
process.env.MODEL_PROVIDER = "databricks";
|
|
269
|
-
process.env.DATABRICKS_API_KEY = "test";
|
|
270
|
-
process.env.DATABRICKS_API_BASE = "http://test.com";
|
|
271
|
-
|
|
272
|
-
const { convertAnthropicToBedrockFormat } = require("../src/clients/bedrock-utils");
|
|
273
|
-
|
|
274
|
-
const anthropicBody = {
|
|
275
|
-
messages: [{ role: "user", content: "Test" }],
|
|
276
|
-
max_tokens: 200,
|
|
277
|
-
temperature: 0.7,
|
|
278
|
-
};
|
|
279
|
-
|
|
280
|
-
const result = convertAnthropicToBedrockFormat(anthropicBody, "jurassic");
|
|
281
|
-
|
|
282
|
-
assert.strictEqual(result.maxTokens, 200);
|
|
283
|
-
assert.strictEqual(result.temperature, 0.7);
|
|
284
|
-
assert.ok(result.prompt.includes("Human: Test"));
|
|
285
|
-
});
|
|
286
|
-
});
|
|
287
|
-
|
|
288
|
-
describe("Format Conversion - Response", () => {
|
|
289
|
-
it("should parse Claude responses (native Anthropic)", () => {
|
|
290
|
-
process.env.MODEL_PROVIDER = "databricks";
|
|
291
|
-
process.env.DATABRICKS_API_KEY = "test";
|
|
292
|
-
process.env.DATABRICKS_API_BASE = "http://test.com";
|
|
293
|
-
|
|
294
|
-
const { convertBedrockResponseToAnthropic } = require("../src/clients/bedrock-utils");
|
|
295
|
-
|
|
296
|
-
const claudeResponse = {
|
|
297
|
-
id: "msg_123",
|
|
298
|
-
type: "message",
|
|
299
|
-
role: "assistant",
|
|
300
|
-
content: [{ type: "text", text: "Hello!" }],
|
|
301
|
-
stop_reason: "end_turn",
|
|
302
|
-
usage: { input_tokens: 10, output_tokens: 5 },
|
|
303
|
-
};
|
|
304
|
-
|
|
305
|
-
const result = convertBedrockResponseToAnthropic(
|
|
306
|
-
claudeResponse,
|
|
307
|
-
"claude",
|
|
308
|
-
"anthropic.claude-3-5-sonnet-20241022-v2:0"
|
|
309
|
-
);
|
|
310
|
-
|
|
311
|
-
assert.deepStrictEqual(result, claudeResponse);
|
|
312
|
-
});
|
|
313
|
-
|
|
314
|
-
it("should convert Titan responses to Anthropic format", () => {
|
|
315
|
-
process.env.MODEL_PROVIDER = "databricks";
|
|
316
|
-
process.env.DATABRICKS_API_KEY = "test";
|
|
317
|
-
process.env.DATABRICKS_API_BASE = "http://test.com";
|
|
318
|
-
|
|
319
|
-
const { convertBedrockResponseToAnthropic } = require("../src/clients/bedrock-utils");
|
|
320
|
-
|
|
321
|
-
const titanResponse = {
|
|
322
|
-
results: [{
|
|
323
|
-
outputText: "Response text",
|
|
324
|
-
tokenCount: 50,
|
|
325
|
-
completionReason: "FINISH",
|
|
326
|
-
}],
|
|
327
|
-
inputTextTokenCount: 20,
|
|
328
|
-
};
|
|
329
|
-
|
|
330
|
-
const result = convertBedrockResponseToAnthropic(
|
|
331
|
-
titanResponse,
|
|
332
|
-
"titan",
|
|
333
|
-
"amazon.titan-text-express-v1"
|
|
334
|
-
);
|
|
335
|
-
|
|
336
|
-
assert.strictEqual(result.role, "assistant");
|
|
337
|
-
assert.strictEqual(result.content[0].type, "text");
|
|
338
|
-
assert.strictEqual(result.content[0].text, "Response text");
|
|
339
|
-
assert.strictEqual(result.stop_reason, "end_turn");
|
|
340
|
-
assert.strictEqual(result.usage.input_tokens, 20);
|
|
341
|
-
assert.strictEqual(result.usage.output_tokens, 50);
|
|
342
|
-
});
|
|
343
|
-
|
|
344
|
-
it("should convert Llama responses to Anthropic format", () => {
|
|
345
|
-
process.env.MODEL_PROVIDER = "databricks";
|
|
346
|
-
process.env.DATABRICKS_API_KEY = "test";
|
|
347
|
-
process.env.DATABRICKS_API_BASE = "http://test.com";
|
|
348
|
-
|
|
349
|
-
const { convertBedrockResponseToAnthropic } = require("../src/clients/bedrock-utils");
|
|
350
|
-
|
|
351
|
-
const llamaResponse = {
|
|
352
|
-
generation: "Llama response",
|
|
353
|
-
prompt_token_count: 15,
|
|
354
|
-
generation_token_count: 30,
|
|
355
|
-
stop_reason: "stop",
|
|
356
|
-
};
|
|
357
|
-
|
|
358
|
-
const result = convertBedrockResponseToAnthropic(
|
|
359
|
-
llamaResponse,
|
|
360
|
-
"llama",
|
|
361
|
-
"meta.llama3-70b-instruct-v1:0"
|
|
362
|
-
);
|
|
363
|
-
|
|
364
|
-
assert.strictEqual(result.role, "assistant");
|
|
365
|
-
assert.strictEqual(result.content[0].text, "Llama response");
|
|
366
|
-
assert.strictEqual(result.stop_reason, "end_turn");
|
|
367
|
-
assert.strictEqual(result.usage.input_tokens, 15);
|
|
368
|
-
assert.strictEqual(result.usage.output_tokens, 30);
|
|
369
|
-
});
|
|
370
|
-
});
|
|
371
|
-
|
|
372
|
-
describe("Routing", () => {
|
|
373
|
-
it("should route to bedrock when MODEL_PROVIDER is bedrock", () => {
|
|
374
|
-
process.env.MODEL_PROVIDER = "bedrock";
|
|
375
|
-
process.env.AWS_ACCESS_KEY_ID = "AKIATEST123";
|
|
376
|
-
process.env.AWS_SECRET_ACCESS_KEY = "testSecretKey123";
|
|
377
|
-
process.env.PREFER_OLLAMA = "false";
|
|
378
|
-
|
|
379
|
-
const config = require("../src/config");
|
|
380
|
-
const routing = require("../src/clients/routing");
|
|
381
|
-
|
|
382
|
-
const payload = { messages: [{ role: "user", content: "test" }] };
|
|
383
|
-
const provider = routing.determineProvider(payload);
|
|
384
|
-
|
|
385
|
-
// When not in hybrid mode, should use primary provider
|
|
386
|
-
assert.strictEqual(provider, "bedrock");
|
|
387
|
-
});
|
|
388
|
-
|
|
389
|
-
it("should route to bedrock in hybrid mode for moderate tool counts", () => {
|
|
390
|
-
process.env.MODEL_PROVIDER = "ollama";
|
|
391
|
-
process.env.PREFER_OLLAMA = "true";
|
|
392
|
-
process.env.OLLAMA_MODEL = "llama3.1";
|
|
393
|
-
process.env.OLLAMA_ENDPOINT = "http://localhost:11434";
|
|
394
|
-
process.env.AWS_ACCESS_KEY_ID = "AKIATEST123";
|
|
395
|
-
process.env.AWS_SECRET_ACCESS_KEY = "testSecretKey123";
|
|
396
|
-
process.env.OLLAMA_MAX_TOOLS_FOR_ROUTING = "2";
|
|
397
|
-
process.env.FALLBACK_ENABLED = "true";
|
|
398
|
-
process.env.FALLBACK_PROVIDER = "bedrock";
|
|
399
|
-
|
|
400
|
-
// Clear other providers to ensure bedrock is chosen
|
|
401
|
-
delete process.env.OPENROUTER_API_KEY;
|
|
402
|
-
delete process.env.OPENAI_API_KEY;
|
|
403
|
-
delete process.env.AZURE_OPENAI_API_KEY;
|
|
404
|
-
delete process.env.AZURE_OPENAI_ENDPOINT;
|
|
405
|
-
delete process.env.LLAMACPP_ENDPOINT;
|
|
406
|
-
delete process.env.LMSTUDIO_ENDPOINT;
|
|
407
|
-
delete process.env.DATABRICKS_API_KEY;
|
|
408
|
-
delete process.env.DATABRICKS_API_BASE;
|
|
409
|
-
|
|
410
|
-
const config = require("../src/config");
|
|
411
|
-
const routing = require("../src/clients/routing");
|
|
412
|
-
|
|
413
|
-
// 20 tools should exceed both Ollama and OpenRouter limits, routing to fallback provider (bedrock)
|
|
414
|
-
const payload = {
|
|
415
|
-
messages: [{ role: "user", content: "test" }],
|
|
416
|
-
tools: Array(20).fill({ name: "tool" }),
|
|
417
|
-
};
|
|
418
|
-
const provider = routing.determineProvider(payload);
|
|
419
|
-
|
|
420
|
-
assert.strictEqual(provider, "bedrock");
|
|
421
|
-
});
|
|
422
|
-
});
|
|
423
|
-
|
|
424
|
-
describe("Fallback Provider", () => {
|
|
425
|
-
it("should allow bedrock as fallback provider", () => {
|
|
426
|
-
process.env.MODEL_PROVIDER = "ollama";
|
|
427
|
-
process.env.PREFER_OLLAMA = "true";
|
|
428
|
-
process.env.OLLAMA_MODEL = "llama3.1";
|
|
429
|
-
process.env.OLLAMA_ENDPOINT = "http://localhost:11434";
|
|
430
|
-
process.env.FALLBACK_PROVIDER = "bedrock";
|
|
431
|
-
process.env.AWS_ACCESS_KEY_ID = "AKIATEST123";
|
|
432
|
-
process.env.AWS_SECRET_ACCESS_KEY = "testSecretKey123";
|
|
433
|
-
process.env.FALLBACK_ENABLED = "true";
|
|
434
|
-
|
|
435
|
-
// Should not throw
|
|
436
|
-
const config = require("../src/config");
|
|
437
|
-
assert.strictEqual(config.modelProvider.fallbackProvider, "bedrock");
|
|
438
|
-
});
|
|
439
|
-
|
|
440
|
-
it("should validate bedrock credentials when used as fallback", () => {
|
|
441
|
-
process.env.MODEL_PROVIDER = "ollama";
|
|
442
|
-
process.env.PREFER_OLLAMA = "true";
|
|
443
|
-
process.env.OLLAMA_MODEL = "llama3.1";
|
|
444
|
-
process.env.OLLAMA_ENDPOINT = "http://localhost:11434";
|
|
445
|
-
process.env.FALLBACK_PROVIDER = "bedrock";
|
|
446
|
-
process.env.FALLBACK_ENABLED = "true";
|
|
447
|
-
// Set to empty string to override .env file values
|
|
448
|
-
process.env.AWS_ACCESS_KEY_ID = "";
|
|
449
|
-
process.env.AWS_SECRET_ACCESS_KEY = "";
|
|
450
|
-
|
|
451
|
-
assert.throws(
|
|
452
|
-
() => require("../src/config"),
|
|
453
|
-
/FALLBACK_PROVIDER is set to 'bedrock' but AWS_ACCESS_KEY_ID and AWS_SECRET_ACCESS_KEY are not configured/
|
|
454
|
-
);
|
|
455
|
-
});
|
|
456
|
-
|
|
457
|
-
it("should not allow local providers as fallback", () => {
|
|
458
|
-
process.env.MODEL_PROVIDER = "ollama";
|
|
459
|
-
process.env.PREFER_OLLAMA = "true";
|
|
460
|
-
process.env.OLLAMA_MODEL = "llama3.1";
|
|
461
|
-
process.env.OLLAMA_ENDPOINT = "http://localhost:11434";
|
|
462
|
-
process.env.FALLBACK_PROVIDER = "llamacpp";
|
|
463
|
-
process.env.FALLBACK_ENABLED = "true";
|
|
464
|
-
|
|
465
|
-
assert.throws(
|
|
466
|
-
() => require("../src/config"),
|
|
467
|
-
/FALLBACK_PROVIDER cannot be 'llamacpp'/
|
|
468
|
-
);
|
|
469
|
-
});
|
|
470
|
-
});
|
|
471
|
-
});
|