@jambonz/llm 0.4.6 → 0.5.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/dist/index.cjs +145 -5
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +2 -2
- package/dist/index.d.ts +2 -2
- package/dist/index.js +145 -5
- package/dist/index.js.map +1 -1
- package/dist/test-kit/index.cjs +145 -5
- package/dist/test-kit/index.cjs.map +1 -1
- package/dist/test-kit/index.d.cts +1 -1
- package/dist/test-kit/index.d.ts +1 -1
- package/dist/test-kit/index.js +145 -5
- package/dist/test-kit/index.js.map +1 -1
- package/dist/{types-DbqWrdT6.d.cts → types-BEgQaQIb.d.cts} +36 -0
- package/dist/{types-DbqWrdT6.d.ts → types-BEgQaQIb.d.ts} +36 -0
- package/package.json +1 -1
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { b as AdapterFactory, e as AuthKind, A as AuthSpec, L as LlmAdapter, d as ApiKeyAuth, h as ClientOptions, P as PromptRequest, m as LlmEvent, M as Message, p as ToolCallEvent, o as ModelInfo, c as AdapterManifest } from '../types-
|
|
1
|
+
import { b as AdapterFactory, e as AuthKind, A as AuthSpec, L as LlmAdapter, d as ApiKeyAuth, h as ClientOptions, P as PromptRequest, m as LlmEvent, M as Message, p as ToolCallEvent, o as ModelInfo, c as AdapterManifest } from '../types-BEgQaQIb.cjs';
|
|
2
2
|
|
|
3
3
|
/**
|
|
4
4
|
* Named scenarios the harness must be able to stage. Each scenario configures
|
package/dist/test-kit/index.d.ts
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { b as AdapterFactory, e as AuthKind, A as AuthSpec, L as LlmAdapter, d as ApiKeyAuth, h as ClientOptions, P as PromptRequest, m as LlmEvent, M as Message, p as ToolCallEvent, o as ModelInfo, c as AdapterManifest } from '../types-
|
|
1
|
+
import { b as AdapterFactory, e as AuthKind, A as AuthSpec, L as LlmAdapter, d as ApiKeyAuth, h as ClientOptions, P as PromptRequest, m as LlmEvent, M as Message, p as ToolCallEvent, o as ModelInfo, c as AdapterManifest } from '../types-BEgQaQIb.js';
|
|
2
2
|
|
|
3
3
|
/**
|
|
4
4
|
* Named scenarios the harness must be able to stage. Each scenario configures
|
package/dist/test-kit/index.js
CHANGED
|
@@ -78,9 +78,22 @@ async function* streamFromOpenAI(client, req, options) {
|
|
|
78
78
|
const param = options.tokensParam ?? (needsMaxCompletionTokens(req.model) ? "max_completion_tokens" : "max_tokens");
|
|
79
79
|
body[param] = effectiveMaxTokens;
|
|
80
80
|
}
|
|
81
|
+
const t0 = process.hrtime.bigint();
|
|
82
|
+
let t1;
|
|
83
|
+
let t2;
|
|
81
84
|
let stream;
|
|
85
|
+
let responseHeaders;
|
|
82
86
|
try {
|
|
83
|
-
|
|
87
|
+
const apiPromise = client.chat.completions.create(body, { signal: req.signal });
|
|
88
|
+
const maybeWithResponse = apiPromise.withResponse;
|
|
89
|
+
if (typeof maybeWithResponse === "function") {
|
|
90
|
+
const result = await maybeWithResponse.call(apiPromise);
|
|
91
|
+
stream = result.data;
|
|
92
|
+
responseHeaders = result.response?.headers;
|
|
93
|
+
} else {
|
|
94
|
+
stream = await apiPromise;
|
|
95
|
+
}
|
|
96
|
+
t1 = process.hrtime.bigint();
|
|
84
97
|
} catch (err) {
|
|
85
98
|
if (isAbortError(err)) {
|
|
86
99
|
yield { type: "end", finishReason: "aborted" };
|
|
@@ -112,6 +125,7 @@ async function* streamFromOpenAI(client, req, options) {
|
|
|
112
125
|
const delta = choice.delta;
|
|
113
126
|
const finishReason = choice.finish_reason;
|
|
114
127
|
if (delta?.content) {
|
|
128
|
+
if (t2 === void 0) t2 = process.hrtime.bigint();
|
|
115
129
|
yield { type: "token", text: delta.content };
|
|
116
130
|
}
|
|
117
131
|
if (delta?.tool_calls) {
|
|
@@ -175,6 +189,20 @@ async function* streamFromOpenAI(client, req, options) {
|
|
|
175
189
|
...usage ? { usage } : {},
|
|
176
190
|
...finalRawReason ? { rawReason: finalRawReason } : {}
|
|
177
191
|
};
|
|
192
|
+
if (options.vendorMetadataExtractor && responseHeaders) {
|
|
193
|
+
const metadata = options.vendorMetadataExtractor(responseHeaders);
|
|
194
|
+
if (metadata && Object.keys(metadata).length > 0) {
|
|
195
|
+
endEvent.vendorMetadata = metadata;
|
|
196
|
+
}
|
|
197
|
+
}
|
|
198
|
+
if (t1 !== void 0) {
|
|
199
|
+
const t3 = process.hrtime.bigint();
|
|
200
|
+
endEvent.clientTiming = {
|
|
201
|
+
requestToHeadersMs: Number(t1 - t0) / 1e6,
|
|
202
|
+
...t2 !== void 0 ? { headersToFirstTokenMs: Number(t2 - t1) / 1e6 } : {},
|
|
203
|
+
totalMs: Number(t3 - t0) / 1e6
|
|
204
|
+
};
|
|
205
|
+
}
|
|
178
206
|
yield endEvent;
|
|
179
207
|
}
|
|
180
208
|
function appendOpenAIAssistantToolCall(history, toolCalls) {
|
|
@@ -302,6 +330,40 @@ function isAbortError(err) {
|
|
|
302
330
|
return e.name === "APIUserAbortError" || e.name === "AbortError" || e.code === "ABORT_ERR" || typeof e.message === "string" && /aborted/i.test(e.message);
|
|
303
331
|
}
|
|
304
332
|
|
|
333
|
+
// src/adapters/_metadata.ts
|
|
334
|
+
function makeMetadataExtractor(fields) {
|
|
335
|
+
return (headers) => {
|
|
336
|
+
const out = {};
|
|
337
|
+
for (const f of fields) {
|
|
338
|
+
const raw = headers.get(f.header);
|
|
339
|
+
if (raw === null || raw === void 0 || raw === "") continue;
|
|
340
|
+
if (f.numeric) {
|
|
341
|
+
const n = Number(raw);
|
|
342
|
+
if (Number.isFinite(n)) out[f.key] = n;
|
|
343
|
+
} else {
|
|
344
|
+
out[f.key] = raw;
|
|
345
|
+
}
|
|
346
|
+
}
|
|
347
|
+
return out;
|
|
348
|
+
};
|
|
349
|
+
}
|
|
350
|
+
function extractMetadata(fields, headers) {
|
|
351
|
+
const headersInstance = headers instanceof Headers ? headers : recordToHeaders(headers);
|
|
352
|
+
return makeMetadataExtractor(fields)(headersInstance);
|
|
353
|
+
}
|
|
354
|
+
function recordToHeaders(record) {
|
|
355
|
+
const h = new Headers();
|
|
356
|
+
for (const [name, value] of Object.entries(record)) {
|
|
357
|
+
if (value === void 0) continue;
|
|
358
|
+
if (Array.isArray(value)) {
|
|
359
|
+
for (const v of value) h.append(name, v);
|
|
360
|
+
} else {
|
|
361
|
+
h.set(name, value);
|
|
362
|
+
}
|
|
363
|
+
}
|
|
364
|
+
return h;
|
|
365
|
+
}
|
|
366
|
+
|
|
305
367
|
// src/adapters/openai/manifest.ts
|
|
306
368
|
var OPENAI_KNOWN_MODELS = [
|
|
307
369
|
{
|
|
@@ -403,6 +465,12 @@ var openAIManifest = {
|
|
|
403
465
|
};
|
|
404
466
|
|
|
405
467
|
// src/adapters/openai/adapter.ts
|
|
468
|
+
var OPENAI_METADATA_EXTRACTOR = makeMetadataExtractor([
|
|
469
|
+
{ header: "x-request-id", key: "request_id" },
|
|
470
|
+
{ header: "openai-processing-ms", key: "processing_ms", numeric: true },
|
|
471
|
+
{ header: "x-ratelimit-remaining-requests", key: "requests_remaining", numeric: true },
|
|
472
|
+
{ header: "x-ratelimit-remaining-tokens", key: "tokens_remaining", numeric: true }
|
|
473
|
+
]);
|
|
406
474
|
var OpenAIAdapter = class {
|
|
407
475
|
vendor = openAIManifest.vendor;
|
|
408
476
|
acceptedAuth = ["apiKey"];
|
|
@@ -420,7 +488,8 @@ var OpenAIAdapter = class {
|
|
|
420
488
|
}
|
|
421
489
|
stream(req) {
|
|
422
490
|
return streamFromOpenAI(this.ensureClient(), req, {
|
|
423
|
-
knownModels: openAIManifest.knownModels
|
|
491
|
+
knownModels: openAIManifest.knownModels,
|
|
492
|
+
vendorMetadataExtractor: OPENAI_METADATA_EXTRACTOR
|
|
424
493
|
});
|
|
425
494
|
}
|
|
426
495
|
appendAssistantToolCall(history, toolCalls) {
|
|
@@ -652,6 +721,12 @@ var anthropicManifest = {
|
|
|
652
721
|
};
|
|
653
722
|
|
|
654
723
|
// src/adapters/anthropic/adapter.ts
|
|
724
|
+
var ANTHROPIC_METADATA_EXTRACTOR = makeMetadataExtractor([
|
|
725
|
+
{ header: "request-id", key: "request_id" },
|
|
726
|
+
{ header: "anthropic-ratelimit-requests-remaining", key: "requests_remaining", numeric: true },
|
|
727
|
+
{ header: "anthropic-ratelimit-input-tokens-remaining", key: "input_tokens_remaining", numeric: true },
|
|
728
|
+
{ header: "anthropic-ratelimit-output-tokens-remaining", key: "output_tokens_remaining", numeric: true }
|
|
729
|
+
]);
|
|
655
730
|
var AnthropicAdapter = class {
|
|
656
731
|
vendor = anthropicManifest.vendor;
|
|
657
732
|
acceptedAuth = ["apiKey"];
|
|
@@ -686,11 +761,20 @@ var AnthropicAdapter = class {
|
|
|
686
761
|
if (tools) body.tools = tools;
|
|
687
762
|
if (req.temperature !== void 0) body.temperature = req.temperature;
|
|
688
763
|
let stream;
|
|
764
|
+
let responseHeaders;
|
|
689
765
|
try {
|
|
690
|
-
|
|
766
|
+
const apiPromise = client.messages.create(
|
|
691
767
|
body,
|
|
692
768
|
{ signal: req.signal }
|
|
693
769
|
);
|
|
770
|
+
const maybeWithResponse = apiPromise.withResponse;
|
|
771
|
+
if (typeof maybeWithResponse === "function") {
|
|
772
|
+
const result = await maybeWithResponse.call(apiPromise);
|
|
773
|
+
stream = result.data;
|
|
774
|
+
responseHeaders = result.response?.headers;
|
|
775
|
+
} else {
|
|
776
|
+
stream = await apiPromise;
|
|
777
|
+
}
|
|
694
778
|
} catch (err) {
|
|
695
779
|
if (isAbortError2(err)) {
|
|
696
780
|
yield { type: "end", finishReason: "aborted" };
|
|
@@ -801,6 +885,12 @@ var AnthropicAdapter = class {
|
|
|
801
885
|
...usage ? { usage } : {},
|
|
802
886
|
...stopReason ? { rawReason: stopReason } : {}
|
|
803
887
|
};
|
|
888
|
+
if (responseHeaders) {
|
|
889
|
+
const metadata = ANTHROPIC_METADATA_EXTRACTOR(responseHeaders);
|
|
890
|
+
if (Object.keys(metadata).length > 0) {
|
|
891
|
+
endEvent.vendorMetadata = metadata;
|
|
892
|
+
}
|
|
893
|
+
}
|
|
804
894
|
yield endEvent;
|
|
805
895
|
}
|
|
806
896
|
appendAssistantToolCall(history, toolCalls) {
|
|
@@ -1593,6 +1683,9 @@ var vertexOpenAIManifest = {
|
|
|
1593
1683
|
};
|
|
1594
1684
|
|
|
1595
1685
|
// src/adapters/vertex-openai/adapter.ts
|
|
1686
|
+
var VERTEX_OPENAI_METADATA_EXTRACTOR = makeMetadataExtractor([
|
|
1687
|
+
{ header: "x-request-id", key: "request_id" }
|
|
1688
|
+
]);
|
|
1596
1689
|
var VertexOpenAIAdapter = class {
|
|
1597
1690
|
vendor = vertexOpenAIManifest.vendor;
|
|
1598
1691
|
acceptedAuth = ["vertexServiceAccount"];
|
|
@@ -1645,7 +1738,8 @@ var VertexOpenAIAdapter = class {
|
|
|
1645
1738
|
// endpoint predates `max_completion_tokens` and may not recognize it.
|
|
1646
1739
|
// The model-id heuristic wouldn't catch a partner model named in the
|
|
1647
1740
|
// OpenAI style (unlikely today, but defensive).
|
|
1648
|
-
tokensParam: "max_tokens"
|
|
1741
|
+
tokensParam: "max_tokens",
|
|
1742
|
+
vendorMetadataExtractor: VERTEX_OPENAI_METADATA_EXTRACTOR
|
|
1649
1743
|
});
|
|
1650
1744
|
}
|
|
1651
1745
|
appendAssistantToolCall(history, toolCalls) {
|
|
@@ -2109,6 +2203,21 @@ var BedrockAdapter = class {
|
|
|
2109
2203
|
...usage ? { usage } : {},
|
|
2110
2204
|
...stopReason ? { rawReason: stopReason } : {}
|
|
2111
2205
|
};
|
|
2206
|
+
const httpHeaders = response.$metadata?.httpHeaders;
|
|
2207
|
+
if (httpHeaders) {
|
|
2208
|
+
const metadata = extractMetadata(
|
|
2209
|
+
[
|
|
2210
|
+
{ header: "x-amzn-bedrock-invocation-latency", key: "invocation_latency_ms", numeric: true },
|
|
2211
|
+
{ header: "x-amzn-bedrock-cache-read-input-token-count", key: "cache_read_input_tokens", numeric: true },
|
|
2212
|
+
{ header: "x-amzn-bedrock-cache-write-input-token-count", key: "cache_write_input_tokens", numeric: true },
|
|
2213
|
+
{ header: "x-amzn-bedrock-trace-id", key: "trace_id" }
|
|
2214
|
+
],
|
|
2215
|
+
httpHeaders
|
|
2216
|
+
);
|
|
2217
|
+
if (Object.keys(metadata).length > 0) {
|
|
2218
|
+
endEvent.vendorMetadata = metadata;
|
|
2219
|
+
}
|
|
2220
|
+
}
|
|
2112
2221
|
yield endEvent;
|
|
2113
2222
|
}
|
|
2114
2223
|
appendAssistantToolCall(history, toolCalls) {
|
|
@@ -2360,6 +2469,14 @@ var azureOpenAIManifest = {
|
|
|
2360
2469
|
};
|
|
2361
2470
|
|
|
2362
2471
|
// src/adapters/azure-openai/adapter.ts
|
|
2472
|
+
var AZURE_OPENAI_METADATA_EXTRACTOR = makeMetadataExtractor([
|
|
2473
|
+
{ header: "x-ms-region", key: "region" },
|
|
2474
|
+
{ header: "x-ms-deployment-name", key: "deployment" },
|
|
2475
|
+
{ header: "apim-request-id", key: "request_id" },
|
|
2476
|
+
{ header: "azureml-model-session", key: "model_session" },
|
|
2477
|
+
{ header: "x-ratelimit-remaining-requests", key: "requests_remaining", numeric: true },
|
|
2478
|
+
{ header: "x-ratelimit-remaining-tokens", key: "tokens_remaining", numeric: true }
|
|
2479
|
+
]);
|
|
2363
2480
|
var AzureOpenAIAdapter = class {
|
|
2364
2481
|
vendor = azureOpenAIManifest.vendor;
|
|
2365
2482
|
acceptedAuth = ["azureOpenAIApiKey"];
|
|
@@ -2394,7 +2511,8 @@ var AzureOpenAIAdapter = class {
|
|
|
2394
2511
|
stream(req) {
|
|
2395
2512
|
return streamFromOpenAI(this.ensureClient(), req, {
|
|
2396
2513
|
knownModels: azureOpenAIManifest.knownModels,
|
|
2397
|
-
tokensParam: "max_completion_tokens"
|
|
2514
|
+
tokensParam: "max_completion_tokens",
|
|
2515
|
+
vendorMetadataExtractor: AZURE_OPENAI_METADATA_EXTRACTOR
|
|
2398
2516
|
});
|
|
2399
2517
|
}
|
|
2400
2518
|
appendAssistantToolCall(history, toolCalls) {
|
|
@@ -2519,6 +2637,12 @@ var groqManifest = {
|
|
|
2519
2637
|
};
|
|
2520
2638
|
|
|
2521
2639
|
// src/adapters/groq/adapter.ts
|
|
2640
|
+
var GROQ_METADATA_EXTRACTOR = makeMetadataExtractor([
|
|
2641
|
+
{ header: "x-request-id", key: "request_id" },
|
|
2642
|
+
{ header: "x-groq-region", key: "region" },
|
|
2643
|
+
{ header: "x-ratelimit-remaining-requests", key: "requests_remaining", numeric: true },
|
|
2644
|
+
{ header: "x-ratelimit-remaining-tokens", key: "tokens_remaining", numeric: true }
|
|
2645
|
+
]);
|
|
2522
2646
|
var GroqAdapter = class extends OpenAIAdapter {
|
|
2523
2647
|
vendor = groqManifest.vendor;
|
|
2524
2648
|
init(auth, client) {
|
|
@@ -2530,6 +2654,12 @@ var GroqAdapter = class extends OpenAIAdapter {
|
|
|
2530
2654
|
client
|
|
2531
2655
|
);
|
|
2532
2656
|
}
|
|
2657
|
+
stream(req) {
|
|
2658
|
+
return streamFromOpenAI(this.ensureClient(), req, {
|
|
2659
|
+
knownModels: groqManifest.knownModels,
|
|
2660
|
+
vendorMetadataExtractor: GROQ_METADATA_EXTRACTOR
|
|
2661
|
+
});
|
|
2662
|
+
}
|
|
2533
2663
|
};
|
|
2534
2664
|
|
|
2535
2665
|
// src/adapters/groq/factory.ts
|
|
@@ -2630,6 +2760,10 @@ var huggingfaceManifest = {
|
|
|
2630
2760
|
};
|
|
2631
2761
|
|
|
2632
2762
|
// src/adapters/huggingface/adapter.ts
|
|
2763
|
+
var HUGGINGFACE_METADATA_EXTRACTOR = makeMetadataExtractor([
|
|
2764
|
+
{ header: "x-inference-provider", key: "provider" },
|
|
2765
|
+
{ header: "x-request-id", key: "request_id" }
|
|
2766
|
+
]);
|
|
2633
2767
|
var HuggingfaceAdapter = class extends OpenAIAdapter {
|
|
2634
2768
|
vendor = huggingfaceManifest.vendor;
|
|
2635
2769
|
init(auth, client) {
|
|
@@ -2641,6 +2775,12 @@ var HuggingfaceAdapter = class extends OpenAIAdapter {
|
|
|
2641
2775
|
client
|
|
2642
2776
|
);
|
|
2643
2777
|
}
|
|
2778
|
+
stream(req) {
|
|
2779
|
+
return streamFromOpenAI(this.ensureClient(), req, {
|
|
2780
|
+
knownModels: huggingfaceManifest.knownModels,
|
|
2781
|
+
vendorMetadataExtractor: HUGGINGFACE_METADATA_EXTRACTOR
|
|
2782
|
+
});
|
|
2783
|
+
}
|
|
2644
2784
|
};
|
|
2645
2785
|
|
|
2646
2786
|
// src/adapters/huggingface/factory.ts
|