braintrust 3.7.1 → 3.8.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/LICENSE +201 -0
- package/dev/dist/index.d.mts +144 -2
- package/dev/dist/index.d.ts +144 -2
- package/dev/dist/index.js +2432 -430
- package/dev/dist/index.mjs +2307 -305
- package/dist/auto-instrumentations/bundler/esbuild.cjs +377 -10
- package/dist/auto-instrumentations/bundler/esbuild.mjs +2 -2
- package/dist/auto-instrumentations/bundler/rollup.cjs +377 -10
- package/dist/auto-instrumentations/bundler/rollup.mjs +2 -2
- package/dist/auto-instrumentations/bundler/vite.cjs +377 -10
- package/dist/auto-instrumentations/bundler/vite.mjs +2 -2
- package/dist/auto-instrumentations/bundler/webpack-loader.cjs +377 -10
- package/dist/auto-instrumentations/bundler/webpack-loader.d.ts +11 -9
- package/dist/auto-instrumentations/bundler/webpack.cjs +377 -10
- package/dist/auto-instrumentations/bundler/webpack.mjs +2 -2
- package/dist/auto-instrumentations/{chunk-EVUKFMHG.mjs → chunk-ITP7RAUY.mjs} +21 -3
- package/dist/auto-instrumentations/{chunk-NY4CGTN6.mjs → chunk-MD7W27YH.mjs} +5 -1
- package/dist/auto-instrumentations/{chunk-YCKND42U.mjs → chunk-OLBMPZXE.mjs} +378 -11
- package/dist/auto-instrumentations/{chunk-VLEJ5AEK.mjs → chunk-P5YLNB2A.mjs} +21 -3
- package/dist/auto-instrumentations/hook.mjs +393 -16
- package/dist/auto-instrumentations/index.cjs +379 -10
- package/dist/auto-instrumentations/index.d.mts +5 -1
- package/dist/auto-instrumentations/index.d.ts +5 -1
- package/dist/auto-instrumentations/index.mjs +5 -1
- package/dist/auto-instrumentations/loader/cjs-patch.cjs +34 -6
- package/dist/auto-instrumentations/loader/cjs-patch.d.mts +1 -0
- package/dist/auto-instrumentations/loader/cjs-patch.d.ts +1 -0
- package/dist/auto-instrumentations/loader/cjs-patch.mjs +15 -5
- package/dist/auto-instrumentations/loader/esm-hook.mjs +8 -3
- package/dist/auto-instrumentations/loader/get-package-version.cjs +20 -2
- package/dist/auto-instrumentations/loader/get-package-version.mjs +1 -1
- package/dist/browser.d.mts +191 -14
- package/dist/browser.d.ts +191 -14
- package/dist/browser.js +2646 -315
- package/dist/browser.mjs +2646 -315
- package/dist/cli.js +2411 -409
- package/dist/edge-light.d.mts +1 -1
- package/dist/edge-light.d.ts +1 -1
- package/dist/edge-light.js +12604 -10184
- package/dist/edge-light.mjs +12604 -10184
- package/dist/index.d.mts +191 -14
- package/dist/index.d.ts +191 -14
- package/dist/index.js +2823 -492
- package/dist/index.mjs +2646 -315
- package/dist/instrumentation/index.d.mts +7 -0
- package/dist/instrumentation/index.d.ts +7 -0
- package/dist/instrumentation/index.js +2409 -407
- package/dist/instrumentation/index.mjs +2409 -407
- package/dist/workerd.d.mts +1 -1
- package/dist/workerd.d.ts +1 -1
- package/dist/workerd.js +12604 -10184
- package/dist/workerd.mjs +12604 -10184
- package/package.json +44 -44
package/dist/browser.mjs
CHANGED
|
@@ -1791,6 +1791,16 @@ var NullableSavedFunctionId = z6.union([
|
|
|
1791
1791
|
}),
|
|
1792
1792
|
z6.null()
|
|
1793
1793
|
]);
|
|
1794
|
+
var TopicMapGenerationSettings = z6.object({
|
|
1795
|
+
algorithm: z6.enum(["hdbscan", "kmeans"]),
|
|
1796
|
+
dimension_reduction: z6.enum(["umap", "pca", "none"]),
|
|
1797
|
+
sample_size: z6.number().int().gt(0).optional(),
|
|
1798
|
+
n_clusters: z6.number().int().gt(0).optional(),
|
|
1799
|
+
min_cluster_size: z6.number().int().gt(0).optional(),
|
|
1800
|
+
min_samples: z6.number().int().gt(0).optional(),
|
|
1801
|
+
hierarchy_threshold: z6.number().int().gt(0).optional(),
|
|
1802
|
+
naming_model: z6.string().optional()
|
|
1803
|
+
});
|
|
1794
1804
|
var TopicMapData = z6.object({
|
|
1795
1805
|
type: z6.literal("topic_map"),
|
|
1796
1806
|
source_facet: z6.string(),
|
|
@@ -1798,6 +1808,7 @@ var TopicMapData = z6.object({
|
|
|
1798
1808
|
bundle_key: z6.string().optional(),
|
|
1799
1809
|
report_key: z6.string().optional(),
|
|
1800
1810
|
topic_names: z6.record(z6.string()).optional(),
|
|
1811
|
+
generation_settings: TopicMapGenerationSettings.optional(),
|
|
1801
1812
|
distance_threshold: z6.number().optional()
|
|
1802
1813
|
});
|
|
1803
1814
|
var BatchedFacetData = z6.object({
|
|
@@ -2022,6 +2033,7 @@ var Dataset = z6.object({
|
|
|
2022
2033
|
created: z6.union([z6.string(), z6.null()]).optional(),
|
|
2023
2034
|
deleted_at: z6.union([z6.string(), z6.null()]).optional(),
|
|
2024
2035
|
user_id: z6.union([z6.string(), z6.null()]).optional(),
|
|
2036
|
+
tags: z6.union([z6.array(z6.string()), z6.null()]).optional(),
|
|
2025
2037
|
metadata: z6.union([z6.object({}).partial().passthrough(), z6.null()]).optional(),
|
|
2026
2038
|
url_slug: z6.string()
|
|
2027
2039
|
});
|
|
@@ -2104,6 +2116,14 @@ var DatasetEvent = z6.object({
|
|
|
2104
2116
|
z6.null()
|
|
2105
2117
|
]).optional()
|
|
2106
2118
|
});
|
|
2119
|
+
var DatasetSnapshot = z6.object({
|
|
2120
|
+
id: z6.string().uuid(),
|
|
2121
|
+
dataset_id: z6.string().uuid(),
|
|
2122
|
+
name: z6.string(),
|
|
2123
|
+
description: z6.union([z6.string(), z6.null()]),
|
|
2124
|
+
xact_id: z6.string(),
|
|
2125
|
+
created: z6.union([z6.string(), z6.null()])
|
|
2126
|
+
});
|
|
2107
2127
|
var EnvVar = z6.object({
|
|
2108
2128
|
id: z6.string().uuid(),
|
|
2109
2129
|
object_type: z6.enum(["organization", "project", "function"]),
|
|
@@ -2862,6 +2882,8 @@ var TopicAutomationConfig = z6.object({
|
|
|
2862
2882
|
scope: z6.union([SpanScope, TraceScope, GroupScope, z6.null()]).optional(),
|
|
2863
2883
|
data_scope: TopicAutomationDataScope.optional(),
|
|
2864
2884
|
btql_filter: z6.union([z6.string(), z6.null()]).optional(),
|
|
2885
|
+
rerun_seconds: z6.union([z6.number(), z6.null()]).optional(),
|
|
2886
|
+
relabel_overlap_seconds: z6.union([z6.number(), z6.null()]).optional(),
|
|
2865
2887
|
backfill_time_range: z6.union([
|
|
2866
2888
|
z6.string(),
|
|
2867
2889
|
z6.object({ from: z6.string(), to: z6.string() }),
|
|
@@ -3198,7 +3220,8 @@ var User = z6.object({
|
|
|
3198
3220
|
family_name: z6.union([z6.string(), z6.null()]).optional(),
|
|
3199
3221
|
email: z6.union([z6.string(), z6.null()]).optional(),
|
|
3200
3222
|
avatar_url: z6.union([z6.string(), z6.null()]).optional(),
|
|
3201
|
-
created: z6.union([z6.string(), z6.null()]).optional()
|
|
3223
|
+
created: z6.union([z6.string(), z6.null()]).optional(),
|
|
3224
|
+
last_active_at: z6.union([z6.number(), z6.null()]).optional()
|
|
3202
3225
|
});
|
|
3203
3226
|
var ViewDataSearch = z6.union([
|
|
3204
3227
|
z6.object({
|
|
@@ -4358,6 +4381,15 @@ var BRAINTRUST_CURRENT_SPAN_STORE = Symbol.for(
|
|
|
4358
4381
|
"braintrust.currentSpanStore"
|
|
4359
4382
|
);
|
|
4360
4383
|
var ContextManager = class {
|
|
4384
|
+
/**
|
|
4385
|
+
* Returns the value to store in the ALS bound to a TracingChannel's start event.
|
|
4386
|
+
* In default mode this is the Span itself; in OTEL mode it is the OTEL Context
|
|
4387
|
+
* containing the span so that OTEL's own ALS stores a proper Context object.
|
|
4388
|
+
*/
|
|
4389
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
4390
|
+
wrapSpanForStore(span) {
|
|
4391
|
+
return span;
|
|
4392
|
+
}
|
|
4361
4393
|
};
|
|
4362
4394
|
var BraintrustContextManager = class extends ContextManager {
|
|
4363
4395
|
_currentSpan;
|
|
@@ -9931,18 +9963,22 @@ function ensureSpanStateForEvent(states, config, event, channelName) {
|
|
|
9931
9963
|
function bindCurrentSpanStoreToStart(tracingChannel2, states, config, channelName) {
|
|
9932
9964
|
const state = _internalGetGlobalState();
|
|
9933
9965
|
const startChannel = tracingChannel2.start;
|
|
9934
|
-
const
|
|
9966
|
+
const contextManager = state?.contextManager;
|
|
9967
|
+
const currentSpanStore = contextManager ? contextManager[BRAINTRUST_CURRENT_SPAN_STORE] : void 0;
|
|
9935
9968
|
if (!currentSpanStore || !startChannel) {
|
|
9936
9969
|
return void 0;
|
|
9937
9970
|
}
|
|
9938
9971
|
startChannel.bindStore(
|
|
9939
9972
|
currentSpanStore,
|
|
9940
|
-
(event) =>
|
|
9941
|
-
|
|
9942
|
-
|
|
9943
|
-
|
|
9944
|
-
|
|
9945
|
-
|
|
9973
|
+
(event) => {
|
|
9974
|
+
const span = ensureSpanStateForEvent(
|
|
9975
|
+
states,
|
|
9976
|
+
config,
|
|
9977
|
+
event,
|
|
9978
|
+
channelName
|
|
9979
|
+
).span;
|
|
9980
|
+
return contextManager.wrapSpanForStore(span);
|
|
9981
|
+
}
|
|
9946
9982
|
);
|
|
9947
9983
|
return () => {
|
|
9948
9984
|
startChannel.unbindStore(currentSpanStore);
|
|
@@ -9959,6 +9995,26 @@ function logErrorAndEnd(states, event) {
|
|
|
9959
9995
|
spanData.span.end();
|
|
9960
9996
|
states.delete(event);
|
|
9961
9997
|
}
|
|
9998
|
+
function runStreamingCompletionHook(args) {
|
|
9999
|
+
if (!args.config.onComplete) {
|
|
10000
|
+
return;
|
|
10001
|
+
}
|
|
10002
|
+
try {
|
|
10003
|
+
args.config.onComplete({
|
|
10004
|
+
channelName: args.channelName,
|
|
10005
|
+
...args.chunks ? { chunks: args.chunks } : {},
|
|
10006
|
+
endEvent: args.endEvent,
|
|
10007
|
+
...args.metadata !== void 0 ? { metadata: args.metadata } : {},
|
|
10008
|
+
metrics: args.metrics,
|
|
10009
|
+
output: args.output,
|
|
10010
|
+
result: args.result,
|
|
10011
|
+
span: args.span,
|
|
10012
|
+
startTime: args.startTime
|
|
10013
|
+
});
|
|
10014
|
+
} catch (error) {
|
|
10015
|
+
console.error(`Error in onComplete hook for ${args.channelName}:`, error);
|
|
10016
|
+
}
|
|
10017
|
+
}
|
|
9962
10018
|
function traceAsyncChannel(channel2, config) {
|
|
9963
10019
|
const tracingChannel2 = channel2.tracingChannel();
|
|
9964
10020
|
const states = /* @__PURE__ */ new WeakMap();
|
|
@@ -10086,6 +10142,18 @@ function traceStreamingChannel(channel2, config) {
|
|
|
10086
10142
|
} else if (metrics.time_to_first_token === void 0 && chunks.length > 0) {
|
|
10087
10143
|
metrics.time_to_first_token = getCurrentUnixTimestamp() - startTime;
|
|
10088
10144
|
}
|
|
10145
|
+
runStreamingCompletionHook({
|
|
10146
|
+
channelName,
|
|
10147
|
+
chunks,
|
|
10148
|
+
config,
|
|
10149
|
+
endEvent: asyncEndEvent,
|
|
10150
|
+
...metadata !== void 0 ? { metadata } : {},
|
|
10151
|
+
metrics,
|
|
10152
|
+
output,
|
|
10153
|
+
result: asyncEndEvent.result,
|
|
10154
|
+
span,
|
|
10155
|
+
startTime
|
|
10156
|
+
});
|
|
10089
10157
|
span.log({
|
|
10090
10158
|
output,
|
|
10091
10159
|
...metadata !== void 0 ? { metadata } : {},
|
|
@@ -10135,6 +10203,17 @@ function traceStreamingChannel(channel2, config) {
|
|
|
10135
10203
|
asyncEndEvent.result,
|
|
10136
10204
|
asyncEndEvent
|
|
10137
10205
|
);
|
|
10206
|
+
runStreamingCompletionHook({
|
|
10207
|
+
channelName,
|
|
10208
|
+
config,
|
|
10209
|
+
endEvent: asyncEndEvent,
|
|
10210
|
+
...normalizeMetadata(metadata) !== void 0 ? { metadata: normalizeMetadata(metadata) } : {},
|
|
10211
|
+
metrics,
|
|
10212
|
+
output,
|
|
10213
|
+
result: asyncEndEvent.result,
|
|
10214
|
+
span,
|
|
10215
|
+
startTime
|
|
10216
|
+
});
|
|
10138
10217
|
span.log({
|
|
10139
10218
|
output,
|
|
10140
10219
|
...normalizeMetadata(metadata) !== void 0 ? { metadata: normalizeMetadata(metadata) } : {},
|
|
@@ -10518,6 +10597,10 @@ var openAIChannels = defineChannels("openai", {
|
|
|
10518
10597
|
responsesParse: channel({
|
|
10519
10598
|
channelName: "responses.parse",
|
|
10520
10599
|
kind: "async"
|
|
10600
|
+
}),
|
|
10601
|
+
responsesCompact: channel({
|
|
10602
|
+
channelName: "responses.compact",
|
|
10603
|
+
kind: "async"
|
|
10521
10604
|
})
|
|
10522
10605
|
});
|
|
10523
10606
|
|
|
@@ -10797,6 +10880,40 @@ var OpenAIPlugin = class extends BasePlugin {
|
|
|
10797
10880
|
aggregateChunks: aggregateResponseStreamEvents
|
|
10798
10881
|
})
|
|
10799
10882
|
);
|
|
10883
|
+
this.unsubscribers.push(
|
|
10884
|
+
traceAsyncChannel(openAIChannels.responsesCompact, {
|
|
10885
|
+
name: "openai.responses.compact",
|
|
10886
|
+
type: "llm" /* LLM */,
|
|
10887
|
+
extractInput: ([params]) => {
|
|
10888
|
+
const { input, ...metadata } = params;
|
|
10889
|
+
return {
|
|
10890
|
+
input: processInputAttachments(input),
|
|
10891
|
+
metadata: { ...metadata, provider: "openai" }
|
|
10892
|
+
};
|
|
10893
|
+
},
|
|
10894
|
+
extractOutput: (result) => {
|
|
10895
|
+
return processImagesInOutput(result?.output);
|
|
10896
|
+
},
|
|
10897
|
+
extractMetadata: (result) => {
|
|
10898
|
+
if (!result) {
|
|
10899
|
+
return void 0;
|
|
10900
|
+
}
|
|
10901
|
+
const { output: _output, usage: _usage, ...metadata } = result;
|
|
10902
|
+
return Object.keys(metadata).length > 0 ? metadata : void 0;
|
|
10903
|
+
},
|
|
10904
|
+
extractMetrics: (result, startTime, endEvent) => {
|
|
10905
|
+
const metrics = withCachedMetric(
|
|
10906
|
+
parseMetricsFromUsage(result?.usage),
|
|
10907
|
+
result,
|
|
10908
|
+
endEvent
|
|
10909
|
+
);
|
|
10910
|
+
if (startTime) {
|
|
10911
|
+
metrics.time_to_first_token = getCurrentUnixTimestamp() - startTime;
|
|
10912
|
+
}
|
|
10913
|
+
return metrics;
|
|
10914
|
+
}
|
|
10915
|
+
})
|
|
10916
|
+
);
|
|
10800
10917
|
}
|
|
10801
10918
|
onDisable() {
|
|
10802
10919
|
this.unsubscribers = unsubscribeAll(this.unsubscribers);
|
|
@@ -11386,6 +11503,10 @@ var aiSDKChannels = defineChannels("ai", {
|
|
|
11386
11503
|
channelName: "streamText",
|
|
11387
11504
|
kind: "async"
|
|
11388
11505
|
}),
|
|
11506
|
+
streamTextSync: channel({
|
|
11507
|
+
channelName: "streamText.sync",
|
|
11508
|
+
kind: "sync-stream"
|
|
11509
|
+
}),
|
|
11389
11510
|
generateObject: channel({
|
|
11390
11511
|
channelName: "generateObject",
|
|
11391
11512
|
kind: "async"
|
|
@@ -11394,6 +11515,20 @@ var aiSDKChannels = defineChannels("ai", {
|
|
|
11394
11515
|
channelName: "streamObject",
|
|
11395
11516
|
kind: "async"
|
|
11396
11517
|
}),
|
|
11518
|
+
streamObjectSync: channel({
|
|
11519
|
+
channelName: "streamObject.sync",
|
|
11520
|
+
kind: "sync-stream"
|
|
11521
|
+
}),
|
|
11522
|
+
embed: channel(
|
|
11523
|
+
{
|
|
11524
|
+
channelName: "embed",
|
|
11525
|
+
kind: "async"
|
|
11526
|
+
}
|
|
11527
|
+
),
|
|
11528
|
+
embedMany: channel({
|
|
11529
|
+
channelName: "embedMany",
|
|
11530
|
+
kind: "async"
|
|
11531
|
+
}),
|
|
11397
11532
|
agentGenerate: channel({
|
|
11398
11533
|
channelName: "Agent.generate",
|
|
11399
11534
|
kind: "async"
|
|
@@ -11402,6 +11537,10 @@ var aiSDKChannels = defineChannels("ai", {
|
|
|
11402
11537
|
channelName: "Agent.stream",
|
|
11403
11538
|
kind: "async"
|
|
11404
11539
|
}),
|
|
11540
|
+
agentStreamSync: channel({
|
|
11541
|
+
channelName: "Agent.stream.sync",
|
|
11542
|
+
kind: "sync-stream"
|
|
11543
|
+
}),
|
|
11405
11544
|
toolLoopAgentGenerate: channel({
|
|
11406
11545
|
channelName: "ToolLoopAgent.generate",
|
|
11407
11546
|
kind: "async"
|
|
@@ -11450,7 +11589,7 @@ var AISDKPlugin = class extends BasePlugin {
|
|
|
11450
11589
|
traceStreamingChannel(aiSDKChannels.generateText, {
|
|
11451
11590
|
name: "generateText",
|
|
11452
11591
|
type: "llm" /* LLM */,
|
|
11453
|
-
extractInput: ([params], event, span) =>
|
|
11592
|
+
extractInput: ([params], event, span) => prepareAISDKCallInput(params, event, span, denyOutputPaths),
|
|
11454
11593
|
extractOutput: (result, endEvent) => {
|
|
11455
11594
|
finalizeAISDKChildTracing(endEvent);
|
|
11456
11595
|
return processAISDKOutput(
|
|
@@ -11466,7 +11605,7 @@ var AISDKPlugin = class extends BasePlugin {
|
|
|
11466
11605
|
traceStreamingChannel(aiSDKChannels.streamText, {
|
|
11467
11606
|
name: "streamText",
|
|
11468
11607
|
type: "llm" /* LLM */,
|
|
11469
|
-
extractInput: ([params], event, span) =>
|
|
11608
|
+
extractInput: ([params], event, span) => prepareAISDKCallInput(params, event, span, denyOutputPaths),
|
|
11470
11609
|
extractOutput: (result, endEvent) => processAISDKOutput(
|
|
11471
11610
|
result,
|
|
11472
11611
|
resolveDenyOutputPaths(endEvent, denyOutputPaths)
|
|
@@ -11482,11 +11621,25 @@ var AISDKPlugin = class extends BasePlugin {
|
|
|
11482
11621
|
})
|
|
11483
11622
|
})
|
|
11484
11623
|
);
|
|
11624
|
+
this.unsubscribers.push(
|
|
11625
|
+
traceSyncStreamChannel(aiSDKChannels.streamTextSync, {
|
|
11626
|
+
name: "streamText",
|
|
11627
|
+
type: "llm" /* LLM */,
|
|
11628
|
+
extractInput: ([params], event, span) => prepareAISDKCallInput(params, event, span, denyOutputPaths),
|
|
11629
|
+
patchResult: ({ endEvent, result, span, startTime }) => patchAISDKStreamingResult({
|
|
11630
|
+
defaultDenyOutputPaths: denyOutputPaths,
|
|
11631
|
+
endEvent,
|
|
11632
|
+
result,
|
|
11633
|
+
span,
|
|
11634
|
+
startTime
|
|
11635
|
+
})
|
|
11636
|
+
})
|
|
11637
|
+
);
|
|
11485
11638
|
this.unsubscribers.push(
|
|
11486
11639
|
traceStreamingChannel(aiSDKChannels.generateObject, {
|
|
11487
11640
|
name: "generateObject",
|
|
11488
11641
|
type: "llm" /* LLM */,
|
|
11489
|
-
extractInput: ([params], event, span) =>
|
|
11642
|
+
extractInput: ([params], event, span) => prepareAISDKCallInput(params, event, span, denyOutputPaths),
|
|
11490
11643
|
extractOutput: (result, endEvent) => {
|
|
11491
11644
|
finalizeAISDKChildTracing(endEvent);
|
|
11492
11645
|
return processAISDKOutput(
|
|
@@ -11502,7 +11655,7 @@ var AISDKPlugin = class extends BasePlugin {
|
|
|
11502
11655
|
traceStreamingChannel(aiSDKChannels.streamObject, {
|
|
11503
11656
|
name: "streamObject",
|
|
11504
11657
|
type: "llm" /* LLM */,
|
|
11505
|
-
extractInput: ([params], event, span) =>
|
|
11658
|
+
extractInput: ([params], event, span) => prepareAISDKCallInput(params, event, span, denyOutputPaths),
|
|
11506
11659
|
extractOutput: (result, endEvent) => processAISDKOutput(
|
|
11507
11660
|
result,
|
|
11508
11661
|
resolveDenyOutputPaths(endEvent, denyOutputPaths)
|
|
@@ -11518,11 +11671,49 @@ var AISDKPlugin = class extends BasePlugin {
|
|
|
11518
11671
|
})
|
|
11519
11672
|
})
|
|
11520
11673
|
);
|
|
11674
|
+
this.unsubscribers.push(
|
|
11675
|
+
traceSyncStreamChannel(aiSDKChannels.streamObjectSync, {
|
|
11676
|
+
name: "streamObject",
|
|
11677
|
+
type: "llm" /* LLM */,
|
|
11678
|
+
extractInput: ([params], event, span) => prepareAISDKCallInput(params, event, span, denyOutputPaths),
|
|
11679
|
+
patchResult: ({ endEvent, result, span, startTime }) => patchAISDKStreamingResult({
|
|
11680
|
+
defaultDenyOutputPaths: denyOutputPaths,
|
|
11681
|
+
endEvent,
|
|
11682
|
+
result,
|
|
11683
|
+
span,
|
|
11684
|
+
startTime
|
|
11685
|
+
})
|
|
11686
|
+
})
|
|
11687
|
+
);
|
|
11688
|
+
this.unsubscribers.push(
|
|
11689
|
+
traceAsyncChannel(aiSDKChannels.embed, {
|
|
11690
|
+
name: "embed",
|
|
11691
|
+
type: "llm" /* LLM */,
|
|
11692
|
+
extractInput: ([params], event) => prepareAISDKEmbedInput(params, event.self),
|
|
11693
|
+
extractOutput: (result, endEvent) => processAISDKEmbeddingOutput(
|
|
11694
|
+
result,
|
|
11695
|
+
resolveDenyOutputPaths(endEvent, denyOutputPaths)
|
|
11696
|
+
),
|
|
11697
|
+
extractMetrics: (result, _startTime, endEvent) => extractTopLevelAISDKMetrics(result, endEvent)
|
|
11698
|
+
})
|
|
11699
|
+
);
|
|
11700
|
+
this.unsubscribers.push(
|
|
11701
|
+
traceAsyncChannel(aiSDKChannels.embedMany, {
|
|
11702
|
+
name: "embedMany",
|
|
11703
|
+
type: "llm" /* LLM */,
|
|
11704
|
+
extractInput: ([params], event) => prepareAISDKEmbedInput(params, event.self),
|
|
11705
|
+
extractOutput: (result, endEvent) => processAISDKEmbeddingOutput(
|
|
11706
|
+
result,
|
|
11707
|
+
resolveDenyOutputPaths(endEvent, denyOutputPaths)
|
|
11708
|
+
),
|
|
11709
|
+
extractMetrics: (result, _startTime, endEvent) => extractTopLevelAISDKMetrics(result, endEvent)
|
|
11710
|
+
})
|
|
11711
|
+
);
|
|
11521
11712
|
this.unsubscribers.push(
|
|
11522
11713
|
traceStreamingChannel(aiSDKChannels.agentGenerate, {
|
|
11523
11714
|
name: "Agent.generate",
|
|
11524
11715
|
type: "llm" /* LLM */,
|
|
11525
|
-
extractInput: ([params], event, span) =>
|
|
11716
|
+
extractInput: ([params], event, span) => prepareAISDKCallInput(params, event, span, denyOutputPaths),
|
|
11526
11717
|
extractOutput: (result, endEvent) => {
|
|
11527
11718
|
finalizeAISDKChildTracing(endEvent);
|
|
11528
11719
|
return processAISDKOutput(
|
|
@@ -11538,7 +11729,7 @@ var AISDKPlugin = class extends BasePlugin {
|
|
|
11538
11729
|
traceStreamingChannel(aiSDKChannels.agentStream, {
|
|
11539
11730
|
name: "Agent.stream",
|
|
11540
11731
|
type: "llm" /* LLM */,
|
|
11541
|
-
extractInput: ([params], event, span) =>
|
|
11732
|
+
extractInput: ([params], event, span) => prepareAISDKCallInput(params, event, span, denyOutputPaths),
|
|
11542
11733
|
extractOutput: (result, endEvent) => processAISDKOutput(
|
|
11543
11734
|
result,
|
|
11544
11735
|
resolveDenyOutputPaths(endEvent, denyOutputPaths)
|
|
@@ -11554,11 +11745,25 @@ var AISDKPlugin = class extends BasePlugin {
|
|
|
11554
11745
|
})
|
|
11555
11746
|
})
|
|
11556
11747
|
);
|
|
11748
|
+
this.unsubscribers.push(
|
|
11749
|
+
traceSyncStreamChannel(aiSDKChannels.agentStreamSync, {
|
|
11750
|
+
name: "Agent.stream",
|
|
11751
|
+
type: "llm" /* LLM */,
|
|
11752
|
+
extractInput: ([params], event, span) => prepareAISDKCallInput(params, event, span, denyOutputPaths),
|
|
11753
|
+
patchResult: ({ endEvent, result, span, startTime }) => patchAISDKStreamingResult({
|
|
11754
|
+
defaultDenyOutputPaths: denyOutputPaths,
|
|
11755
|
+
endEvent,
|
|
11756
|
+
result,
|
|
11757
|
+
span,
|
|
11758
|
+
startTime
|
|
11759
|
+
})
|
|
11760
|
+
})
|
|
11761
|
+
);
|
|
11557
11762
|
this.unsubscribers.push(
|
|
11558
11763
|
traceStreamingChannel(aiSDKChannels.toolLoopAgentGenerate, {
|
|
11559
11764
|
name: "ToolLoopAgent.generate",
|
|
11560
11765
|
type: "llm" /* LLM */,
|
|
11561
|
-
extractInput: ([params], event, span) =>
|
|
11766
|
+
extractInput: ([params], event, span) => prepareAISDKCallInput(params, event, span, denyOutputPaths),
|
|
11562
11767
|
extractOutput: (result, endEvent) => {
|
|
11563
11768
|
finalizeAISDKChildTracing(endEvent);
|
|
11564
11769
|
return processAISDKOutput(
|
|
@@ -11574,7 +11779,7 @@ var AISDKPlugin = class extends BasePlugin {
|
|
|
11574
11779
|
traceStreamingChannel(aiSDKChannels.toolLoopAgentStream, {
|
|
11575
11780
|
name: "ToolLoopAgent.stream",
|
|
11576
11781
|
type: "llm" /* LLM */,
|
|
11577
|
-
extractInput: ([params], event, span) =>
|
|
11782
|
+
extractInput: ([params], event, span) => prepareAISDKCallInput(params, event, span, denyOutputPaths),
|
|
11578
11783
|
extractOutput: (result, endEvent) => processAISDKOutput(
|
|
11579
11784
|
result,
|
|
11580
11785
|
resolveDenyOutputPaths(endEvent, denyOutputPaths)
|
|
@@ -11884,11 +12089,11 @@ var convertDataToAttachment = (data, mimeType, filename) => {
|
|
|
11884
12089
|
}
|
|
11885
12090
|
return null;
|
|
11886
12091
|
};
|
|
11887
|
-
function
|
|
12092
|
+
function processAISDKCallInput(params) {
|
|
11888
12093
|
return processInputAttachmentsSync(params);
|
|
11889
12094
|
}
|
|
11890
|
-
function
|
|
11891
|
-
const { input, outputPromise } =
|
|
12095
|
+
function prepareAISDKCallInput(params, event, span, defaultDenyOutputPaths) {
|
|
12096
|
+
const { input, outputPromise } = processAISDKCallInput(params);
|
|
11892
12097
|
if (outputPromise && input && typeof input === "object") {
|
|
11893
12098
|
outputPromise.then((resolvedData) => {
|
|
11894
12099
|
span.log({
|
|
@@ -11900,7 +12105,7 @@ function prepareAISDKInput(params, event, span, defaultDenyOutputPaths) {
|
|
|
11900
12105
|
}).catch(() => {
|
|
11901
12106
|
});
|
|
11902
12107
|
}
|
|
11903
|
-
const metadata =
|
|
12108
|
+
const metadata = extractMetadataFromCallParams(params, event.self);
|
|
11904
12109
|
const childTracing = prepareAISDKChildTracing(
|
|
11905
12110
|
params,
|
|
11906
12111
|
event.self,
|
|
@@ -11917,6 +12122,12 @@ function prepareAISDKInput(params, event, span, defaultDenyOutputPaths) {
|
|
|
11917
12122
|
metadata
|
|
11918
12123
|
};
|
|
11919
12124
|
}
|
|
12125
|
+
function prepareAISDKEmbedInput(params, self) {
|
|
12126
|
+
return {
|
|
12127
|
+
input: { ...params },
|
|
12128
|
+
metadata: extractMetadataFromEmbedParams(params, self)
|
|
12129
|
+
};
|
|
12130
|
+
}
|
|
11920
12131
|
function extractTopLevelAISDKMetrics(result, event, startTime) {
|
|
11921
12132
|
const metrics = hasModelChildTracing(event) ? {} : extractTokenMetrics(result);
|
|
11922
12133
|
if (startTime) {
|
|
@@ -11927,29 +12138,41 @@ function extractTopLevelAISDKMetrics(result, event, startTime) {
|
|
|
11927
12138
|
function hasModelChildTracing(event) {
|
|
11928
12139
|
return event?.modelWrapped === true || event?.__braintrust_ai_sdk_model_wrapped === true;
|
|
11929
12140
|
}
|
|
11930
|
-
function
|
|
11931
|
-
|
|
12141
|
+
function createAISDKIntegrationMetadata() {
|
|
12142
|
+
return {
|
|
11932
12143
|
braintrust: {
|
|
11933
12144
|
integration_name: "ai-sdk",
|
|
11934
12145
|
sdk_language: "typescript"
|
|
11935
12146
|
}
|
|
11936
12147
|
};
|
|
11937
|
-
|
|
11938
|
-
|
|
11939
|
-
|
|
12148
|
+
}
|
|
12149
|
+
function resolveModelFromSelf(self) {
|
|
12150
|
+
return self && typeof self === "object" && "model" in self && self.model ? self.model : self && typeof self === "object" && "settings" in self && self.settings?.model ? self.settings?.model : void 0;
|
|
12151
|
+
}
|
|
12152
|
+
function extractBaseMetadata(model, self) {
|
|
12153
|
+
const metadata = createAISDKIntegrationMetadata();
|
|
12154
|
+
const { model: modelId, provider } = serializeModelWithProvider(
|
|
12155
|
+
model ?? resolveModelFromSelf(self)
|
|
11940
12156
|
);
|
|
11941
|
-
if (
|
|
11942
|
-
metadata.model =
|
|
12157
|
+
if (modelId) {
|
|
12158
|
+
metadata.model = modelId;
|
|
11943
12159
|
}
|
|
11944
12160
|
if (provider) {
|
|
11945
12161
|
metadata.provider = provider;
|
|
11946
12162
|
}
|
|
12163
|
+
return metadata;
|
|
12164
|
+
}
|
|
12165
|
+
function extractMetadataFromCallParams(params, self) {
|
|
12166
|
+
const metadata = extractBaseMetadata(params.model, self);
|
|
11947
12167
|
const tools = serializeAISDKToolsForLogging(params.tools);
|
|
11948
12168
|
if (tools) {
|
|
11949
12169
|
metadata.tools = tools;
|
|
11950
12170
|
}
|
|
11951
12171
|
return metadata;
|
|
11952
12172
|
}
|
|
12173
|
+
function extractMetadataFromEmbedParams(params, self) {
|
|
12174
|
+
return extractBaseMetadata(params.model, self);
|
|
12175
|
+
}
|
|
11953
12176
|
function prepareAISDKChildTracing(params, self, parentSpan, denyOutputPaths, aiSDK) {
|
|
11954
12177
|
const cleanup = [];
|
|
11955
12178
|
const patchedModels = /* @__PURE__ */ new WeakSet();
|
|
@@ -11987,7 +12210,7 @@ function prepareAISDKChildTracing(params, self, parentSpan, denyOutputPaths, aiS
|
|
|
11987
12210
|
type: "llm" /* LLM */
|
|
11988
12211
|
},
|
|
11989
12212
|
event: {
|
|
11990
|
-
input:
|
|
12213
|
+
input: processAISDKCallInput(options).input,
|
|
11991
12214
|
metadata: baseMetadata
|
|
11992
12215
|
}
|
|
11993
12216
|
}
|
|
@@ -12001,7 +12224,7 @@ function prepareAISDKChildTracing(params, self, parentSpan, denyOutputPaths, aiS
|
|
|
12001
12224
|
type: "llm" /* LLM */
|
|
12002
12225
|
},
|
|
12003
12226
|
event: {
|
|
12004
|
-
input:
|
|
12227
|
+
input: processAISDKCallInput(options).input,
|
|
12005
12228
|
metadata: baseMetadata
|
|
12006
12229
|
}
|
|
12007
12230
|
});
|
|
@@ -12310,9 +12533,14 @@ function attachKnownResultPromiseHandlers(result) {
|
|
|
12310
12533
|
"content",
|
|
12311
12534
|
"text",
|
|
12312
12535
|
"object",
|
|
12536
|
+
"value",
|
|
12537
|
+
"values",
|
|
12313
12538
|
"finishReason",
|
|
12539
|
+
"embedding",
|
|
12540
|
+
"embeddings",
|
|
12314
12541
|
"usage",
|
|
12315
12542
|
"totalUsage",
|
|
12543
|
+
"responses",
|
|
12316
12544
|
"steps"
|
|
12317
12545
|
];
|
|
12318
12546
|
for (const field of promiseLikeFields) {
|
|
@@ -12460,6 +12688,38 @@ function processAISDKOutput(output, denyOutputPaths) {
|
|
|
12460
12688
|
const merged = extractSerializableOutputFields(output);
|
|
12461
12689
|
return normalizeAISDKLoggedOutput(omit(merged, denyOutputPaths));
|
|
12462
12690
|
}
|
|
12691
|
+
function processAISDKEmbeddingOutput(output, denyOutputPaths) {
|
|
12692
|
+
if (!output || typeof output !== "object") {
|
|
12693
|
+
return output;
|
|
12694
|
+
}
|
|
12695
|
+
const summarized = {};
|
|
12696
|
+
const whitelistedFields = [
|
|
12697
|
+
"usage",
|
|
12698
|
+
"totalUsage",
|
|
12699
|
+
"warnings",
|
|
12700
|
+
"providerMetadata",
|
|
12701
|
+
"experimental_providerMetadata"
|
|
12702
|
+
];
|
|
12703
|
+
for (const field of whitelistedFields) {
|
|
12704
|
+
const value = safeSerializableFieldRead(output, field);
|
|
12705
|
+
if (value !== void 0 && isSerializableOutputValue(value)) {
|
|
12706
|
+
summarized[field] = value;
|
|
12707
|
+
}
|
|
12708
|
+
}
|
|
12709
|
+
const embedding = safeSerializableFieldRead(output, "embedding");
|
|
12710
|
+
if (Array.isArray(embedding)) {
|
|
12711
|
+
summarized.embedding_length = embedding.length;
|
|
12712
|
+
}
|
|
12713
|
+
const embeddings = safeSerializableFieldRead(output, "embeddings");
|
|
12714
|
+
if (Array.isArray(embeddings)) {
|
|
12715
|
+
summarized.embedding_count = embeddings.length;
|
|
12716
|
+
const firstEmbedding = embeddings.find((item) => Array.isArray(item));
|
|
12717
|
+
if (Array.isArray(firstEmbedding)) {
|
|
12718
|
+
summarized.embedding_length = firstEmbedding.length;
|
|
12719
|
+
}
|
|
12720
|
+
}
|
|
12721
|
+
return normalizeAISDKLoggedOutput(omit(summarized, denyOutputPaths));
|
|
12722
|
+
}
|
|
12463
12723
|
function extractTokenMetrics(result) {
|
|
12464
12724
|
const metrics = {};
|
|
12465
12725
|
let usage;
|
|
@@ -12558,12 +12818,17 @@ function extractGetterValues(obj) {
|
|
|
12558
12818
|
"content",
|
|
12559
12819
|
"text",
|
|
12560
12820
|
"object",
|
|
12821
|
+
"value",
|
|
12822
|
+
"values",
|
|
12823
|
+
"embedding",
|
|
12824
|
+
"embeddings",
|
|
12561
12825
|
"finishReason",
|
|
12562
12826
|
"usage",
|
|
12563
12827
|
"totalUsage",
|
|
12564
12828
|
"toolCalls",
|
|
12565
12829
|
"toolResults",
|
|
12566
12830
|
"warnings",
|
|
12831
|
+
"responses",
|
|
12567
12832
|
"experimental_providerMetadata",
|
|
12568
12833
|
"providerMetadata",
|
|
12569
12834
|
"rawResponse",
|
|
@@ -12824,65 +13089,365 @@ var claudeAgentSDKChannels = defineChannels(
|
|
|
12824
13089
|
}
|
|
12825
13090
|
);
|
|
12826
13091
|
|
|
12827
|
-
// src/instrumentation/plugins/claude-agent-sdk-
|
|
12828
|
-
|
|
12829
|
-
|
|
12830
|
-
|
|
12831
|
-
|
|
12832
|
-
|
|
12833
|
-
|
|
12834
|
-
|
|
12835
|
-
|
|
12836
|
-
|
|
12837
|
-
|
|
12838
|
-
|
|
12839
|
-
|
|
12840
|
-
|
|
12841
|
-
|
|
12842
|
-
|
|
12843
|
-
|
|
12844
|
-
|
|
12845
|
-
|
|
12846
|
-
|
|
12847
|
-
|
|
12848
|
-
|
|
12849
|
-
|
|
12850
|
-
|
|
13092
|
+
// src/instrumentation/plugins/claude-agent-sdk-instrumentation-constants.ts
|
|
13093
|
+
var CLAUDE_AGENT_SDK_SKIP_LOCAL_TOOL_HOOKS_OPTION = "__braintrust_skip_local_tool_hooks";
|
|
13094
|
+
|
|
13095
|
+
// src/instrumentation/plugins/claude-agent-sdk-local-tool-context.ts
|
|
13096
|
+
var LOCAL_TOOL_CONTEXT_ASYNC_ITERATOR_PATCHED = Symbol.for(
|
|
13097
|
+
"braintrust.claude_agent_sdk.local_tool_context_async_iterator_patched"
|
|
13098
|
+
);
|
|
13099
|
+
function createLocalToolContextStore() {
|
|
13100
|
+
const maybeIsoWithAsyncLocalStorage = isomorph_default;
|
|
13101
|
+
if (typeof maybeIsoWithAsyncLocalStorage.newAsyncLocalStorage === "function") {
|
|
13102
|
+
return maybeIsoWithAsyncLocalStorage.newAsyncLocalStorage();
|
|
13103
|
+
}
|
|
13104
|
+
let currentStore;
|
|
13105
|
+
return {
|
|
13106
|
+
enterWith(store) {
|
|
13107
|
+
currentStore = store;
|
|
13108
|
+
},
|
|
13109
|
+
getStore() {
|
|
13110
|
+
return currentStore;
|
|
13111
|
+
},
|
|
13112
|
+
run(store, callback) {
|
|
13113
|
+
const previousStore = currentStore;
|
|
13114
|
+
currentStore = store;
|
|
13115
|
+
try {
|
|
13116
|
+
return callback();
|
|
13117
|
+
} finally {
|
|
13118
|
+
currentStore = previousStore;
|
|
13119
|
+
}
|
|
12851
13120
|
}
|
|
13121
|
+
};
|
|
13122
|
+
}
|
|
13123
|
+
var localToolContextStore = createLocalToolContextStore();
|
|
13124
|
+
var fallbackLocalToolParentResolver;
|
|
13125
|
+
function createClaudeLocalToolContext() {
|
|
13126
|
+
return {};
|
|
13127
|
+
}
|
|
13128
|
+
function runWithClaudeLocalToolContext(callback, context) {
|
|
13129
|
+
return localToolContextStore.run(
|
|
13130
|
+
context ?? createClaudeLocalToolContext(),
|
|
13131
|
+
callback
|
|
13132
|
+
);
|
|
13133
|
+
}
|
|
13134
|
+
function ensureClaudeLocalToolContext() {
|
|
13135
|
+
const existing = localToolContextStore.getStore();
|
|
13136
|
+
if (existing) {
|
|
13137
|
+
return existing;
|
|
12852
13138
|
}
|
|
12853
|
-
|
|
13139
|
+
const created = {};
|
|
13140
|
+
localToolContextStore.enterWith(created);
|
|
13141
|
+
return created;
|
|
12854
13142
|
}
|
|
12855
|
-
function
|
|
12856
|
-
|
|
12857
|
-
|
|
13143
|
+
function setClaudeLocalToolParentResolver(resolver) {
|
|
13144
|
+
fallbackLocalToolParentResolver = resolver;
|
|
13145
|
+
const context = ensureClaudeLocalToolContext();
|
|
13146
|
+
if (!context) {
|
|
13147
|
+
return;
|
|
12858
13148
|
}
|
|
12859
|
-
|
|
12860
|
-
return typeof value === "number" ? value : void 0;
|
|
13149
|
+
context.resolveLocalToolParent = resolver;
|
|
12861
13150
|
}
|
|
12862
|
-
function
|
|
12863
|
-
|
|
12864
|
-
|
|
12865
|
-
|
|
12866
|
-
|
|
12867
|
-
|
|
12868
|
-
|
|
13151
|
+
function getClaudeLocalToolParentResolver() {
|
|
13152
|
+
return localToolContextStore.getStore()?.resolveLocalToolParent ?? fallbackLocalToolParentResolver;
|
|
13153
|
+
}
|
|
13154
|
+
function isAsyncIterable2(value) {
|
|
13155
|
+
return value !== null && typeof value === "object" && Symbol.asyncIterator in value && typeof value[Symbol.asyncIterator] === "function";
|
|
13156
|
+
}
|
|
13157
|
+
function bindClaudeLocalToolContextToAsyncIterable(result, localToolContext) {
|
|
13158
|
+
if (!isAsyncIterable2(result) || Object.isFrozen(result) || Object.isSealed(result)) {
|
|
13159
|
+
return result;
|
|
12869
13160
|
}
|
|
12870
|
-
|
|
12871
|
-
|
|
13161
|
+
const stream = result;
|
|
13162
|
+
const originalAsyncIterator = stream[Symbol.asyncIterator];
|
|
13163
|
+
if (originalAsyncIterator[LOCAL_TOOL_CONTEXT_ASYNC_ITERATOR_PATCHED]) {
|
|
13164
|
+
return result;
|
|
12872
13165
|
}
|
|
12873
|
-
const
|
|
12874
|
-
|
|
12875
|
-
|
|
13166
|
+
const patchedAsyncIterator = function() {
|
|
13167
|
+
return runWithClaudeLocalToolContext(() => {
|
|
13168
|
+
const iterator = Reflect.apply(originalAsyncIterator, this, []);
|
|
13169
|
+
if (!iterator || typeof iterator !== "object") {
|
|
13170
|
+
return iterator;
|
|
13171
|
+
}
|
|
13172
|
+
const patchMethod = (methodName) => {
|
|
13173
|
+
const originalMethod = Reflect.get(iterator, methodName);
|
|
13174
|
+
if (typeof originalMethod !== "function") {
|
|
13175
|
+
return;
|
|
13176
|
+
}
|
|
13177
|
+
Reflect.set(
|
|
13178
|
+
iterator,
|
|
13179
|
+
methodName,
|
|
13180
|
+
(...args) => runWithClaudeLocalToolContext(
|
|
13181
|
+
() => Reflect.apply(
|
|
13182
|
+
originalMethod,
|
|
13183
|
+
iterator,
|
|
13184
|
+
args
|
|
13185
|
+
),
|
|
13186
|
+
localToolContext
|
|
13187
|
+
)
|
|
13188
|
+
);
|
|
13189
|
+
};
|
|
13190
|
+
patchMethod("next");
|
|
13191
|
+
patchMethod("return");
|
|
13192
|
+
patchMethod("throw");
|
|
13193
|
+
return iterator;
|
|
13194
|
+
}, localToolContext);
|
|
13195
|
+
};
|
|
13196
|
+
Object.defineProperty(
|
|
13197
|
+
patchedAsyncIterator,
|
|
13198
|
+
LOCAL_TOOL_CONTEXT_ASYNC_ITERATOR_PATCHED,
|
|
13199
|
+
{
|
|
13200
|
+
configurable: false,
|
|
13201
|
+
enumerable: false,
|
|
13202
|
+
value: true,
|
|
13203
|
+
writable: false
|
|
13204
|
+
}
|
|
13205
|
+
);
|
|
13206
|
+
Reflect.set(stream, Symbol.asyncIterator, patchedAsyncIterator);
|
|
13207
|
+
return result;
|
|
13208
|
+
}
|
|
13209
|
+
|
|
13210
|
+
// src/instrumentation/plugins/claude-agent-sdk-local-tool-spans.ts
|
|
13211
|
+
var LOCAL_TOOL_HANDLER_WRAPPED = Symbol.for(
|
|
13212
|
+
"braintrust.claude_agent_sdk.local_tool_handler_wrapped"
|
|
13213
|
+
);
|
|
13214
|
+
function toErrorMessage(error) {
|
|
13215
|
+
return error instanceof Error ? error.message : String(error);
|
|
13216
|
+
}
|
|
13217
|
+
function isPromiseLike2(value) {
|
|
13218
|
+
return value !== null && typeof value === "object" && "then" in value && typeof value.then === "function";
|
|
13219
|
+
}
|
|
13220
|
+
function getToolUseIdFromExtra(extra) {
|
|
13221
|
+
if (!extra || typeof extra !== "object" || !("_meta" in extra)) {
|
|
13222
|
+
return void 0;
|
|
12876
13223
|
}
|
|
12877
|
-
const
|
|
12878
|
-
if (
|
|
12879
|
-
|
|
13224
|
+
const meta = Reflect.get(extra, "_meta");
|
|
13225
|
+
if (!meta || typeof meta !== "object") {
|
|
13226
|
+
return void 0;
|
|
12880
13227
|
}
|
|
12881
|
-
const
|
|
12882
|
-
|
|
12883
|
-
|
|
12884
|
-
|
|
12885
|
-
|
|
13228
|
+
const toolUseId = Reflect.get(meta, "claudecode/toolUseId");
|
|
13229
|
+
return typeof toolUseId === "string" ? toolUseId : void 0;
|
|
13230
|
+
}
|
|
13231
|
+
function wrapLocalClaudeToolHandler(handler, getMetadata) {
|
|
13232
|
+
if (handler[LOCAL_TOOL_HANDLER_WRAPPED]) {
|
|
13233
|
+
return handler;
|
|
13234
|
+
}
|
|
13235
|
+
const wrappedHandler = function wrappedLocalToolHandler(...handlerArgs) {
|
|
13236
|
+
const metadata = getMetadata();
|
|
13237
|
+
const rawToolName = metadata.serverName ? `mcp__${metadata.serverName}__${metadata.toolName}` : metadata.toolName;
|
|
13238
|
+
const toolUseId = getToolUseIdFromExtra(handlerArgs[1]);
|
|
13239
|
+
const localToolParentResolver = getClaudeLocalToolParentResolver();
|
|
13240
|
+
const spanName = metadata.serverName ? `tool: ${metadata.serverName}/${metadata.toolName}` : `tool: ${metadata.toolName}`;
|
|
13241
|
+
const runWithResolvedParent = async () => {
|
|
13242
|
+
const parent = toolUseId && localToolParentResolver ? await localToolParentResolver(toolUseId).catch(() => void 0) : void 0;
|
|
13243
|
+
const span = startSpan({
|
|
13244
|
+
event: {
|
|
13245
|
+
input: handlerArgs[0],
|
|
13246
|
+
metadata: {
|
|
13247
|
+
"claude_agent_sdk.raw_tool_name": rawToolName,
|
|
13248
|
+
"gen_ai.tool.name": metadata.toolName,
|
|
13249
|
+
...toolUseId && { "gen_ai.tool.call.id": toolUseId },
|
|
13250
|
+
...metadata.serverName && {
|
|
13251
|
+
"mcp.server": metadata.serverName
|
|
13252
|
+
}
|
|
13253
|
+
}
|
|
13254
|
+
},
|
|
13255
|
+
name: spanName,
|
|
13256
|
+
...parent && { parent },
|
|
13257
|
+
spanAttributes: { type: "tool" /* TOOL */ }
|
|
13258
|
+
});
|
|
13259
|
+
const runHandler = () => Reflect.apply(handler, this, handlerArgs);
|
|
13260
|
+
const finalizeSuccess = (result) => {
|
|
13261
|
+
span.log({ output: result });
|
|
13262
|
+
span.end();
|
|
13263
|
+
return result;
|
|
13264
|
+
};
|
|
13265
|
+
const finalizeError = (error) => {
|
|
13266
|
+
span.log({ error: toErrorMessage(error) });
|
|
13267
|
+
span.end();
|
|
13268
|
+
throw error;
|
|
13269
|
+
};
|
|
13270
|
+
return withCurrent(span, () => {
|
|
13271
|
+
try {
|
|
13272
|
+
const result = runHandler();
|
|
13273
|
+
if (isPromiseLike2(result)) {
|
|
13274
|
+
return result.then(finalizeSuccess, finalizeError);
|
|
13275
|
+
}
|
|
13276
|
+
return finalizeSuccess(result);
|
|
13277
|
+
} catch (error) {
|
|
13278
|
+
return finalizeError(error);
|
|
13279
|
+
}
|
|
13280
|
+
});
|
|
13281
|
+
};
|
|
13282
|
+
return runWithResolvedParent();
|
|
13283
|
+
};
|
|
13284
|
+
Object.defineProperty(wrappedHandler, LOCAL_TOOL_HANDLER_WRAPPED, {
|
|
13285
|
+
configurable: false,
|
|
13286
|
+
enumerable: false,
|
|
13287
|
+
value: true,
|
|
13288
|
+
writable: false
|
|
13289
|
+
});
|
|
13290
|
+
return wrappedHandler;
|
|
13291
|
+
}
|
|
13292
|
+
function getRegisteredTools(instance) {
|
|
13293
|
+
if (!instance || typeof instance !== "object") {
|
|
13294
|
+
return void 0;
|
|
13295
|
+
}
|
|
13296
|
+
if (!("_registeredTools" in instance)) {
|
|
13297
|
+
return void 0;
|
|
13298
|
+
}
|
|
13299
|
+
const registeredTools = Reflect.get(instance, "_registeredTools");
|
|
13300
|
+
if (registeredTools instanceof Map) {
|
|
13301
|
+
return registeredTools;
|
|
13302
|
+
}
|
|
13303
|
+
if (registeredTools && typeof registeredTools === "object") {
|
|
13304
|
+
return registeredTools;
|
|
13305
|
+
}
|
|
13306
|
+
return void 0;
|
|
13307
|
+
}
|
|
13308
|
+
function wrapLocalMcpServerToolHandlers(serverName, serverConfig) {
|
|
13309
|
+
if (!serverConfig || typeof serverConfig !== "object") {
|
|
13310
|
+
return false;
|
|
13311
|
+
}
|
|
13312
|
+
if (!("instance" in serverConfig)) {
|
|
13313
|
+
return false;
|
|
13314
|
+
}
|
|
13315
|
+
const instance = Reflect.get(serverConfig, "instance");
|
|
13316
|
+
const registeredTools = getRegisteredTools(instance);
|
|
13317
|
+
if (!registeredTools) {
|
|
13318
|
+
return false;
|
|
13319
|
+
}
|
|
13320
|
+
let wrappedAny = false;
|
|
13321
|
+
const wrapHandler = (toolName, registration) => {
|
|
13322
|
+
if (!registration || typeof registration !== "object") {
|
|
13323
|
+
return;
|
|
13324
|
+
}
|
|
13325
|
+
const handler = Reflect.get(registration, "handler");
|
|
13326
|
+
if (typeof handler !== "function") {
|
|
13327
|
+
return;
|
|
13328
|
+
}
|
|
13329
|
+
const wrappedHandler = wrapLocalClaudeToolHandler(handler, () => ({
|
|
13330
|
+
serverName,
|
|
13331
|
+
toolName
|
|
13332
|
+
}));
|
|
13333
|
+
if (wrappedHandler !== handler) {
|
|
13334
|
+
Reflect.set(registration, "handler", wrappedHandler);
|
|
13335
|
+
wrappedAny = true;
|
|
13336
|
+
}
|
|
13337
|
+
};
|
|
13338
|
+
if (registeredTools instanceof Map) {
|
|
13339
|
+
for (const [toolName, registration] of registeredTools.entries()) {
|
|
13340
|
+
wrapHandler(toolName, registration);
|
|
13341
|
+
}
|
|
13342
|
+
return wrappedAny;
|
|
13343
|
+
}
|
|
13344
|
+
for (const [toolName, registration] of Object.entries(registeredTools)) {
|
|
13345
|
+
wrapHandler(toolName, registration);
|
|
13346
|
+
}
|
|
13347
|
+
return wrappedAny;
|
|
13348
|
+
}
|
|
13349
|
+
function collectLocalMcpServerToolHookNames(serverName, serverConfig) {
|
|
13350
|
+
const toolNames = /* @__PURE__ */ new Set();
|
|
13351
|
+
if (!serverConfig || typeof serverConfig !== "object") {
|
|
13352
|
+
return toolNames;
|
|
13353
|
+
}
|
|
13354
|
+
if ("instance" in serverConfig) {
|
|
13355
|
+
const instance = Reflect.get(serverConfig, "instance");
|
|
13356
|
+
const registeredTools = getRegisteredTools(instance);
|
|
13357
|
+
if (registeredTools instanceof Map) {
|
|
13358
|
+
for (const toolName of registeredTools.keys()) {
|
|
13359
|
+
toolNames.add(toolName);
|
|
13360
|
+
toolNames.add(`mcp__${serverName}__${toolName}`);
|
|
13361
|
+
}
|
|
13362
|
+
} else if (registeredTools) {
|
|
13363
|
+
for (const toolName of Object.keys(registeredTools)) {
|
|
13364
|
+
toolNames.add(toolName);
|
|
13365
|
+
toolNames.add(`mcp__${serverName}__${toolName}`);
|
|
13366
|
+
}
|
|
13367
|
+
}
|
|
13368
|
+
}
|
|
13369
|
+
if ("tools" in serverConfig) {
|
|
13370
|
+
const rawTools = Reflect.get(serverConfig, "tools");
|
|
13371
|
+
if (Array.isArray(rawTools)) {
|
|
13372
|
+
for (const tool of rawTools) {
|
|
13373
|
+
if (!tool || typeof tool !== "object") {
|
|
13374
|
+
continue;
|
|
13375
|
+
}
|
|
13376
|
+
const toolName = Reflect.get(tool, "name");
|
|
13377
|
+
if (typeof toolName !== "string") {
|
|
13378
|
+
continue;
|
|
13379
|
+
}
|
|
13380
|
+
toolNames.add(toolName);
|
|
13381
|
+
toolNames.add(`mcp__${serverName}__${toolName}`);
|
|
13382
|
+
}
|
|
13383
|
+
}
|
|
13384
|
+
}
|
|
13385
|
+
return toolNames;
|
|
13386
|
+
}
|
|
13387
|
+
|
|
13388
|
+
// src/instrumentation/plugins/claude-agent-sdk-plugin.ts
|
|
13389
|
+
var ROOT_LLM_PARENT_KEY = "__root__";
|
|
13390
|
+
function llmParentKey(parentToolUseId) {
|
|
13391
|
+
return parentToolUseId ?? ROOT_LLM_PARENT_KEY;
|
|
13392
|
+
}
|
|
13393
|
+
function isSubAgentToolName(toolName) {
|
|
13394
|
+
return toolName === "Agent" || toolName === "Task";
|
|
13395
|
+
}
|
|
13396
|
+
function filterSerializableOptions(options) {
|
|
13397
|
+
const allowedKeys = [
|
|
13398
|
+
"model",
|
|
13399
|
+
"maxTurns",
|
|
13400
|
+
"cwd",
|
|
13401
|
+
"continue",
|
|
13402
|
+
"allowedTools",
|
|
13403
|
+
"disallowedTools",
|
|
13404
|
+
"additionalDirectories",
|
|
13405
|
+
"permissionMode",
|
|
13406
|
+
"debug",
|
|
13407
|
+
"apiKey",
|
|
13408
|
+
"apiKeySource",
|
|
13409
|
+
"agentName",
|
|
13410
|
+
"instructions"
|
|
13411
|
+
];
|
|
13412
|
+
const filtered = {};
|
|
13413
|
+
for (const key of allowedKeys) {
|
|
13414
|
+
if (options[key] !== void 0) {
|
|
13415
|
+
filtered[key] = options[key];
|
|
13416
|
+
}
|
|
13417
|
+
}
|
|
13418
|
+
return filtered;
|
|
13419
|
+
}
|
|
13420
|
+
function getNumberProperty(obj, key) {
|
|
13421
|
+
if (!obj || typeof obj !== "object" || !(key in obj)) {
|
|
13422
|
+
return void 0;
|
|
13423
|
+
}
|
|
13424
|
+
const value = Reflect.get(obj, key);
|
|
13425
|
+
return typeof value === "number" ? value : void 0;
|
|
13426
|
+
}
|
|
13427
|
+
function extractUsageFromMessage(message) {
|
|
13428
|
+
const metrics = {};
|
|
13429
|
+
let usage;
|
|
13430
|
+
if (message.type === "assistant") {
|
|
13431
|
+
usage = message.message?.usage;
|
|
13432
|
+
} else if (message.type === "result") {
|
|
13433
|
+
usage = message.usage;
|
|
13434
|
+
}
|
|
13435
|
+
if (!usage || typeof usage !== "object") {
|
|
13436
|
+
return metrics;
|
|
13437
|
+
}
|
|
13438
|
+
const inputTokens = getNumberProperty(usage, "input_tokens");
|
|
13439
|
+
if (inputTokens !== void 0) {
|
|
13440
|
+
metrics.prompt_tokens = inputTokens;
|
|
13441
|
+
}
|
|
13442
|
+
const outputTokens = getNumberProperty(usage, "output_tokens");
|
|
13443
|
+
if (outputTokens !== void 0) {
|
|
13444
|
+
metrics.completion_tokens = outputTokens;
|
|
13445
|
+
}
|
|
13446
|
+
const cacheReadTokens = getNumberProperty(usage, "cache_read_input_tokens") || 0;
|
|
13447
|
+
const cacheCreationTokens = getNumberProperty(usage, "cache_creation_input_tokens") || 0;
|
|
13448
|
+
if (cacheReadTokens > 0 || cacheCreationTokens > 0) {
|
|
13449
|
+
Object.assign(
|
|
13450
|
+
metrics,
|
|
12886
13451
|
extractAnthropicCacheTokens(cacheReadTokens, cacheCreationTokens)
|
|
12887
13452
|
);
|
|
12888
13453
|
}
|
|
@@ -12910,7 +13475,7 @@ function buildLLMInput(prompt, conversationHistory, capturedPromptMessages) {
|
|
|
12910
13475
|
function formatCapturedMessages(messages) {
|
|
12911
13476
|
return messages.length > 0 ? messages : [];
|
|
12912
13477
|
}
|
|
12913
|
-
async function createLLMSpanForMessages(messages, prompt, conversationHistory, options, startTime, capturedPromptMessages, parentSpan) {
|
|
13478
|
+
async function createLLMSpanForMessages(messages, prompt, conversationHistory, options, startTime, capturedPromptMessages, parentSpan, existingSpan) {
|
|
12914
13479
|
if (messages.length === 0) {
|
|
12915
13480
|
return void 0;
|
|
12916
13481
|
}
|
|
@@ -12930,7 +13495,7 @@ async function createLLMSpanForMessages(messages, prompt, conversationHistory, o
|
|
|
12930
13495
|
).filter(
|
|
12931
13496
|
(c) => c !== void 0
|
|
12932
13497
|
);
|
|
12933
|
-
const span = startSpan({
|
|
13498
|
+
const span = existingSpan ?? startSpan({
|
|
12934
13499
|
name: "anthropic.messages.create",
|
|
12935
13500
|
parent: parentSpan,
|
|
12936
13501
|
spanAttributes: {
|
|
@@ -12944,8 +13509,13 @@ async function createLLMSpanForMessages(messages, prompt, conversationHistory, o
|
|
|
12944
13509
|
metrics: usage,
|
|
12945
13510
|
output: outputs
|
|
12946
13511
|
});
|
|
13512
|
+
const spanExport = await span.export();
|
|
12947
13513
|
await span.end();
|
|
12948
|
-
|
|
13514
|
+
const finalMessage = lastMessage.message?.content && lastMessage.message?.role ? { content: lastMessage.message.content, role: lastMessage.message.role } : void 0;
|
|
13515
|
+
return {
|
|
13516
|
+
finalMessage,
|
|
13517
|
+
spanExport
|
|
13518
|
+
};
|
|
12949
13519
|
}
|
|
12950
13520
|
function getMcpServerMetadata(serverName, mcpServers) {
|
|
12951
13521
|
if (!serverName || !mcpServers) {
|
|
@@ -12989,11 +13559,51 @@ function parseToolName(rawToolName) {
|
|
|
12989
13559
|
toolName: rawToolName
|
|
12990
13560
|
};
|
|
12991
13561
|
}
|
|
12992
|
-
function
|
|
13562
|
+
function isLocalToolUse(rawToolName, mcpServers) {
|
|
13563
|
+
const parsed = parseToolName(rawToolName);
|
|
13564
|
+
if (!parsed.mcpServer || !mcpServers) {
|
|
13565
|
+
return false;
|
|
13566
|
+
}
|
|
13567
|
+
const serverConfig = mcpServers[parsed.mcpServer];
|
|
13568
|
+
if (!serverConfig || typeof serverConfig !== "object") {
|
|
13569
|
+
return false;
|
|
13570
|
+
}
|
|
13571
|
+
return serverConfig.type === "sdk" || "transport" in serverConfig;
|
|
13572
|
+
}
|
|
13573
|
+
function prepareLocalToolHandlersInMcpServers(mcpServers) {
|
|
13574
|
+
const localToolHookNames = /* @__PURE__ */ new Set();
|
|
13575
|
+
if (!mcpServers) {
|
|
13576
|
+
return {
|
|
13577
|
+
hasLocalToolHandlers: false,
|
|
13578
|
+
localToolHookNames
|
|
13579
|
+
};
|
|
13580
|
+
}
|
|
13581
|
+
let hasLocalToolHandlers = false;
|
|
13582
|
+
for (const [serverName, serverConfig] of Object.entries(mcpServers)) {
|
|
13583
|
+
const toolNames = collectLocalMcpServerToolHookNames(
|
|
13584
|
+
serverName,
|
|
13585
|
+
serverConfig
|
|
13586
|
+
);
|
|
13587
|
+
for (const toolName of toolNames) {
|
|
13588
|
+
localToolHookNames.add(toolName);
|
|
13589
|
+
}
|
|
13590
|
+
if (toolNames.size > 0) {
|
|
13591
|
+
hasLocalToolHandlers = true;
|
|
13592
|
+
}
|
|
13593
|
+
if (wrapLocalMcpServerToolHandlers(serverName, serverConfig)) {
|
|
13594
|
+
hasLocalToolHandlers = true;
|
|
13595
|
+
}
|
|
13596
|
+
}
|
|
13597
|
+
return { hasLocalToolHandlers, localToolHookNames };
|
|
13598
|
+
}
|
|
13599
|
+
function createToolTracingHooks(resolveParentSpan, activeToolSpans, mcpServers, localToolHookNames, skipLocalToolHooks, subAgentSpans, endedSubAgentSpans) {
|
|
12993
13600
|
const preToolUse = async (input, toolUseID) => {
|
|
12994
13601
|
if (input.hook_event_name !== "PreToolUse" || !toolUseID) {
|
|
12995
13602
|
return {};
|
|
12996
13603
|
}
|
|
13604
|
+
if (skipLocalToolHooks && (isLocalToolUse(input.tool_name, mcpServers) || localToolHookNames.has(input.tool_name))) {
|
|
13605
|
+
return {};
|
|
13606
|
+
}
|
|
12997
13607
|
if (isSubAgentToolName(input.tool_name)) {
|
|
12998
13608
|
return {};
|
|
12999
13609
|
}
|
|
@@ -13022,6 +13632,9 @@ function createToolTracingHooks(resolveParentSpan, activeToolSpans, mcpServers,
|
|
|
13022
13632
|
if (input.hook_event_name !== "PostToolUse" || !toolUseID) {
|
|
13023
13633
|
return {};
|
|
13024
13634
|
}
|
|
13635
|
+
if (skipLocalToolHooks && (isLocalToolUse(input.tool_name, mcpServers) || localToolHookNames.has(input.tool_name))) {
|
|
13636
|
+
return {};
|
|
13637
|
+
}
|
|
13025
13638
|
const subAgentSpan = subAgentSpans.get(toolUseID);
|
|
13026
13639
|
if (subAgentSpan) {
|
|
13027
13640
|
try {
|
|
@@ -13062,6 +13675,9 @@ function createToolTracingHooks(resolveParentSpan, activeToolSpans, mcpServers,
|
|
|
13062
13675
|
if (input.hook_event_name !== "PostToolUseFailure" || !toolUseID) {
|
|
13063
13676
|
return {};
|
|
13064
13677
|
}
|
|
13678
|
+
if (skipLocalToolHooks && (isLocalToolUse(input.tool_name, mcpServers) || localToolHookNames.has(input.tool_name))) {
|
|
13679
|
+
return {};
|
|
13680
|
+
}
|
|
13065
13681
|
const subAgentSpan = subAgentSpans.get(toolUseID);
|
|
13066
13682
|
if (subAgentSpan) {
|
|
13067
13683
|
try {
|
|
@@ -13096,11 +13712,13 @@ function createToolTracingHooks(resolveParentSpan, activeToolSpans, mcpServers,
|
|
|
13096
13712
|
};
|
|
13097
13713
|
return { postToolUse, postToolUseFailure, preToolUse };
|
|
13098
13714
|
}
|
|
13099
|
-
function injectTracingHooks(options, resolveParentSpan, activeToolSpans, subAgentSpans, endedSubAgentSpans) {
|
|
13715
|
+
function injectTracingHooks(options, resolveParentSpan, activeToolSpans, localToolHookNames, skipLocalToolHooks, subAgentSpans, endedSubAgentSpans) {
|
|
13100
13716
|
const { preToolUse, postToolUse, postToolUseFailure } = createToolTracingHooks(
|
|
13101
13717
|
resolveParentSpan,
|
|
13102
13718
|
activeToolSpans,
|
|
13103
13719
|
options.mcpServers,
|
|
13720
|
+
localToolHookNames,
|
|
13721
|
+
skipLocalToolHooks,
|
|
13104
13722
|
subAgentSpans,
|
|
13105
13723
|
endedSubAgentSpans
|
|
13106
13724
|
);
|
|
@@ -13131,6 +13749,7 @@ async function finalizeCurrentMessageGroup(state) {
|
|
|
13131
13749
|
return;
|
|
13132
13750
|
}
|
|
13133
13751
|
const parentToolUseId = state.currentMessages[0]?.parent_tool_use_id ?? null;
|
|
13752
|
+
const parentKey = llmParentKey(parentToolUseId);
|
|
13134
13753
|
let parentSpan = await state.span.export();
|
|
13135
13754
|
if (parentToolUseId) {
|
|
13136
13755
|
const subAgentSpan = state.subAgentSpans.get(parentToolUseId);
|
|
@@ -13138,17 +13757,30 @@ async function finalizeCurrentMessageGroup(state) {
|
|
|
13138
13757
|
parentSpan = await subAgentSpan.export();
|
|
13139
13758
|
}
|
|
13140
13759
|
}
|
|
13141
|
-
const
|
|
13760
|
+
const existingLlmSpan = state.activeLlmSpansByParentToolUse.get(parentKey);
|
|
13761
|
+
const llmSpanResult = await createLLMSpanForMessages(
|
|
13142
13762
|
state.currentMessages,
|
|
13143
13763
|
state.originalPrompt,
|
|
13144
13764
|
state.finalResults,
|
|
13145
13765
|
state.options,
|
|
13146
13766
|
state.currentMessageStartTime,
|
|
13147
13767
|
state.capturedPromptMessages,
|
|
13148
|
-
parentSpan
|
|
13768
|
+
parentSpan,
|
|
13769
|
+
existingLlmSpan
|
|
13149
13770
|
);
|
|
13150
|
-
|
|
13151
|
-
|
|
13771
|
+
state.activeLlmSpansByParentToolUse.delete(parentKey);
|
|
13772
|
+
if (llmSpanResult) {
|
|
13773
|
+
if (parentToolUseId) {
|
|
13774
|
+
state.latestLlmParentBySubAgentToolUse.set(
|
|
13775
|
+
parentToolUseId,
|
|
13776
|
+
llmSpanResult.spanExport
|
|
13777
|
+
);
|
|
13778
|
+
} else {
|
|
13779
|
+
state.latestRootLlmParentRef.value = llmSpanResult.spanExport;
|
|
13780
|
+
}
|
|
13781
|
+
if (llmSpanResult.finalMessage) {
|
|
13782
|
+
state.finalResults.push(llmSpanResult.finalMessage);
|
|
13783
|
+
}
|
|
13152
13784
|
}
|
|
13153
13785
|
const lastMessage = state.currentMessages[state.currentMessages.length - 1];
|
|
13154
13786
|
if (lastMessage?.message?.usage) {
|
|
@@ -13216,6 +13848,29 @@ async function handleStreamMessage(state, message) {
|
|
|
13216
13848
|
state.currentMessageStartTime = getCurrentUnixTimestamp();
|
|
13217
13849
|
}
|
|
13218
13850
|
if (message.type === "assistant" && message.message?.usage) {
|
|
13851
|
+
const parentToolUseId = message.parent_tool_use_id ?? null;
|
|
13852
|
+
const parentKey = llmParentKey(parentToolUseId);
|
|
13853
|
+
if (!state.activeLlmSpansByParentToolUse.has(parentKey)) {
|
|
13854
|
+
let llmParentSpan = await state.span.export();
|
|
13855
|
+
if (parentToolUseId) {
|
|
13856
|
+
const subAgentSpan = await ensureSubAgentSpan(
|
|
13857
|
+
state.pendingSubAgentNames,
|
|
13858
|
+
state.span,
|
|
13859
|
+
state.subAgentSpans,
|
|
13860
|
+
parentToolUseId
|
|
13861
|
+
);
|
|
13862
|
+
llmParentSpan = await subAgentSpan.export();
|
|
13863
|
+
}
|
|
13864
|
+
const llmSpan = startSpan({
|
|
13865
|
+
name: "anthropic.messages.create",
|
|
13866
|
+
parent: llmParentSpan,
|
|
13867
|
+
spanAttributes: {
|
|
13868
|
+
type: "llm" /* LLM */
|
|
13869
|
+
},
|
|
13870
|
+
startTime: state.currentMessageStartTime
|
|
13871
|
+
});
|
|
13872
|
+
state.activeLlmSpansByParentToolUse.set(parentKey, llmSpan);
|
|
13873
|
+
}
|
|
13219
13874
|
state.currentMessages.push(message);
|
|
13220
13875
|
}
|
|
13221
13876
|
if (message.type !== "result" || !message.usage) {
|
|
@@ -13276,6 +13931,10 @@ async function finalizeQuerySpan(state) {
|
|
|
13276
13931
|
}
|
|
13277
13932
|
}
|
|
13278
13933
|
} finally {
|
|
13934
|
+
for (const llmSpan of state.activeLlmSpansByParentToolUse.values()) {
|
|
13935
|
+
llmSpan.end();
|
|
13936
|
+
}
|
|
13937
|
+
state.activeLlmSpansByParentToolUse.clear();
|
|
13279
13938
|
for (const [id, subAgentSpan] of state.subAgentSpans) {
|
|
13280
13939
|
if (!state.endedSubAgentSpans.has(id)) {
|
|
13281
13940
|
subAgentSpan.end();
|
|
@@ -13341,26 +14000,51 @@ var ClaudeAgentSDKPlugin = class extends BasePlugin {
|
|
|
13341
14000
|
console.error("Error extracting input for Claude Agent SDK:", error);
|
|
13342
14001
|
}
|
|
13343
14002
|
const activeToolSpans = /* @__PURE__ */ new Map();
|
|
14003
|
+
const activeLlmSpansByParentToolUse = /* @__PURE__ */ new Map();
|
|
13344
14004
|
const subAgentSpans = /* @__PURE__ */ new Map();
|
|
13345
14005
|
const endedSubAgentSpans = /* @__PURE__ */ new Set();
|
|
13346
14006
|
const toolUseToParent = /* @__PURE__ */ new Map();
|
|
14007
|
+
const latestLlmParentBySubAgentToolUse = /* @__PURE__ */ new Map();
|
|
14008
|
+
const latestRootLlmParentRef = {
|
|
14009
|
+
value: void 0
|
|
14010
|
+
};
|
|
13347
14011
|
const pendingSubAgentNames = /* @__PURE__ */ new Map();
|
|
14012
|
+
const localToolContext = createClaudeLocalToolContext();
|
|
14013
|
+
const { hasLocalToolHandlers, localToolHookNames } = prepareLocalToolHandlersInMcpServers(options.mcpServers);
|
|
14014
|
+
const skipLocalToolHooks = options[CLAUDE_AGENT_SDK_SKIP_LOCAL_TOOL_HOOKS_OPTION] === true || hasLocalToolHandlers;
|
|
14015
|
+
const resolveToolUseParentSpan = async (toolUseID) => {
|
|
14016
|
+
const parentToolUseId = toolUseToParent.get(toolUseID) ?? null;
|
|
14017
|
+
const parentKey = llmParentKey(parentToolUseId);
|
|
14018
|
+
const activeLlmSpan = activeLlmSpansByParentToolUse.get(parentKey);
|
|
14019
|
+
if (activeLlmSpan) {
|
|
14020
|
+
return activeLlmSpan.export();
|
|
14021
|
+
}
|
|
14022
|
+
if (parentToolUseId) {
|
|
14023
|
+
const parentLlm = latestLlmParentBySubAgentToolUse.get(parentToolUseId);
|
|
14024
|
+
if (parentLlm) {
|
|
14025
|
+
return parentLlm;
|
|
14026
|
+
}
|
|
14027
|
+
const subAgentSpan = await ensureSubAgentSpan(
|
|
14028
|
+
pendingSubAgentNames,
|
|
14029
|
+
span,
|
|
14030
|
+
subAgentSpans,
|
|
14031
|
+
parentToolUseId
|
|
14032
|
+
);
|
|
14033
|
+
return subAgentSpan.export();
|
|
14034
|
+
}
|
|
14035
|
+
if (latestRootLlmParentRef.value) {
|
|
14036
|
+
return latestRootLlmParentRef.value;
|
|
14037
|
+
}
|
|
14038
|
+
return span.export();
|
|
14039
|
+
};
|
|
14040
|
+
localToolContext.resolveLocalToolParent = resolveToolUseParentSpan;
|
|
14041
|
+
setClaudeLocalToolParentResolver(resolveToolUseParentSpan);
|
|
13348
14042
|
const optionsWithHooks = injectTracingHooks(
|
|
13349
14043
|
options,
|
|
13350
|
-
|
|
13351
|
-
const parentToolUseId = toolUseToParent.get(toolUseID);
|
|
13352
|
-
if (parentToolUseId) {
|
|
13353
|
-
const subAgentSpan = await ensureSubAgentSpan(
|
|
13354
|
-
pendingSubAgentNames,
|
|
13355
|
-
span,
|
|
13356
|
-
subAgentSpans,
|
|
13357
|
-
parentToolUseId
|
|
13358
|
-
);
|
|
13359
|
-
return subAgentSpan.export();
|
|
13360
|
-
}
|
|
13361
|
-
return span.export();
|
|
13362
|
-
},
|
|
14044
|
+
resolveToolUseParentSpan,
|
|
13363
14045
|
activeToolSpans,
|
|
14046
|
+
localToolHookNames,
|
|
14047
|
+
skipLocalToolHooks,
|
|
13364
14048
|
subAgentSpans,
|
|
13365
14049
|
endedSubAgentSpans
|
|
13366
14050
|
);
|
|
@@ -13368,6 +14052,7 @@ var ClaudeAgentSDKPlugin = class extends BasePlugin {
|
|
|
13368
14052
|
event.arguments[0] = params;
|
|
13369
14053
|
spans.set(event, {
|
|
13370
14054
|
accumulatedOutputTokens: 0,
|
|
14055
|
+
activeLlmSpansByParentToolUse,
|
|
13371
14056
|
activeToolSpans,
|
|
13372
14057
|
capturedPromptMessages,
|
|
13373
14058
|
currentMessageId: void 0,
|
|
@@ -13383,7 +14068,10 @@ var ClaudeAgentSDKPlugin = class extends BasePlugin {
|
|
|
13383
14068
|
promptStarted: () => promptStarted,
|
|
13384
14069
|
span,
|
|
13385
14070
|
subAgentSpans,
|
|
13386
|
-
|
|
14071
|
+
latestLlmParentBySubAgentToolUse,
|
|
14072
|
+
latestRootLlmParentRef,
|
|
14073
|
+
toolUseToParent,
|
|
14074
|
+
localToolContext
|
|
13387
14075
|
});
|
|
13388
14076
|
},
|
|
13389
14077
|
end: (event) => {
|
|
@@ -13391,7 +14079,10 @@ var ClaudeAgentSDKPlugin = class extends BasePlugin {
|
|
|
13391
14079
|
if (!state) {
|
|
13392
14080
|
return;
|
|
13393
14081
|
}
|
|
13394
|
-
const eventResult =
|
|
14082
|
+
const eventResult = bindClaudeLocalToolContextToAsyncIterable(
|
|
14083
|
+
event.result,
|
|
14084
|
+
state.localToolContext
|
|
14085
|
+
);
|
|
13395
14086
|
if (eventResult === void 0) {
|
|
13396
14087
|
state.span.end();
|
|
13397
14088
|
spans.delete(event);
|
|
@@ -13596,19 +14287,20 @@ function ensureSpanState(states, event, create) {
|
|
|
13596
14287
|
}
|
|
13597
14288
|
function bindCurrentSpanStoreToStart2(tracingChannel2, states, create) {
|
|
13598
14289
|
const state = _internalGetGlobalState();
|
|
14290
|
+
const contextManager = state?.contextManager;
|
|
13599
14291
|
const startChannel = tracingChannel2.start;
|
|
13600
|
-
const currentSpanStore =
|
|
14292
|
+
const currentSpanStore = contextManager ? contextManager[BRAINTRUST_CURRENT_SPAN_STORE] : void 0;
|
|
13601
14293
|
if (!startChannel?.bindStore || !currentSpanStore) {
|
|
13602
14294
|
return void 0;
|
|
13603
14295
|
}
|
|
13604
|
-
startChannel.bindStore(
|
|
13605
|
-
|
|
13606
|
-
(event) => ensureSpanState(
|
|
14296
|
+
startChannel.bindStore(currentSpanStore, (event) => {
|
|
14297
|
+
const span = ensureSpanState(
|
|
13607
14298
|
states,
|
|
13608
14299
|
event,
|
|
13609
14300
|
() => create(event)
|
|
13610
|
-
).span
|
|
13611
|
-
|
|
14301
|
+
).span;
|
|
14302
|
+
return contextManager.wrapSpanForStore(span);
|
|
14303
|
+
});
|
|
13612
14304
|
return () => {
|
|
13613
14305
|
startChannel.unbindStore?.(currentSpanStore);
|
|
13614
14306
|
};
|
|
@@ -14003,20 +14695,8 @@ function tryToDict(obj) {
|
|
|
14003
14695
|
return null;
|
|
14004
14696
|
}
|
|
14005
14697
|
|
|
14006
|
-
// src/instrumentation/plugins/openrouter-channels.ts
|
|
14007
|
-
var
|
|
14008
|
-
chatSend: channel({
|
|
14009
|
-
channelName: "chat.send",
|
|
14010
|
-
kind: "async"
|
|
14011
|
-
}),
|
|
14012
|
-
embeddingsGenerate: channel({
|
|
14013
|
-
channelName: "embeddings.generate",
|
|
14014
|
-
kind: "async"
|
|
14015
|
-
}),
|
|
14016
|
-
betaResponsesSend: channel({
|
|
14017
|
-
channelName: "beta.responses.send",
|
|
14018
|
-
kind: "async"
|
|
14019
|
-
}),
|
|
14698
|
+
// src/instrumentation/plugins/openrouter-agent-channels.ts
|
|
14699
|
+
var openRouterAgentChannels = defineChannels("@openrouter/agent", {
|
|
14020
14700
|
callModel: channel({
|
|
14021
14701
|
channelName: "callModel",
|
|
14022
14702
|
kind: "sync-stream"
|
|
@@ -14031,65 +14711,862 @@ var openRouterChannels = defineChannels("@openrouter/sdk", {
|
|
|
14031
14711
|
})
|
|
14032
14712
|
});
|
|
14033
14713
|
|
|
14034
|
-
// src/instrumentation/plugins/openrouter-plugin.ts
|
|
14035
|
-
var
|
|
14714
|
+
// src/instrumentation/plugins/openrouter-agent-plugin.ts
|
|
14715
|
+
var OpenRouterAgentPlugin = class extends BasePlugin {
|
|
14036
14716
|
onEnable() {
|
|
14037
|
-
this.
|
|
14717
|
+
this.subscribeToOpenRouterAgentChannels();
|
|
14038
14718
|
}
|
|
14039
14719
|
onDisable() {
|
|
14040
14720
|
this.unsubscribers = unsubscribeAll(this.unsubscribers);
|
|
14041
14721
|
}
|
|
14042
|
-
|
|
14722
|
+
subscribeToOpenRouterAgentChannels() {
|
|
14043
14723
|
this.unsubscribers.push(
|
|
14044
|
-
|
|
14045
|
-
name: "openrouter.
|
|
14724
|
+
traceSyncStreamChannel(openRouterAgentChannels.callModel, {
|
|
14725
|
+
name: "openrouter.callModel",
|
|
14046
14726
|
type: "llm" /* LLM */,
|
|
14047
14727
|
extractInput: (args) => {
|
|
14048
|
-
const request =
|
|
14049
|
-
const chatGenerationParams = isObject(request?.chatGenerationParams) ? request.chatGenerationParams : {};
|
|
14050
|
-
const httpReferer = request?.httpReferer;
|
|
14051
|
-
const xTitle = request?.xTitle;
|
|
14052
|
-
const { messages, ...metadata } = chatGenerationParams;
|
|
14728
|
+
const request = getOpenRouterCallModelRequestArg(args);
|
|
14053
14729
|
return {
|
|
14054
|
-
input:
|
|
14055
|
-
metadata:
|
|
14730
|
+
input: request ? extractOpenRouterCallModelInput(request) : void 0,
|
|
14731
|
+
metadata: request ? extractOpenRouterCallModelMetadata(request) : { provider: "openrouter" }
|
|
14056
14732
|
};
|
|
14057
14733
|
},
|
|
14058
|
-
|
|
14059
|
-
return
|
|
14060
|
-
|
|
14061
|
-
|
|
14062
|
-
|
|
14063
|
-
|
|
14064
|
-
|
|
14065
|
-
}
|
|
14066
|
-
return metrics;
|
|
14067
|
-
},
|
|
14068
|
-
aggregateChunks: aggregateOpenRouterChatChunks
|
|
14734
|
+
patchResult: ({ endEvent, result, span }) => {
|
|
14735
|
+
return patchOpenRouterCallModelResult({
|
|
14736
|
+
request: getOpenRouterCallModelRequestArg(endEvent.arguments),
|
|
14737
|
+
result,
|
|
14738
|
+
span
|
|
14739
|
+
});
|
|
14740
|
+
}
|
|
14069
14741
|
})
|
|
14070
14742
|
);
|
|
14071
14743
|
this.unsubscribers.push(
|
|
14072
|
-
traceAsyncChannel(
|
|
14073
|
-
name: "openrouter.
|
|
14744
|
+
traceAsyncChannel(openRouterAgentChannels.callModelTurn, {
|
|
14745
|
+
name: "openrouter.beta.responses.send",
|
|
14074
14746
|
type: "llm" /* LLM */,
|
|
14075
|
-
extractInput: (args) => {
|
|
14076
|
-
const request =
|
|
14077
|
-
const
|
|
14078
|
-
|
|
14079
|
-
|
|
14080
|
-
|
|
14747
|
+
extractInput: (args, event) => {
|
|
14748
|
+
const request = getOpenRouterCallModelRequestArg(args);
|
|
14749
|
+
const metadata = request ? extractOpenRouterCallModelMetadata(request) : { provider: "openrouter" };
|
|
14750
|
+
if (isObject(metadata) && "tools" in metadata) {
|
|
14751
|
+
delete metadata.tools;
|
|
14752
|
+
}
|
|
14081
14753
|
return {
|
|
14082
|
-
input,
|
|
14083
|
-
metadata:
|
|
14084
|
-
metadata,
|
|
14085
|
-
|
|
14086
|
-
|
|
14087
|
-
|
|
14754
|
+
input: request ? extractOpenRouterCallModelInput(request) : void 0,
|
|
14755
|
+
metadata: {
|
|
14756
|
+
...metadata,
|
|
14757
|
+
step: event.step,
|
|
14758
|
+
step_type: event.stepType
|
|
14759
|
+
}
|
|
14088
14760
|
};
|
|
14089
14761
|
},
|
|
14090
|
-
extractOutput: (result) =>
|
|
14762
|
+
extractOutput: (result) => extractOpenRouterResponseOutput(result),
|
|
14763
|
+
extractMetadata: (result, event) => {
|
|
14091
14764
|
if (!isObject(result)) {
|
|
14092
|
-
return
|
|
14765
|
+
return {
|
|
14766
|
+
step: event?.step,
|
|
14767
|
+
step_type: event?.stepType
|
|
14768
|
+
};
|
|
14769
|
+
}
|
|
14770
|
+
return {
|
|
14771
|
+
...extractOpenRouterResponseMetadata(result) || {},
|
|
14772
|
+
...event?.step !== void 0 ? { step: event.step } : {},
|
|
14773
|
+
...event?.stepType ? { step_type: event.stepType } : {}
|
|
14774
|
+
};
|
|
14775
|
+
},
|
|
14776
|
+
extractMetrics: (result) => isObject(result) ? parseOpenRouterMetricsFromUsage(result.usage) : {}
|
|
14777
|
+
})
|
|
14778
|
+
);
|
|
14779
|
+
this.unsubscribers.push(
|
|
14780
|
+
traceStreamingChannel(openRouterAgentChannels.toolExecute, {
|
|
14781
|
+
name: "openrouter.tool",
|
|
14782
|
+
type: "tool" /* TOOL */,
|
|
14783
|
+
extractInput: (args, event) => ({
|
|
14784
|
+
input: args[0],
|
|
14785
|
+
metadata: {
|
|
14786
|
+
provider: "openrouter",
|
|
14787
|
+
tool_name: event.toolName,
|
|
14788
|
+
...event.toolCallId ? { tool_call_id: event.toolCallId } : {}
|
|
14789
|
+
}
|
|
14790
|
+
}),
|
|
14791
|
+
extractOutput: (result) => result,
|
|
14792
|
+
extractMetrics: () => ({}),
|
|
14793
|
+
aggregateChunks: (chunks) => ({
|
|
14794
|
+
output: chunks.length > 0 ? chunks[chunks.length - 1] : void 0,
|
|
14795
|
+
metrics: {}
|
|
14796
|
+
})
|
|
14797
|
+
})
|
|
14798
|
+
);
|
|
14799
|
+
const callModelChannel = openRouterAgentChannels.callModel.tracingChannel();
|
|
14800
|
+
const callModelHandlers = {
|
|
14801
|
+
start: (event) => {
|
|
14802
|
+
const request = getOpenRouterCallModelRequestArg(event.arguments);
|
|
14803
|
+
if (!request) {
|
|
14804
|
+
return;
|
|
14805
|
+
}
|
|
14806
|
+
patchOpenRouterCallModelRequestTools(request);
|
|
14807
|
+
}
|
|
14808
|
+
};
|
|
14809
|
+
callModelChannel.subscribe(callModelHandlers);
|
|
14810
|
+
this.unsubscribers.push(() => {
|
|
14811
|
+
callModelChannel.unsubscribe(callModelHandlers);
|
|
14812
|
+
});
|
|
14813
|
+
}
|
|
14814
|
+
};
|
|
14815
|
+
function normalizeArgs(args) {
|
|
14816
|
+
if (Array.isArray(args)) {
|
|
14817
|
+
return args;
|
|
14818
|
+
}
|
|
14819
|
+
if (isArrayLike(args)) {
|
|
14820
|
+
return Array.from(args);
|
|
14821
|
+
}
|
|
14822
|
+
return [args];
|
|
14823
|
+
}
|
|
14824
|
+
function isArrayLike(value) {
|
|
14825
|
+
return isObject(value) && "length" in value && typeof value.length === "number" && Number.isInteger(value.length) && value.length >= 0;
|
|
14826
|
+
}
|
|
14827
|
+
function getOpenRouterCallModelRequestArg(args) {
|
|
14828
|
+
const normalizedArgs = normalizeArgs(args);
|
|
14829
|
+
const keyedRequestArg = normalizedArgs.find(
|
|
14830
|
+
(arg) => isObject(arg) && ("input" in arg || "model" in arg || "tools" in arg)
|
|
14831
|
+
);
|
|
14832
|
+
if (isObject(keyedRequestArg)) {
|
|
14833
|
+
return keyedRequestArg;
|
|
14834
|
+
}
|
|
14835
|
+
const firstObjectArg = normalizedArgs.find((arg) => isObject(arg));
|
|
14836
|
+
return isObject(firstObjectArg) ? firstObjectArg : void 0;
|
|
14837
|
+
}
|
|
14838
|
+
var TOKEN_NAME_MAP2 = {
|
|
14839
|
+
promptTokens: "prompt_tokens",
|
|
14840
|
+
inputTokens: "prompt_tokens",
|
|
14841
|
+
completionTokens: "completion_tokens",
|
|
14842
|
+
outputTokens: "completion_tokens",
|
|
14843
|
+
totalTokens: "tokens",
|
|
14844
|
+
prompt_tokens: "prompt_tokens",
|
|
14845
|
+
input_tokens: "prompt_tokens",
|
|
14846
|
+
completion_tokens: "completion_tokens",
|
|
14847
|
+
output_tokens: "completion_tokens",
|
|
14848
|
+
total_tokens: "tokens"
|
|
14849
|
+
};
|
|
14850
|
+
var TOKEN_DETAIL_PREFIX_MAP = {
|
|
14851
|
+
promptTokensDetails: "prompt",
|
|
14852
|
+
inputTokensDetails: "prompt",
|
|
14853
|
+
completionTokensDetails: "completion",
|
|
14854
|
+
outputTokensDetails: "completion",
|
|
14855
|
+
costDetails: "cost",
|
|
14856
|
+
prompt_tokens_details: "prompt",
|
|
14857
|
+
input_tokens_details: "prompt",
|
|
14858
|
+
completion_tokens_details: "completion",
|
|
14859
|
+
output_tokens_details: "completion",
|
|
14860
|
+
cost_details: "cost"
|
|
14861
|
+
};
|
|
14862
|
+
function camelToSnake(value) {
|
|
14863
|
+
return value.replace(/[A-Z]/g, (match) => `_${match.toLowerCase()}`);
|
|
14864
|
+
}
|
|
14865
|
+
function parseOpenRouterMetricsFromUsage(usage) {
|
|
14866
|
+
if (!isObject(usage)) {
|
|
14867
|
+
return {};
|
|
14868
|
+
}
|
|
14869
|
+
const metrics = {};
|
|
14870
|
+
for (const [name, value] of Object.entries(usage)) {
|
|
14871
|
+
if (typeof value === "number") {
|
|
14872
|
+
metrics[TOKEN_NAME_MAP2[name] || camelToSnake(name)] = value;
|
|
14873
|
+
continue;
|
|
14874
|
+
}
|
|
14875
|
+
if (!isObject(value)) {
|
|
14876
|
+
continue;
|
|
14877
|
+
}
|
|
14878
|
+
const prefix = TOKEN_DETAIL_PREFIX_MAP[name];
|
|
14879
|
+
if (!prefix) {
|
|
14880
|
+
continue;
|
|
14881
|
+
}
|
|
14882
|
+
for (const [nestedName, nestedValue] of Object.entries(value)) {
|
|
14883
|
+
if (typeof nestedValue !== "number") {
|
|
14884
|
+
continue;
|
|
14885
|
+
}
|
|
14886
|
+
metrics[`${prefix}_${camelToSnake(nestedName)}`] = nestedValue;
|
|
14887
|
+
}
|
|
14888
|
+
}
|
|
14889
|
+
return metrics;
|
|
14890
|
+
}
|
|
14891
|
+
function extractOpenRouterUsageMetadata(usage) {
|
|
14892
|
+
if (!isObject(usage)) {
|
|
14893
|
+
return void 0;
|
|
14894
|
+
}
|
|
14895
|
+
const metadata = {};
|
|
14896
|
+
if (typeof usage.isByok === "boolean") {
|
|
14897
|
+
metadata.is_byok = usage.isByok;
|
|
14898
|
+
} else if (typeof usage.is_byok === "boolean") {
|
|
14899
|
+
metadata.is_byok = usage.is_byok;
|
|
14900
|
+
}
|
|
14901
|
+
return Object.keys(metadata).length > 0 ? metadata : void 0;
|
|
14902
|
+
}
|
|
14903
|
+
var OMITTED_OPENROUTER_KEYS = /* @__PURE__ */ new Set([
|
|
14904
|
+
"execute",
|
|
14905
|
+
"render",
|
|
14906
|
+
"nextTurnParams",
|
|
14907
|
+
"requireApproval"
|
|
14908
|
+
]);
|
|
14909
|
+
function parseOpenRouterModelString(model) {
|
|
14910
|
+
if (typeof model !== "string") {
|
|
14911
|
+
return { model };
|
|
14912
|
+
}
|
|
14913
|
+
const slashIndex = model.indexOf("/");
|
|
14914
|
+
if (slashIndex > 0 && slashIndex < model.length - 1) {
|
|
14915
|
+
return {
|
|
14916
|
+
provider: model.substring(0, slashIndex),
|
|
14917
|
+
model: model.substring(slashIndex + 1)
|
|
14918
|
+
};
|
|
14919
|
+
}
|
|
14920
|
+
return { model };
|
|
14921
|
+
}
|
|
14922
|
+
function isZodSchema3(value) {
|
|
14923
|
+
return value != null && typeof value === "object" && "_def" in value && typeof value._def === "object";
|
|
14924
|
+
}
|
|
14925
|
+
function serializeZodSchema3(schema) {
|
|
14926
|
+
try {
|
|
14927
|
+
return zodToJsonSchema(schema);
|
|
14928
|
+
} catch {
|
|
14929
|
+
return {
|
|
14930
|
+
type: "object",
|
|
14931
|
+
description: "Zod schema (conversion failed)"
|
|
14932
|
+
};
|
|
14933
|
+
}
|
|
14934
|
+
}
|
|
14935
|
+
function serializeOpenRouterTool(tool) {
|
|
14936
|
+
if (!isObject(tool)) {
|
|
14937
|
+
return tool;
|
|
14938
|
+
}
|
|
14939
|
+
const serialized = {};
|
|
14940
|
+
for (const [key, value] of Object.entries(tool)) {
|
|
14941
|
+
if (OMITTED_OPENROUTER_KEYS.has(key)) {
|
|
14942
|
+
continue;
|
|
14943
|
+
}
|
|
14944
|
+
if (key === "function" && isObject(value)) {
|
|
14945
|
+
serialized.function = sanitizeOpenRouterLoggedValue(value);
|
|
14946
|
+
continue;
|
|
14947
|
+
}
|
|
14948
|
+
serialized[key] = sanitizeOpenRouterLoggedValue(value);
|
|
14949
|
+
}
|
|
14950
|
+
return serialized;
|
|
14951
|
+
}
|
|
14952
|
+
function serializeOpenRouterToolsForLogging(tools) {
|
|
14953
|
+
if (!Array.isArray(tools)) {
|
|
14954
|
+
return void 0;
|
|
14955
|
+
}
|
|
14956
|
+
return tools.map((tool) => serializeOpenRouterTool(tool));
|
|
14957
|
+
}
|
|
14958
|
+
function sanitizeOpenRouterLoggedValue(value) {
|
|
14959
|
+
if (isZodSchema3(value)) {
|
|
14960
|
+
return serializeZodSchema3(value);
|
|
14961
|
+
}
|
|
14962
|
+
if (typeof value === "function") {
|
|
14963
|
+
return "[Function]";
|
|
14964
|
+
}
|
|
14965
|
+
if (Array.isArray(value)) {
|
|
14966
|
+
return value.map((entry) => sanitizeOpenRouterLoggedValue(entry));
|
|
14967
|
+
}
|
|
14968
|
+
if (!isObject(value)) {
|
|
14969
|
+
return value;
|
|
14970
|
+
}
|
|
14971
|
+
const sanitized = {};
|
|
14972
|
+
for (const [key, entry] of Object.entries(value)) {
|
|
14973
|
+
if (OMITTED_OPENROUTER_KEYS.has(key)) {
|
|
14974
|
+
continue;
|
|
14975
|
+
}
|
|
14976
|
+
if (key === "tools" && Array.isArray(entry)) {
|
|
14977
|
+
sanitized.tools = serializeOpenRouterToolsForLogging(entry);
|
|
14978
|
+
continue;
|
|
14979
|
+
}
|
|
14980
|
+
sanitized[key] = sanitizeOpenRouterLoggedValue(entry);
|
|
14981
|
+
}
|
|
14982
|
+
return sanitized;
|
|
14983
|
+
}
|
|
14984
|
+
function buildOpenRouterMetadata(metadata, httpReferer, appTitle, appCategories, xTitle) {
|
|
14985
|
+
const sanitized = sanitizeOpenRouterLoggedValue(metadata);
|
|
14986
|
+
const metadataRecord = isObject(sanitized) ? sanitized : {};
|
|
14987
|
+
const { model, provider: providerRouting, ...rest } = metadataRecord;
|
|
14988
|
+
const normalizedModel = parseOpenRouterModelString(model);
|
|
14989
|
+
return {
|
|
14990
|
+
...rest,
|
|
14991
|
+
...normalizedModel.model !== void 0 ? { model: normalizedModel.model } : {},
|
|
14992
|
+
...providerRouting !== void 0 ? { providerRouting } : {},
|
|
14993
|
+
...httpReferer !== void 0 ? { httpReferer } : {},
|
|
14994
|
+
...appTitle !== void 0 ? { appTitle } : {},
|
|
14995
|
+
...appCategories !== void 0 ? { appCategories } : {},
|
|
14996
|
+
...xTitle !== void 0 ? { xTitle } : {},
|
|
14997
|
+
provider: normalizedModel.provider || "openrouter"
|
|
14998
|
+
};
|
|
14999
|
+
}
|
|
15000
|
+
function extractOpenRouterCallModelInput(request) {
|
|
15001
|
+
return isObject(request) && "input" in request ? sanitizeOpenRouterLoggedValue(request.input) : void 0;
|
|
15002
|
+
}
|
|
15003
|
+
function extractOpenRouterCallModelMetadata(request) {
|
|
15004
|
+
if (!isObject(request)) {
|
|
15005
|
+
return { provider: "openrouter" };
|
|
15006
|
+
}
|
|
15007
|
+
const { input: _input, ...metadata } = request;
|
|
15008
|
+
return buildOpenRouterMetadata(
|
|
15009
|
+
metadata,
|
|
15010
|
+
void 0,
|
|
15011
|
+
void 0,
|
|
15012
|
+
void 0,
|
|
15013
|
+
void 0
|
|
15014
|
+
);
|
|
15015
|
+
}
|
|
15016
|
+
function extractOpenRouterResponseMetadata(result) {
|
|
15017
|
+
if (!isObject(result)) {
|
|
15018
|
+
return void 0;
|
|
15019
|
+
}
|
|
15020
|
+
const { output: _output, data: _data, usage, ...metadata } = result;
|
|
15021
|
+
const sanitized = sanitizeOpenRouterLoggedValue(metadata);
|
|
15022
|
+
const metadataRecord = isObject(sanitized) ? sanitized : {};
|
|
15023
|
+
const { model, provider, ...rest } = metadataRecord;
|
|
15024
|
+
const normalizedModel = parseOpenRouterModelString(model);
|
|
15025
|
+
const normalizedProvider = (typeof provider === "string" ? provider : void 0) || normalizedModel.provider;
|
|
15026
|
+
const usageMetadata = extractOpenRouterUsageMetadata(usage);
|
|
15027
|
+
const combined = {
|
|
15028
|
+
...rest,
|
|
15029
|
+
...normalizedModel.model !== void 0 ? { model: normalizedModel.model } : {},
|
|
15030
|
+
...usageMetadata || {},
|
|
15031
|
+
...normalizedProvider !== void 0 ? { provider: normalizedProvider } : {}
|
|
15032
|
+
};
|
|
15033
|
+
return Object.keys(combined).length > 0 ? combined : void 0;
|
|
15034
|
+
}
|
|
15035
|
+
function extractOpenRouterResponseOutput(response, fallbackOutput) {
|
|
15036
|
+
if (isObject(response) && "output" in response && response.output !== void 0) {
|
|
15037
|
+
return sanitizeOpenRouterLoggedValue(response.output);
|
|
15038
|
+
}
|
|
15039
|
+
if (fallbackOutput !== void 0) {
|
|
15040
|
+
return sanitizeOpenRouterLoggedValue(fallbackOutput);
|
|
15041
|
+
}
|
|
15042
|
+
return void 0;
|
|
15043
|
+
}
|
|
15044
|
+
var OPENROUTER_WRAPPED_TOOL = Symbol("braintrust.openrouter.wrappedTool");
|
|
15045
|
+
function patchOpenRouterCallModelRequestTools(request) {
|
|
15046
|
+
if (!Array.isArray(request.tools) || request.tools.length === 0) {
|
|
15047
|
+
return void 0;
|
|
15048
|
+
}
|
|
15049
|
+
const originalTools = request.tools;
|
|
15050
|
+
const wrappedTools = originalTools.map((tool) => wrapOpenRouterTool(tool));
|
|
15051
|
+
const didPatch = wrappedTools.some(
|
|
15052
|
+
(tool, index) => tool !== originalTools[index]
|
|
15053
|
+
);
|
|
15054
|
+
if (!didPatch) {
|
|
15055
|
+
return void 0;
|
|
15056
|
+
}
|
|
15057
|
+
request.tools = wrappedTools;
|
|
15058
|
+
return () => {
|
|
15059
|
+
request.tools = originalTools;
|
|
15060
|
+
};
|
|
15061
|
+
}
|
|
15062
|
+
function wrapOpenRouterTool(tool) {
|
|
15063
|
+
if (isWrappedTool(tool) || !tool.function || typeof tool.function !== "object" || typeof tool.function.execute !== "function") {
|
|
15064
|
+
return tool;
|
|
15065
|
+
}
|
|
15066
|
+
const toolName = tool.function.name || "tool";
|
|
15067
|
+
const originalExecute = tool.function.execute;
|
|
15068
|
+
const wrappedTool = {
|
|
15069
|
+
...tool,
|
|
15070
|
+
function: {
|
|
15071
|
+
...tool.function,
|
|
15072
|
+
execute(...args) {
|
|
15073
|
+
return traceToolExecution({
|
|
15074
|
+
args,
|
|
15075
|
+
execute: () => Reflect.apply(originalExecute, this, args),
|
|
15076
|
+
toolCallId: getToolCallId(args[1]),
|
|
15077
|
+
toolName
|
|
15078
|
+
});
|
|
15079
|
+
}
|
|
15080
|
+
}
|
|
15081
|
+
};
|
|
15082
|
+
Object.defineProperty(wrappedTool, OPENROUTER_WRAPPED_TOOL, {
|
|
15083
|
+
value: true,
|
|
15084
|
+
enumerable: false,
|
|
15085
|
+
configurable: false
|
|
15086
|
+
});
|
|
15087
|
+
return wrappedTool;
|
|
15088
|
+
}
|
|
15089
|
+
function isWrappedTool(tool) {
|
|
15090
|
+
return Boolean(tool[OPENROUTER_WRAPPED_TOOL]);
|
|
15091
|
+
}
|
|
15092
|
+
function traceToolExecution(args) {
|
|
15093
|
+
const tracingChannel2 = openRouterAgentChannels.toolExecute.tracingChannel();
|
|
15094
|
+
const input = args.args.length > 0 ? args.args[0] : void 0;
|
|
15095
|
+
const event = {
|
|
15096
|
+
arguments: [input],
|
|
15097
|
+
span_info: {
|
|
15098
|
+
name: args.toolName
|
|
15099
|
+
},
|
|
15100
|
+
toolCallId: args.toolCallId,
|
|
15101
|
+
toolName: args.toolName
|
|
15102
|
+
};
|
|
15103
|
+
tracingChannel2.start.publish(event);
|
|
15104
|
+
try {
|
|
15105
|
+
const result = args.execute();
|
|
15106
|
+
return publishToolResult(tracingChannel2, event, result);
|
|
15107
|
+
} catch (error) {
|
|
15108
|
+
event.error = normalizeError(error);
|
|
15109
|
+
tracingChannel2.error.publish(event);
|
|
15110
|
+
throw error;
|
|
15111
|
+
}
|
|
15112
|
+
}
|
|
15113
|
+
function publishToolResult(tracingChannel2, event, result) {
|
|
15114
|
+
if (isPromiseLike3(result)) {
|
|
15115
|
+
return result.then(
|
|
15116
|
+
(resolved) => {
|
|
15117
|
+
event.result = resolved;
|
|
15118
|
+
tracingChannel2.asyncEnd.publish(event);
|
|
15119
|
+
return resolved;
|
|
15120
|
+
},
|
|
15121
|
+
(error) => {
|
|
15122
|
+
event.error = normalizeError(error);
|
|
15123
|
+
tracingChannel2.error.publish(event);
|
|
15124
|
+
throw error;
|
|
15125
|
+
}
|
|
15126
|
+
);
|
|
15127
|
+
}
|
|
15128
|
+
event.result = result;
|
|
15129
|
+
tracingChannel2.asyncEnd.publish(event);
|
|
15130
|
+
return result;
|
|
15131
|
+
}
|
|
15132
|
+
function getToolCallId(context) {
|
|
15133
|
+
const toolContext = context;
|
|
15134
|
+
return typeof toolContext?.toolCall?.id === "string" ? toolContext.toolCall.id : void 0;
|
|
15135
|
+
}
|
|
15136
|
+
function isPromiseLike3(value) {
|
|
15137
|
+
return !!value && (typeof value === "object" || typeof value === "function") && "then" in value && typeof value.then === "function";
|
|
15138
|
+
}
|
|
15139
|
+
var OPENROUTER_WRAPPED_CALL_MODEL_RESULT = Symbol(
|
|
15140
|
+
"braintrust.openrouter.wrappedCallModelResult"
|
|
15141
|
+
);
|
|
15142
|
+
var OPENROUTER_CALL_MODEL_STREAM_METHODS = [
|
|
15143
|
+
"getFullResponsesStream",
|
|
15144
|
+
"getItemsStream",
|
|
15145
|
+
"getNewMessagesStream",
|
|
15146
|
+
"getReasoningStream",
|
|
15147
|
+
"getTextStream",
|
|
15148
|
+
"getToolCallsStream",
|
|
15149
|
+
"getToolStream"
|
|
15150
|
+
];
|
|
15151
|
+
var OPENROUTER_CALL_MODEL_CONTEXT_METHODS = [
|
|
15152
|
+
"cancel",
|
|
15153
|
+
"getPendingToolCalls",
|
|
15154
|
+
"getState",
|
|
15155
|
+
"getToolCalls",
|
|
15156
|
+
"requiresApproval"
|
|
15157
|
+
];
|
|
15158
|
+
function patchOpenRouterCallModelResult(args) {
|
|
15159
|
+
const { request, result, span } = args;
|
|
15160
|
+
if (!isObject(result) || isWrappedCallModelResult(result)) {
|
|
15161
|
+
return false;
|
|
15162
|
+
}
|
|
15163
|
+
const resultLike = result;
|
|
15164
|
+
const hasInstrumentableMethod = typeof resultLike.getResponse === "function" || typeof resultLike.getText === "function" || OPENROUTER_CALL_MODEL_STREAM_METHODS.some(
|
|
15165
|
+
(methodName) => typeof resultLike[methodName] === "function"
|
|
15166
|
+
);
|
|
15167
|
+
if (!hasInstrumentableMethod) {
|
|
15168
|
+
return false;
|
|
15169
|
+
}
|
|
15170
|
+
Object.defineProperty(resultLike, OPENROUTER_WRAPPED_CALL_MODEL_RESULT, {
|
|
15171
|
+
value: true,
|
|
15172
|
+
enumerable: false,
|
|
15173
|
+
configurable: false
|
|
15174
|
+
});
|
|
15175
|
+
const originalGetResponse = typeof resultLike.getResponse === "function" ? resultLike.getResponse.bind(resultLike) : void 0;
|
|
15176
|
+
const originalGetInitialResponse = typeof resultLike.getInitialResponse === "function" ? resultLike.getInitialResponse.bind(resultLike) : void 0;
|
|
15177
|
+
const originalMakeFollowupRequest = typeof resultLike.makeFollowupRequest === "function" ? resultLike.makeFollowupRequest.bind(resultLike) : void 0;
|
|
15178
|
+
let ended = false;
|
|
15179
|
+
let tracedTurnCount = 0;
|
|
15180
|
+
const endSpanWithResult = async (response, fallbackOutput) => {
|
|
15181
|
+
if (ended) {
|
|
15182
|
+
return;
|
|
15183
|
+
}
|
|
15184
|
+
ended = true;
|
|
15185
|
+
const finalResponse = getFinalOpenRouterCallModelResponse(
|
|
15186
|
+
resultLike,
|
|
15187
|
+
response
|
|
15188
|
+
);
|
|
15189
|
+
if (finalResponse) {
|
|
15190
|
+
const rounds = getOpenRouterCallModelRounds(resultLike);
|
|
15191
|
+
const metadata = extractOpenRouterCallModelResultMetadata(
|
|
15192
|
+
finalResponse,
|
|
15193
|
+
rounds.length + 1
|
|
15194
|
+
);
|
|
15195
|
+
span.log({
|
|
15196
|
+
output: extractOpenRouterResponseOutput(finalResponse, fallbackOutput),
|
|
15197
|
+
...metadata ? { metadata } : {},
|
|
15198
|
+
metrics: aggregateOpenRouterCallModelMetrics(rounds, finalResponse)
|
|
15199
|
+
});
|
|
15200
|
+
span.end();
|
|
15201
|
+
return;
|
|
15202
|
+
}
|
|
15203
|
+
if (fallbackOutput !== void 0) {
|
|
15204
|
+
span.log({
|
|
15205
|
+
output: fallbackOutput
|
|
15206
|
+
});
|
|
15207
|
+
}
|
|
15208
|
+
span.end();
|
|
15209
|
+
};
|
|
15210
|
+
const endSpanWithError = (error) => {
|
|
15211
|
+
if (ended) {
|
|
15212
|
+
return;
|
|
15213
|
+
}
|
|
15214
|
+
ended = true;
|
|
15215
|
+
span.log({
|
|
15216
|
+
error: normalizeError(error).message
|
|
15217
|
+
});
|
|
15218
|
+
span.end();
|
|
15219
|
+
};
|
|
15220
|
+
const finalizeFromResponse = async (fallbackOutput) => {
|
|
15221
|
+
if (!originalGetResponse) {
|
|
15222
|
+
await endSpanWithResult(void 0, fallbackOutput);
|
|
15223
|
+
return;
|
|
15224
|
+
}
|
|
15225
|
+
try {
|
|
15226
|
+
await endSpanWithResult(await originalGetResponse(), fallbackOutput);
|
|
15227
|
+
} catch {
|
|
15228
|
+
await endSpanWithResult(void 0, fallbackOutput);
|
|
15229
|
+
}
|
|
15230
|
+
};
|
|
15231
|
+
if (originalGetResponse) {
|
|
15232
|
+
resultLike.getResponse = async (...args2) => {
|
|
15233
|
+
return await withCurrent(span, async () => {
|
|
15234
|
+
try {
|
|
15235
|
+
const response = await originalGetResponse(...args2);
|
|
15236
|
+
await endSpanWithResult(response);
|
|
15237
|
+
return response;
|
|
15238
|
+
} catch (error) {
|
|
15239
|
+
endSpanWithError(error);
|
|
15240
|
+
throw error;
|
|
15241
|
+
}
|
|
15242
|
+
});
|
|
15243
|
+
};
|
|
15244
|
+
}
|
|
15245
|
+
if (typeof resultLike.getText === "function") {
|
|
15246
|
+
const originalGetText = resultLike.getText.bind(resultLike);
|
|
15247
|
+
resultLike.getText = async (...args2) => {
|
|
15248
|
+
return await withCurrent(span, async () => {
|
|
15249
|
+
try {
|
|
15250
|
+
const text = await originalGetText(...args2);
|
|
15251
|
+
await finalizeFromResponse(text);
|
|
15252
|
+
return text;
|
|
15253
|
+
} catch (error) {
|
|
15254
|
+
endSpanWithError(error);
|
|
15255
|
+
throw error;
|
|
15256
|
+
}
|
|
15257
|
+
});
|
|
15258
|
+
};
|
|
15259
|
+
}
|
|
15260
|
+
for (const methodName of OPENROUTER_CALL_MODEL_CONTEXT_METHODS) {
|
|
15261
|
+
if (typeof resultLike[methodName] !== "function") {
|
|
15262
|
+
continue;
|
|
15263
|
+
}
|
|
15264
|
+
const originalMethod = resultLike[methodName];
|
|
15265
|
+
resultLike[methodName] = async (...args2) => {
|
|
15266
|
+
return await withCurrent(span, async () => {
|
|
15267
|
+
return await originalMethod.apply(resultLike, args2);
|
|
15268
|
+
});
|
|
15269
|
+
};
|
|
15270
|
+
}
|
|
15271
|
+
for (const methodName of OPENROUTER_CALL_MODEL_STREAM_METHODS) {
|
|
15272
|
+
if (typeof resultLike[methodName] !== "function") {
|
|
15273
|
+
continue;
|
|
15274
|
+
}
|
|
15275
|
+
const originalMethod = resultLike[methodName];
|
|
15276
|
+
resultLike[methodName] = (...args2) => {
|
|
15277
|
+
const stream = withCurrent(
|
|
15278
|
+
span,
|
|
15279
|
+
() => originalMethod.apply(resultLike, args2)
|
|
15280
|
+
);
|
|
15281
|
+
if (!isAsyncIterable3(stream)) {
|
|
15282
|
+
return stream;
|
|
15283
|
+
}
|
|
15284
|
+
return wrapAsyncIterableWithSpan({
|
|
15285
|
+
finalize: finalizeFromResponse,
|
|
15286
|
+
iteratorFactory: () => stream[Symbol.asyncIterator](),
|
|
15287
|
+
onError: endSpanWithError,
|
|
15288
|
+
span
|
|
15289
|
+
});
|
|
15290
|
+
};
|
|
15291
|
+
}
|
|
15292
|
+
if (originalGetInitialResponse) {
|
|
15293
|
+
let initialTurnTraced = false;
|
|
15294
|
+
resultLike.getInitialResponse = async (...args2) => {
|
|
15295
|
+
if (initialTurnTraced) {
|
|
15296
|
+
return await withCurrent(span, async () => {
|
|
15297
|
+
return await originalGetInitialResponse(...args2);
|
|
15298
|
+
});
|
|
15299
|
+
}
|
|
15300
|
+
initialTurnTraced = true;
|
|
15301
|
+
const step = tracedTurnCount + 1;
|
|
15302
|
+
const stepType = tracedTurnCount === 0 ? "initial" : "continue";
|
|
15303
|
+
const response = await traceOpenRouterCallModelTurn({
|
|
15304
|
+
fn: async () => {
|
|
15305
|
+
const nextResponse = await originalGetInitialResponse(...args2);
|
|
15306
|
+
tracedTurnCount++;
|
|
15307
|
+
return nextResponse;
|
|
15308
|
+
},
|
|
15309
|
+
parentSpan: span,
|
|
15310
|
+
request: getOpenRouterResolvedRequest(resultLike, request),
|
|
15311
|
+
step,
|
|
15312
|
+
stepType
|
|
15313
|
+
});
|
|
15314
|
+
return response;
|
|
15315
|
+
};
|
|
15316
|
+
}
|
|
15317
|
+
if (originalMakeFollowupRequest) {
|
|
15318
|
+
resultLike.makeFollowupRequest = async (...args2) => {
|
|
15319
|
+
const currentResponse = args2[0];
|
|
15320
|
+
const toolResults = Array.isArray(args2[1]) ? args2[1] : [];
|
|
15321
|
+
const step = tracedTurnCount + 1;
|
|
15322
|
+
const response = await traceOpenRouterCallModelTurn({
|
|
15323
|
+
fn: async () => {
|
|
15324
|
+
const nextResponse = await originalMakeFollowupRequest(...args2);
|
|
15325
|
+
tracedTurnCount++;
|
|
15326
|
+
return nextResponse;
|
|
15327
|
+
},
|
|
15328
|
+
parentSpan: span,
|
|
15329
|
+
request: buildOpenRouterFollowupRequest(
|
|
15330
|
+
getOpenRouterResolvedRequest(resultLike, request),
|
|
15331
|
+
currentResponse,
|
|
15332
|
+
toolResults
|
|
15333
|
+
),
|
|
15334
|
+
step,
|
|
15335
|
+
stepType: "continue"
|
|
15336
|
+
});
|
|
15337
|
+
return response;
|
|
15338
|
+
};
|
|
15339
|
+
}
|
|
15340
|
+
return true;
|
|
15341
|
+
}
|
|
15342
|
+
async function traceOpenRouterCallModelTurn(args) {
|
|
15343
|
+
const context = {
|
|
15344
|
+
arguments: [args.request],
|
|
15345
|
+
step: args.step,
|
|
15346
|
+
stepType: args.stepType
|
|
15347
|
+
};
|
|
15348
|
+
return await withCurrent(
|
|
15349
|
+
args.parentSpan,
|
|
15350
|
+
() => openRouterAgentChannels.callModelTurn.tracePromise(args.fn, context)
|
|
15351
|
+
);
|
|
15352
|
+
}
|
|
15353
|
+
function isWrappedCallModelResult(value) {
|
|
15354
|
+
return Boolean(
|
|
15355
|
+
isObject(value) && value[OPENROUTER_WRAPPED_CALL_MODEL_RESULT]
|
|
15356
|
+
);
|
|
15357
|
+
}
|
|
15358
|
+
function extractOpenRouterCallModelResultMetadata(response, turnCount) {
|
|
15359
|
+
const combined = {
|
|
15360
|
+
...extractOpenRouterResponseMetadata(response) || {},
|
|
15361
|
+
...turnCount !== void 0 ? { turn_count: turnCount } : {}
|
|
15362
|
+
};
|
|
15363
|
+
return Object.keys(combined).length > 0 ? combined : void 0;
|
|
15364
|
+
}
|
|
15365
|
+
function getFinalOpenRouterCallModelResponse(result, response) {
|
|
15366
|
+
if (isObject(response)) {
|
|
15367
|
+
return response;
|
|
15368
|
+
}
|
|
15369
|
+
return isObject(result.finalResponse) ? result.finalResponse : void 0;
|
|
15370
|
+
}
|
|
15371
|
+
function getOpenRouterCallModelRounds(result) {
|
|
15372
|
+
if (!Array.isArray(result.allToolExecutionRounds)) {
|
|
15373
|
+
return [];
|
|
15374
|
+
}
|
|
15375
|
+
return result.allToolExecutionRounds.filter((round) => isObject(round)).map((round) => ({
|
|
15376
|
+
response: isObject(round.response) ? round.response : void 0,
|
|
15377
|
+
round: typeof round.round === "number" ? round.round : void 0,
|
|
15378
|
+
toolResults: Array.isArray(round.toolResults) ? round.toolResults : []
|
|
15379
|
+
})).filter((round) => round.response !== void 0);
|
|
15380
|
+
}
|
|
15381
|
+
function aggregateOpenRouterCallModelMetrics(rounds, finalResponse) {
|
|
15382
|
+
const metrics = {};
|
|
15383
|
+
const responses = [
|
|
15384
|
+
...rounds.map((round) => round.response).filter(isObject),
|
|
15385
|
+
finalResponse
|
|
15386
|
+
];
|
|
15387
|
+
for (const response of responses) {
|
|
15388
|
+
const responseMetrics = parseOpenRouterMetricsFromUsage(response.usage);
|
|
15389
|
+
for (const [name, value] of Object.entries(responseMetrics)) {
|
|
15390
|
+
metrics[name] = (metrics[name] || 0) + value;
|
|
15391
|
+
}
|
|
15392
|
+
}
|
|
15393
|
+
return metrics;
|
|
15394
|
+
}
|
|
15395
|
+
function buildNextOpenRouterCallModelInput(currentInput, response, toolResults) {
|
|
15396
|
+
const normalizedInput = Array.isArray(currentInput) ? [...currentInput] : currentInput === void 0 ? [] : [currentInput];
|
|
15397
|
+
const responseOutput = Array.isArray(response.output) ? response.output : response.output === void 0 ? [] : [response.output];
|
|
15398
|
+
return [...normalizedInput, ...responseOutput, ...toolResults].map(
|
|
15399
|
+
(entry) => sanitizeOpenRouterLoggedValue(entry)
|
|
15400
|
+
);
|
|
15401
|
+
}
|
|
15402
|
+
function getOpenRouterResolvedRequest(result, request) {
|
|
15403
|
+
if (isObject(result.resolvedRequest)) {
|
|
15404
|
+
return result.resolvedRequest;
|
|
15405
|
+
}
|
|
15406
|
+
return request;
|
|
15407
|
+
}
|
|
15408
|
+
function buildOpenRouterFollowupRequest(request, currentResponse, toolResults) {
|
|
15409
|
+
if (!request) {
|
|
15410
|
+
return void 0;
|
|
15411
|
+
}
|
|
15412
|
+
return {
|
|
15413
|
+
...request,
|
|
15414
|
+
input: buildNextOpenRouterCallModelInput(
|
|
15415
|
+
extractOpenRouterCallModelInput(request),
|
|
15416
|
+
isObject(currentResponse) ? currentResponse : {},
|
|
15417
|
+
toolResults
|
|
15418
|
+
),
|
|
15419
|
+
stream: false
|
|
15420
|
+
};
|
|
15421
|
+
}
|
|
15422
|
+
function wrapAsyncIterableWithSpan(args) {
|
|
15423
|
+
return {
|
|
15424
|
+
[Symbol.asyncIterator]() {
|
|
15425
|
+
const iterator = args.iteratorFactory();
|
|
15426
|
+
return {
|
|
15427
|
+
next(value) {
|
|
15428
|
+
return withCurrent(
|
|
15429
|
+
args.span,
|
|
15430
|
+
() => value === void 0 ? iterator.next() : iterator.next(value)
|
|
15431
|
+
).then(
|
|
15432
|
+
async (result) => {
|
|
15433
|
+
if (result.done) {
|
|
15434
|
+
await args.finalize();
|
|
15435
|
+
}
|
|
15436
|
+
return result;
|
|
15437
|
+
},
|
|
15438
|
+
(error) => {
|
|
15439
|
+
args.onError(error);
|
|
15440
|
+
throw error;
|
|
15441
|
+
}
|
|
15442
|
+
);
|
|
15443
|
+
},
|
|
15444
|
+
return(value) {
|
|
15445
|
+
if (typeof iterator.return !== "function") {
|
|
15446
|
+
return args.finalize().then(() => ({
|
|
15447
|
+
done: true,
|
|
15448
|
+
value
|
|
15449
|
+
}));
|
|
15450
|
+
}
|
|
15451
|
+
return withCurrent(args.span, () => iterator.return(value)).then(
|
|
15452
|
+
async (result) => {
|
|
15453
|
+
await args.finalize();
|
|
15454
|
+
return result;
|
|
15455
|
+
},
|
|
15456
|
+
(error) => {
|
|
15457
|
+
args.onError(error);
|
|
15458
|
+
throw error;
|
|
15459
|
+
}
|
|
15460
|
+
);
|
|
15461
|
+
},
|
|
15462
|
+
throw(error) {
|
|
15463
|
+
args.onError(error);
|
|
15464
|
+
if (typeof iterator.throw !== "function") {
|
|
15465
|
+
return Promise.reject(error);
|
|
15466
|
+
}
|
|
15467
|
+
return withCurrent(args.span, () => iterator.throw(error));
|
|
15468
|
+
},
|
|
15469
|
+
[Symbol.asyncIterator]() {
|
|
15470
|
+
return this;
|
|
15471
|
+
}
|
|
15472
|
+
};
|
|
15473
|
+
}
|
|
15474
|
+
};
|
|
15475
|
+
}
|
|
15476
|
+
function isAsyncIterable3(value) {
|
|
15477
|
+
return !!value && (typeof value === "object" || typeof value === "function") && Symbol.asyncIterator in value && typeof value[Symbol.asyncIterator] === "function";
|
|
15478
|
+
}
|
|
15479
|
+
function normalizeError(error) {
|
|
15480
|
+
return error instanceof Error ? error : new Error(String(error));
|
|
15481
|
+
}
|
|
15482
|
+
|
|
15483
|
+
// src/instrumentation/plugins/openrouter-channels.ts
|
|
15484
|
+
var openRouterChannels = defineChannels("@openrouter/sdk", {
|
|
15485
|
+
chatSend: channel({
|
|
15486
|
+
channelName: "chat.send",
|
|
15487
|
+
kind: "async"
|
|
15488
|
+
}),
|
|
15489
|
+
embeddingsGenerate: channel({
|
|
15490
|
+
channelName: "embeddings.generate",
|
|
15491
|
+
kind: "async"
|
|
15492
|
+
}),
|
|
15493
|
+
betaResponsesSend: channel({
|
|
15494
|
+
channelName: "beta.responses.send",
|
|
15495
|
+
kind: "async"
|
|
15496
|
+
}),
|
|
15497
|
+
callModel: channel({
|
|
15498
|
+
channelName: "callModel",
|
|
15499
|
+
kind: "sync-stream"
|
|
15500
|
+
}),
|
|
15501
|
+
callModelTurn: channel({
|
|
15502
|
+
channelName: "callModel.turn",
|
|
15503
|
+
kind: "async"
|
|
15504
|
+
}),
|
|
15505
|
+
toolExecute: channel({
|
|
15506
|
+
channelName: "tool.execute",
|
|
15507
|
+
kind: "async"
|
|
15508
|
+
})
|
|
15509
|
+
});
|
|
15510
|
+
|
|
15511
|
+
// src/instrumentation/plugins/openrouter-plugin.ts
|
|
15512
|
+
var OpenRouterPlugin = class extends BasePlugin {
|
|
15513
|
+
onEnable() {
|
|
15514
|
+
this.subscribeToOpenRouterChannels();
|
|
15515
|
+
}
|
|
15516
|
+
onDisable() {
|
|
15517
|
+
this.unsubscribers = unsubscribeAll(this.unsubscribers);
|
|
15518
|
+
}
|
|
15519
|
+
subscribeToOpenRouterChannels() {
|
|
15520
|
+
this.unsubscribers.push(
|
|
15521
|
+
traceStreamingChannel(openRouterChannels.chatSend, {
|
|
15522
|
+
name: "openrouter.chat.send",
|
|
15523
|
+
type: "llm" /* LLM */,
|
|
15524
|
+
extractInput: (args) => {
|
|
15525
|
+
const request = getOpenRouterRequestArg(args);
|
|
15526
|
+
const chatGenerationParams = isObject(request?.chatGenerationParams) ? request.chatGenerationParams : {};
|
|
15527
|
+
const httpReferer = request?.httpReferer;
|
|
15528
|
+
const xTitle = request?.xTitle;
|
|
15529
|
+
const { messages, ...metadata } = chatGenerationParams;
|
|
15530
|
+
return {
|
|
15531
|
+
input: messages,
|
|
15532
|
+
metadata: buildOpenRouterMetadata2(metadata, httpReferer, xTitle)
|
|
15533
|
+
};
|
|
15534
|
+
},
|
|
15535
|
+
extractOutput: (result) => {
|
|
15536
|
+
return isObject(result) ? result.choices : void 0;
|
|
15537
|
+
},
|
|
15538
|
+
extractMetrics: (result, startTime) => {
|
|
15539
|
+
const metrics = parseOpenRouterMetricsFromUsage2(result?.usage);
|
|
15540
|
+
if (startTime) {
|
|
15541
|
+
metrics.time_to_first_token = getCurrentUnixTimestamp() - startTime;
|
|
15542
|
+
}
|
|
15543
|
+
return metrics;
|
|
15544
|
+
},
|
|
15545
|
+
aggregateChunks: aggregateOpenRouterChatChunks
|
|
15546
|
+
})
|
|
15547
|
+
);
|
|
15548
|
+
this.unsubscribers.push(
|
|
15549
|
+
traceAsyncChannel(openRouterChannels.embeddingsGenerate, {
|
|
15550
|
+
name: "openrouter.embeddings.generate",
|
|
15551
|
+
type: "llm" /* LLM */,
|
|
15552
|
+
extractInput: (args) => {
|
|
15553
|
+
const request = getOpenRouterRequestArg(args);
|
|
15554
|
+
const requestBody = isObject(request?.requestBody) ? request.requestBody : {};
|
|
15555
|
+
const httpReferer = request?.httpReferer;
|
|
15556
|
+
const xTitle = request?.xTitle;
|
|
15557
|
+
const { input, ...metadata } = requestBody;
|
|
15558
|
+
return {
|
|
15559
|
+
input,
|
|
15560
|
+
metadata: buildOpenRouterEmbeddingMetadata(
|
|
15561
|
+
metadata,
|
|
15562
|
+
httpReferer,
|
|
15563
|
+
xTitle
|
|
15564
|
+
)
|
|
15565
|
+
};
|
|
15566
|
+
},
|
|
15567
|
+
extractOutput: (result) => {
|
|
15568
|
+
if (!isObject(result)) {
|
|
15569
|
+
return void 0;
|
|
14093
15570
|
}
|
|
14094
15571
|
const embedding = result.data?.[0]?.embedding;
|
|
14095
15572
|
return Array.isArray(embedding) ? { embedding_length: embedding.length } : void 0;
|
|
@@ -14098,10 +15575,10 @@ var OpenRouterPlugin = class extends BasePlugin {
|
|
|
14098
15575
|
if (!isObject(result)) {
|
|
14099
15576
|
return void 0;
|
|
14100
15577
|
}
|
|
14101
|
-
return
|
|
15578
|
+
return extractOpenRouterResponseMetadata2(result);
|
|
14102
15579
|
},
|
|
14103
15580
|
extractMetrics: (result) => {
|
|
14104
|
-
return isObject(result) ?
|
|
15581
|
+
return isObject(result) ? parseOpenRouterMetricsFromUsage2(result.usage) : {};
|
|
14105
15582
|
}
|
|
14106
15583
|
})
|
|
14107
15584
|
);
|
|
@@ -14117,13 +15594,13 @@ var OpenRouterPlugin = class extends BasePlugin {
|
|
|
14117
15594
|
const { input, ...metadata } = openResponsesRequest;
|
|
14118
15595
|
return {
|
|
14119
15596
|
input,
|
|
14120
|
-
metadata:
|
|
15597
|
+
metadata: buildOpenRouterMetadata2(metadata, httpReferer, xTitle)
|
|
14121
15598
|
};
|
|
14122
15599
|
},
|
|
14123
|
-
extractOutput: (result) =>
|
|
14124
|
-
extractMetadata: (result) =>
|
|
15600
|
+
extractOutput: (result) => extractOpenRouterResponseOutput2(result),
|
|
15601
|
+
extractMetadata: (result) => extractOpenRouterResponseMetadata2(result),
|
|
14125
15602
|
extractMetrics: (result, startTime) => {
|
|
14126
|
-
const metrics =
|
|
15603
|
+
const metrics = parseOpenRouterMetricsFromUsage2(result?.usage);
|
|
14127
15604
|
if (startTime) {
|
|
14128
15605
|
metrics.time_to_first_token = getCurrentUnixTimestamp() - startTime;
|
|
14129
15606
|
}
|
|
@@ -14137,15 +15614,15 @@ var OpenRouterPlugin = class extends BasePlugin {
|
|
|
14137
15614
|
name: "openrouter.callModel",
|
|
14138
15615
|
type: "llm" /* LLM */,
|
|
14139
15616
|
extractInput: (args) => {
|
|
14140
|
-
const request =
|
|
15617
|
+
const request = getOpenRouterCallModelRequestArg2(args);
|
|
14141
15618
|
return {
|
|
14142
|
-
input: request ?
|
|
14143
|
-
metadata: request ?
|
|
15619
|
+
input: request ? extractOpenRouterCallModelInput2(request) : void 0,
|
|
15620
|
+
metadata: request ? extractOpenRouterCallModelMetadata2(request) : { provider: "openrouter" }
|
|
14144
15621
|
};
|
|
14145
15622
|
},
|
|
14146
15623
|
patchResult: ({ endEvent, result, span }) => {
|
|
14147
|
-
return
|
|
14148
|
-
request:
|
|
15624
|
+
return patchOpenRouterCallModelResult2({
|
|
15625
|
+
request: getOpenRouterCallModelRequestArg2(endEvent.arguments),
|
|
14149
15626
|
result,
|
|
14150
15627
|
span
|
|
14151
15628
|
});
|
|
@@ -14157,13 +15634,13 @@ var OpenRouterPlugin = class extends BasePlugin {
|
|
|
14157
15634
|
name: "openrouter.beta.responses.send",
|
|
14158
15635
|
type: "llm" /* LLM */,
|
|
14159
15636
|
extractInput: (args, event) => {
|
|
14160
|
-
const request =
|
|
14161
|
-
const metadata = request ?
|
|
15637
|
+
const request = getOpenRouterCallModelRequestArg2(args);
|
|
15638
|
+
const metadata = request ? extractOpenRouterCallModelMetadata2(request) : { provider: "openrouter" };
|
|
14162
15639
|
if (isObject(metadata) && "tools" in metadata) {
|
|
14163
15640
|
delete metadata.tools;
|
|
14164
15641
|
}
|
|
14165
15642
|
return {
|
|
14166
|
-
input: request ?
|
|
15643
|
+
input: request ? extractOpenRouterCallModelInput2(request) : void 0,
|
|
14167
15644
|
metadata: {
|
|
14168
15645
|
...metadata,
|
|
14169
15646
|
step: event.step,
|
|
@@ -14171,7 +15648,7 @@ var OpenRouterPlugin = class extends BasePlugin {
|
|
|
14171
15648
|
}
|
|
14172
15649
|
};
|
|
14173
15650
|
},
|
|
14174
|
-
extractOutput: (result) =>
|
|
15651
|
+
extractOutput: (result) => extractOpenRouterResponseOutput2(result),
|
|
14175
15652
|
extractMetadata: (result, event) => {
|
|
14176
15653
|
if (!isObject(result)) {
|
|
14177
15654
|
return {
|
|
@@ -14180,12 +15657,12 @@ var OpenRouterPlugin = class extends BasePlugin {
|
|
|
14180
15657
|
};
|
|
14181
15658
|
}
|
|
14182
15659
|
return {
|
|
14183
|
-
...
|
|
15660
|
+
...extractOpenRouterResponseMetadata2(result) || {},
|
|
14184
15661
|
...event?.step !== void 0 ? { step: event.step } : {},
|
|
14185
15662
|
...event?.stepType ? { step_type: event.stepType } : {}
|
|
14186
15663
|
};
|
|
14187
15664
|
},
|
|
14188
|
-
extractMetrics: (result) => isObject(result) ?
|
|
15665
|
+
extractMetrics: (result) => isObject(result) ? parseOpenRouterMetricsFromUsage2(result.usage) : {}
|
|
14189
15666
|
})
|
|
14190
15667
|
);
|
|
14191
15668
|
this.unsubscribers.push(
|
|
@@ -14211,11 +15688,11 @@ var OpenRouterPlugin = class extends BasePlugin {
|
|
|
14211
15688
|
const callModelChannel = openRouterChannels.callModel.tracingChannel();
|
|
14212
15689
|
const callModelHandlers = {
|
|
14213
15690
|
start: (event) => {
|
|
14214
|
-
const request =
|
|
15691
|
+
const request = getOpenRouterCallModelRequestArg2(event.arguments);
|
|
14215
15692
|
if (!request) {
|
|
14216
15693
|
return;
|
|
14217
15694
|
}
|
|
14218
|
-
|
|
15695
|
+
patchOpenRouterCallModelRequestTools2(request);
|
|
14219
15696
|
}
|
|
14220
15697
|
};
|
|
14221
15698
|
callModelChannel.subscribe(callModelHandlers);
|
|
@@ -14224,20 +15701,20 @@ var OpenRouterPlugin = class extends BasePlugin {
|
|
|
14224
15701
|
});
|
|
14225
15702
|
}
|
|
14226
15703
|
};
|
|
14227
|
-
function
|
|
15704
|
+
function normalizeArgs2(args) {
|
|
14228
15705
|
if (Array.isArray(args)) {
|
|
14229
15706
|
return args;
|
|
14230
15707
|
}
|
|
14231
|
-
if (
|
|
15708
|
+
if (isArrayLike2(args)) {
|
|
14232
15709
|
return Array.from(args);
|
|
14233
15710
|
}
|
|
14234
15711
|
return [args];
|
|
14235
15712
|
}
|
|
14236
|
-
function
|
|
15713
|
+
function isArrayLike2(value) {
|
|
14237
15714
|
return isObject(value) && "length" in value && typeof value.length === "number" && Number.isInteger(value.length) && value.length >= 0;
|
|
14238
15715
|
}
|
|
14239
15716
|
function getOpenRouterRequestArg(args) {
|
|
14240
|
-
const normalizedArgs =
|
|
15717
|
+
const normalizedArgs = normalizeArgs2(args);
|
|
14241
15718
|
const keyedCandidate = normalizedArgs.find(
|
|
14242
15719
|
(arg) => isObject(arg) && ("chatGenerationParams" in arg || "requestBody" in arg || "openResponsesRequest" in arg)
|
|
14243
15720
|
);
|
|
@@ -14247,11 +15724,11 @@ function getOpenRouterRequestArg(args) {
|
|
|
14247
15724
|
const firstObjectArg = normalizedArgs.find((arg) => isObject(arg));
|
|
14248
15725
|
return isObject(firstObjectArg) ? firstObjectArg : void 0;
|
|
14249
15726
|
}
|
|
14250
|
-
function
|
|
14251
|
-
const firstObjectArg =
|
|
15727
|
+
function getOpenRouterCallModelRequestArg2(args) {
|
|
15728
|
+
const firstObjectArg = normalizeArgs2(args).find((arg) => isObject(arg));
|
|
14252
15729
|
return isObject(firstObjectArg) ? firstObjectArg : void 0;
|
|
14253
15730
|
}
|
|
14254
|
-
var
|
|
15731
|
+
var TOKEN_NAME_MAP3 = {
|
|
14255
15732
|
promptTokens: "prompt_tokens",
|
|
14256
15733
|
inputTokens: "prompt_tokens",
|
|
14257
15734
|
completionTokens: "completion_tokens",
|
|
@@ -14263,7 +15740,7 @@ var TOKEN_NAME_MAP2 = {
|
|
|
14263
15740
|
output_tokens: "completion_tokens",
|
|
14264
15741
|
total_tokens: "tokens"
|
|
14265
15742
|
};
|
|
14266
|
-
var
|
|
15743
|
+
var TOKEN_DETAIL_PREFIX_MAP2 = {
|
|
14267
15744
|
promptTokensDetails: "prompt",
|
|
14268
15745
|
inputTokensDetails: "prompt",
|
|
14269
15746
|
completionTokensDetails: "completion",
|
|
@@ -14275,23 +15752,23 @@ var TOKEN_DETAIL_PREFIX_MAP = {
|
|
|
14275
15752
|
output_tokens_details: "completion",
|
|
14276
15753
|
cost_details: "cost"
|
|
14277
15754
|
};
|
|
14278
|
-
function
|
|
15755
|
+
function camelToSnake2(value) {
|
|
14279
15756
|
return value.replace(/[A-Z]/g, (match) => `_${match.toLowerCase()}`);
|
|
14280
15757
|
}
|
|
14281
|
-
function
|
|
15758
|
+
function parseOpenRouterMetricsFromUsage2(usage) {
|
|
14282
15759
|
if (!isObject(usage)) {
|
|
14283
15760
|
return {};
|
|
14284
15761
|
}
|
|
14285
15762
|
const metrics = {};
|
|
14286
15763
|
for (const [name, value] of Object.entries(usage)) {
|
|
14287
15764
|
if (typeof value === "number") {
|
|
14288
|
-
metrics[
|
|
15765
|
+
metrics[TOKEN_NAME_MAP3[name] || camelToSnake2(name)] = value;
|
|
14289
15766
|
continue;
|
|
14290
15767
|
}
|
|
14291
15768
|
if (!isObject(value)) {
|
|
14292
15769
|
continue;
|
|
14293
15770
|
}
|
|
14294
|
-
const prefix =
|
|
15771
|
+
const prefix = TOKEN_DETAIL_PREFIX_MAP2[name];
|
|
14295
15772
|
if (!prefix) {
|
|
14296
15773
|
continue;
|
|
14297
15774
|
}
|
|
@@ -14299,12 +15776,12 @@ function parseOpenRouterMetricsFromUsage(usage) {
|
|
|
14299
15776
|
if (typeof nestedValue !== "number") {
|
|
14300
15777
|
continue;
|
|
14301
15778
|
}
|
|
14302
|
-
metrics[`${prefix}_${
|
|
15779
|
+
metrics[`${prefix}_${camelToSnake2(nestedName)}`] = nestedValue;
|
|
14303
15780
|
}
|
|
14304
15781
|
}
|
|
14305
15782
|
return metrics;
|
|
14306
15783
|
}
|
|
14307
|
-
function
|
|
15784
|
+
function extractOpenRouterUsageMetadata2(usage) {
|
|
14308
15785
|
if (!isObject(usage)) {
|
|
14309
15786
|
return void 0;
|
|
14310
15787
|
}
|
|
@@ -14316,13 +15793,13 @@ function extractOpenRouterUsageMetadata(usage) {
|
|
|
14316
15793
|
}
|
|
14317
15794
|
return Object.keys(metadata).length > 0 ? metadata : void 0;
|
|
14318
15795
|
}
|
|
14319
|
-
var
|
|
15796
|
+
var OMITTED_OPENROUTER_KEYS2 = /* @__PURE__ */ new Set([
|
|
14320
15797
|
"execute",
|
|
14321
15798
|
"render",
|
|
14322
15799
|
"nextTurnParams",
|
|
14323
15800
|
"requireApproval"
|
|
14324
15801
|
]);
|
|
14325
|
-
function
|
|
15802
|
+
function parseOpenRouterModelString2(model) {
|
|
14326
15803
|
if (typeof model !== "string") {
|
|
14327
15804
|
return { model };
|
|
14328
15805
|
}
|
|
@@ -14335,10 +15812,10 @@ function parseOpenRouterModelString(model) {
|
|
|
14335
15812
|
}
|
|
14336
15813
|
return { model };
|
|
14337
15814
|
}
|
|
14338
|
-
function
|
|
15815
|
+
function isZodSchema4(value) {
|
|
14339
15816
|
return value != null && typeof value === "object" && "_def" in value && typeof value._def === "object";
|
|
14340
15817
|
}
|
|
14341
|
-
function
|
|
15818
|
+
function serializeZodSchema4(schema) {
|
|
14342
15819
|
try {
|
|
14343
15820
|
return zodToJsonSchema(schema);
|
|
14344
15821
|
} catch {
|
|
@@ -14348,60 +15825,60 @@ function serializeZodSchema3(schema) {
|
|
|
14348
15825
|
};
|
|
14349
15826
|
}
|
|
14350
15827
|
}
|
|
14351
|
-
function
|
|
15828
|
+
function serializeOpenRouterTool2(tool) {
|
|
14352
15829
|
if (!isObject(tool)) {
|
|
14353
15830
|
return tool;
|
|
14354
15831
|
}
|
|
14355
15832
|
const serialized = {};
|
|
14356
15833
|
for (const [key, value] of Object.entries(tool)) {
|
|
14357
|
-
if (
|
|
15834
|
+
if (OMITTED_OPENROUTER_KEYS2.has(key)) {
|
|
14358
15835
|
continue;
|
|
14359
15836
|
}
|
|
14360
15837
|
if (key === "function" && isObject(value)) {
|
|
14361
|
-
serialized.function =
|
|
15838
|
+
serialized.function = sanitizeOpenRouterLoggedValue2(value);
|
|
14362
15839
|
continue;
|
|
14363
15840
|
}
|
|
14364
|
-
serialized[key] =
|
|
15841
|
+
serialized[key] = sanitizeOpenRouterLoggedValue2(value);
|
|
14365
15842
|
}
|
|
14366
15843
|
return serialized;
|
|
14367
15844
|
}
|
|
14368
|
-
function
|
|
15845
|
+
function serializeOpenRouterToolsForLogging2(tools) {
|
|
14369
15846
|
if (!Array.isArray(tools)) {
|
|
14370
15847
|
return void 0;
|
|
14371
15848
|
}
|
|
14372
|
-
return tools.map((tool) =>
|
|
15849
|
+
return tools.map((tool) => serializeOpenRouterTool2(tool));
|
|
14373
15850
|
}
|
|
14374
|
-
function
|
|
14375
|
-
if (
|
|
14376
|
-
return
|
|
15851
|
+
function sanitizeOpenRouterLoggedValue2(value) {
|
|
15852
|
+
if (isZodSchema4(value)) {
|
|
15853
|
+
return serializeZodSchema4(value);
|
|
14377
15854
|
}
|
|
14378
15855
|
if (typeof value === "function") {
|
|
14379
15856
|
return "[Function]";
|
|
14380
15857
|
}
|
|
14381
15858
|
if (Array.isArray(value)) {
|
|
14382
|
-
return value.map((entry) =>
|
|
15859
|
+
return value.map((entry) => sanitizeOpenRouterLoggedValue2(entry));
|
|
14383
15860
|
}
|
|
14384
15861
|
if (!isObject(value)) {
|
|
14385
15862
|
return value;
|
|
14386
15863
|
}
|
|
14387
15864
|
const sanitized = {};
|
|
14388
15865
|
for (const [key, entry] of Object.entries(value)) {
|
|
14389
|
-
if (
|
|
15866
|
+
if (OMITTED_OPENROUTER_KEYS2.has(key)) {
|
|
14390
15867
|
continue;
|
|
14391
15868
|
}
|
|
14392
15869
|
if (key === "tools" && Array.isArray(entry)) {
|
|
14393
|
-
sanitized.tools =
|
|
15870
|
+
sanitized.tools = serializeOpenRouterToolsForLogging2(entry);
|
|
14394
15871
|
continue;
|
|
14395
15872
|
}
|
|
14396
|
-
sanitized[key] =
|
|
15873
|
+
sanitized[key] = sanitizeOpenRouterLoggedValue2(entry);
|
|
14397
15874
|
}
|
|
14398
15875
|
return sanitized;
|
|
14399
15876
|
}
|
|
14400
|
-
function
|
|
14401
|
-
const sanitized =
|
|
15877
|
+
function buildOpenRouterMetadata2(metadata, httpReferer, xTitle) {
|
|
15878
|
+
const sanitized = sanitizeOpenRouterLoggedValue2(metadata);
|
|
14402
15879
|
const metadataRecord = isObject(sanitized) ? sanitized : {};
|
|
14403
15880
|
const { model, provider: providerRouting, ...rest } = metadataRecord;
|
|
14404
|
-
const normalizedModel =
|
|
15881
|
+
const normalizedModel = parseOpenRouterModelString2(model);
|
|
14405
15882
|
return {
|
|
14406
15883
|
...rest,
|
|
14407
15884
|
...normalizedModel.model !== void 0 ? { model: normalizedModel.model } : {},
|
|
@@ -14412,33 +15889,33 @@ function buildOpenRouterMetadata(metadata, httpReferer, xTitle) {
|
|
|
14412
15889
|
};
|
|
14413
15890
|
}
|
|
14414
15891
|
function buildOpenRouterEmbeddingMetadata(metadata, httpReferer, xTitle) {
|
|
14415
|
-
const normalized =
|
|
15892
|
+
const normalized = buildOpenRouterMetadata2(metadata, httpReferer, xTitle);
|
|
14416
15893
|
return typeof normalized.model === "string" ? {
|
|
14417
15894
|
...normalized,
|
|
14418
15895
|
embedding_model: normalized.model
|
|
14419
15896
|
} : normalized;
|
|
14420
15897
|
}
|
|
14421
|
-
function
|
|
14422
|
-
return isObject(request) && "input" in request ?
|
|
15898
|
+
function extractOpenRouterCallModelInput2(request) {
|
|
15899
|
+
return isObject(request) && "input" in request ? sanitizeOpenRouterLoggedValue2(request.input) : void 0;
|
|
14423
15900
|
}
|
|
14424
|
-
function
|
|
15901
|
+
function extractOpenRouterCallModelMetadata2(request) {
|
|
14425
15902
|
if (!isObject(request)) {
|
|
14426
15903
|
return { provider: "openrouter" };
|
|
14427
15904
|
}
|
|
14428
15905
|
const { input: _input, ...metadata } = request;
|
|
14429
|
-
return
|
|
15906
|
+
return buildOpenRouterMetadata2(metadata, void 0, void 0);
|
|
14430
15907
|
}
|
|
14431
|
-
function
|
|
15908
|
+
function extractOpenRouterResponseMetadata2(result) {
|
|
14432
15909
|
if (!isObject(result)) {
|
|
14433
15910
|
return void 0;
|
|
14434
15911
|
}
|
|
14435
15912
|
const { output: _output, data: _data, usage, ...metadata } = result;
|
|
14436
|
-
const sanitized =
|
|
15913
|
+
const sanitized = sanitizeOpenRouterLoggedValue2(metadata);
|
|
14437
15914
|
const metadataRecord = isObject(sanitized) ? sanitized : {};
|
|
14438
15915
|
const { model, provider, ...rest } = metadataRecord;
|
|
14439
|
-
const normalizedModel =
|
|
15916
|
+
const normalizedModel = parseOpenRouterModelString2(model);
|
|
14440
15917
|
const normalizedProvider = (typeof provider === "string" ? provider : void 0) || normalizedModel.provider;
|
|
14441
|
-
const usageMetadata =
|
|
15918
|
+
const usageMetadata = extractOpenRouterUsageMetadata2(usage);
|
|
14442
15919
|
const combined = {
|
|
14443
15920
|
...rest,
|
|
14444
15921
|
...normalizedModel.model !== void 0 ? { model: normalizedModel.model } : {},
|
|
@@ -14447,22 +15924,22 @@ function extractOpenRouterResponseMetadata(result) {
|
|
|
14447
15924
|
};
|
|
14448
15925
|
return Object.keys(combined).length > 0 ? combined : void 0;
|
|
14449
15926
|
}
|
|
14450
|
-
function
|
|
15927
|
+
function extractOpenRouterResponseOutput2(response, fallbackOutput) {
|
|
14451
15928
|
if (isObject(response) && "output" in response && response.output !== void 0) {
|
|
14452
|
-
return
|
|
15929
|
+
return sanitizeOpenRouterLoggedValue2(response.output);
|
|
14453
15930
|
}
|
|
14454
15931
|
if (fallbackOutput !== void 0) {
|
|
14455
|
-
return
|
|
15932
|
+
return sanitizeOpenRouterLoggedValue2(fallbackOutput);
|
|
14456
15933
|
}
|
|
14457
15934
|
return void 0;
|
|
14458
15935
|
}
|
|
14459
|
-
var
|
|
14460
|
-
function
|
|
15936
|
+
var OPENROUTER_WRAPPED_TOOL2 = Symbol("braintrust.openrouter.wrappedTool");
|
|
15937
|
+
function patchOpenRouterCallModelRequestTools2(request) {
|
|
14461
15938
|
if (!Array.isArray(request.tools) || request.tools.length === 0) {
|
|
14462
15939
|
return void 0;
|
|
14463
15940
|
}
|
|
14464
15941
|
const originalTools = request.tools;
|
|
14465
|
-
const wrappedTools = originalTools.map((tool) =>
|
|
15942
|
+
const wrappedTools = originalTools.map((tool) => wrapOpenRouterTool2(tool));
|
|
14466
15943
|
const didPatch = wrappedTools.some(
|
|
14467
15944
|
(tool, index) => tool !== originalTools[index]
|
|
14468
15945
|
);
|
|
@@ -14474,8 +15951,8 @@ function patchOpenRouterCallModelRequestTools(request) {
|
|
|
14474
15951
|
request.tools = originalTools;
|
|
14475
15952
|
};
|
|
14476
15953
|
}
|
|
14477
|
-
function
|
|
14478
|
-
if (
|
|
15954
|
+
function wrapOpenRouterTool2(tool) {
|
|
15955
|
+
if (isWrappedTool2(tool) || !tool.function || typeof tool.function !== "object" || typeof tool.function.execute !== "function") {
|
|
14479
15956
|
return tool;
|
|
14480
15957
|
}
|
|
14481
15958
|
const toolName = tool.function.name || "tool";
|
|
@@ -14485,26 +15962,26 @@ function wrapOpenRouterTool(tool) {
|
|
|
14485
15962
|
function: {
|
|
14486
15963
|
...tool.function,
|
|
14487
15964
|
execute(...args) {
|
|
14488
|
-
return
|
|
15965
|
+
return traceToolExecution2({
|
|
14489
15966
|
args,
|
|
14490
15967
|
execute: () => Reflect.apply(originalExecute, this, args),
|
|
14491
|
-
toolCallId:
|
|
15968
|
+
toolCallId: getToolCallId2(args[1]),
|
|
14492
15969
|
toolName
|
|
14493
15970
|
});
|
|
14494
15971
|
}
|
|
14495
15972
|
}
|
|
14496
15973
|
};
|
|
14497
|
-
Object.defineProperty(wrappedTool,
|
|
15974
|
+
Object.defineProperty(wrappedTool, OPENROUTER_WRAPPED_TOOL2, {
|
|
14498
15975
|
value: true,
|
|
14499
15976
|
enumerable: false,
|
|
14500
15977
|
configurable: false
|
|
14501
15978
|
});
|
|
14502
15979
|
return wrappedTool;
|
|
14503
15980
|
}
|
|
14504
|
-
function
|
|
14505
|
-
return Boolean(tool[
|
|
15981
|
+
function isWrappedTool2(tool) {
|
|
15982
|
+
return Boolean(tool[OPENROUTER_WRAPPED_TOOL2]);
|
|
14506
15983
|
}
|
|
14507
|
-
function
|
|
15984
|
+
function traceToolExecution2(args) {
|
|
14508
15985
|
const tracingChannel2 = openRouterChannels.toolExecute.tracingChannel();
|
|
14509
15986
|
const input = args.args.length > 0 ? args.args[0] : void 0;
|
|
14510
15987
|
const event = {
|
|
@@ -14518,15 +15995,15 @@ function traceToolExecution(args) {
|
|
|
14518
15995
|
tracingChannel2.start.publish(event);
|
|
14519
15996
|
try {
|
|
14520
15997
|
const result = args.execute();
|
|
14521
|
-
return
|
|
15998
|
+
return publishToolResult2(tracingChannel2, event, result);
|
|
14522
15999
|
} catch (error) {
|
|
14523
|
-
event.error =
|
|
16000
|
+
event.error = normalizeError2(error);
|
|
14524
16001
|
tracingChannel2.error.publish(event);
|
|
14525
16002
|
throw error;
|
|
14526
16003
|
}
|
|
14527
16004
|
}
|
|
14528
|
-
function
|
|
14529
|
-
if (
|
|
16005
|
+
function publishToolResult2(tracingChannel2, event, result) {
|
|
16006
|
+
if (isPromiseLike4(result)) {
|
|
14530
16007
|
return result.then(
|
|
14531
16008
|
(resolved) => {
|
|
14532
16009
|
event.result = resolved;
|
|
@@ -14534,7 +16011,7 @@ function publishToolResult(tracingChannel2, event, result) {
|
|
|
14534
16011
|
return resolved;
|
|
14535
16012
|
},
|
|
14536
16013
|
(error) => {
|
|
14537
|
-
event.error =
|
|
16014
|
+
event.error = normalizeError2(error);
|
|
14538
16015
|
tracingChannel2.error.publish(event);
|
|
14539
16016
|
throw error;
|
|
14540
16017
|
}
|
|
@@ -14544,11 +16021,11 @@ function publishToolResult(tracingChannel2, event, result) {
|
|
|
14544
16021
|
tracingChannel2.asyncEnd.publish(event);
|
|
14545
16022
|
return result;
|
|
14546
16023
|
}
|
|
14547
|
-
function
|
|
16024
|
+
function getToolCallId2(context) {
|
|
14548
16025
|
const toolContext = context;
|
|
14549
16026
|
return typeof toolContext?.toolCall?.id === "string" ? toolContext.toolCall.id : void 0;
|
|
14550
16027
|
}
|
|
14551
|
-
function
|
|
16028
|
+
function isPromiseLike4(value) {
|
|
14552
16029
|
return !!value && (typeof value === "object" || typeof value === "function") && "then" in value && typeof value.then === "function";
|
|
14553
16030
|
}
|
|
14554
16031
|
function aggregateOpenRouterChatChunks(chunks) {
|
|
@@ -14560,7 +16037,7 @@ function aggregateOpenRouterChatChunks(chunks) {
|
|
|
14560
16037
|
for (const chunk of chunks) {
|
|
14561
16038
|
metrics = {
|
|
14562
16039
|
...metrics,
|
|
14563
|
-
...
|
|
16040
|
+
...parseOpenRouterMetricsFromUsage2(chunk?.usage)
|
|
14564
16041
|
};
|
|
14565
16042
|
const choice = chunk?.choices?.[0];
|
|
14566
16043
|
const delta = choice?.delta;
|
|
@@ -14654,15 +16131,15 @@ function aggregateOpenRouterResponseStreamEvents(chunks) {
|
|
|
14654
16131
|
};
|
|
14655
16132
|
}
|
|
14656
16133
|
return {
|
|
14657
|
-
output:
|
|
14658
|
-
metrics:
|
|
14659
|
-
...
|
|
16134
|
+
output: extractOpenRouterResponseOutput2(finalResponse),
|
|
16135
|
+
metrics: parseOpenRouterMetricsFromUsage2(finalResponse.usage),
|
|
16136
|
+
...extractOpenRouterResponseMetadata2(finalResponse) ? { metadata: extractOpenRouterResponseMetadata2(finalResponse) } : {}
|
|
14660
16137
|
};
|
|
14661
16138
|
}
|
|
14662
|
-
var
|
|
16139
|
+
var OPENROUTER_WRAPPED_CALL_MODEL_RESULT2 = Symbol(
|
|
14663
16140
|
"braintrust.openrouter.wrappedCallModelResult"
|
|
14664
16141
|
);
|
|
14665
|
-
var
|
|
16142
|
+
var OPENROUTER_CALL_MODEL_STREAM_METHODS2 = [
|
|
14666
16143
|
"getFullResponsesStream",
|
|
14667
16144
|
"getItemsStream",
|
|
14668
16145
|
"getNewMessagesStream",
|
|
@@ -14671,26 +16148,26 @@ var OPENROUTER_CALL_MODEL_STREAM_METHODS = [
|
|
|
14671
16148
|
"getToolCallsStream",
|
|
14672
16149
|
"getToolStream"
|
|
14673
16150
|
];
|
|
14674
|
-
var
|
|
16151
|
+
var OPENROUTER_CALL_MODEL_CONTEXT_METHODS2 = [
|
|
14675
16152
|
"cancel",
|
|
14676
16153
|
"getPendingToolCalls",
|
|
14677
16154
|
"getState",
|
|
14678
16155
|
"getToolCalls",
|
|
14679
16156
|
"requiresApproval"
|
|
14680
16157
|
];
|
|
14681
|
-
function
|
|
16158
|
+
function patchOpenRouterCallModelResult2(args) {
|
|
14682
16159
|
const { request, result, span } = args;
|
|
14683
|
-
if (!isObject(result) ||
|
|
16160
|
+
if (!isObject(result) || isWrappedCallModelResult2(result)) {
|
|
14684
16161
|
return false;
|
|
14685
16162
|
}
|
|
14686
16163
|
const resultLike = result;
|
|
14687
|
-
const hasInstrumentableMethod = typeof resultLike.getResponse === "function" || typeof resultLike.getText === "function" ||
|
|
16164
|
+
const hasInstrumentableMethod = typeof resultLike.getResponse === "function" || typeof resultLike.getText === "function" || OPENROUTER_CALL_MODEL_STREAM_METHODS2.some(
|
|
14688
16165
|
(methodName) => typeof resultLike[methodName] === "function"
|
|
14689
16166
|
);
|
|
14690
16167
|
if (!hasInstrumentableMethod) {
|
|
14691
16168
|
return false;
|
|
14692
16169
|
}
|
|
14693
|
-
Object.defineProperty(resultLike,
|
|
16170
|
+
Object.defineProperty(resultLike, OPENROUTER_WRAPPED_CALL_MODEL_RESULT2, {
|
|
14694
16171
|
value: true,
|
|
14695
16172
|
enumerable: false,
|
|
14696
16173
|
configurable: false
|
|
@@ -14705,20 +16182,20 @@ function patchOpenRouterCallModelResult(args) {
|
|
|
14705
16182
|
return;
|
|
14706
16183
|
}
|
|
14707
16184
|
ended = true;
|
|
14708
|
-
const finalResponse =
|
|
16185
|
+
const finalResponse = getFinalOpenRouterCallModelResponse2(
|
|
14709
16186
|
resultLike,
|
|
14710
16187
|
response
|
|
14711
16188
|
);
|
|
14712
16189
|
if (finalResponse) {
|
|
14713
|
-
const rounds =
|
|
14714
|
-
const metadata =
|
|
16190
|
+
const rounds = getOpenRouterCallModelRounds2(resultLike);
|
|
16191
|
+
const metadata = extractOpenRouterCallModelResultMetadata2(
|
|
14715
16192
|
finalResponse,
|
|
14716
16193
|
rounds.length + 1
|
|
14717
16194
|
);
|
|
14718
16195
|
span.log({
|
|
14719
|
-
output:
|
|
16196
|
+
output: extractOpenRouterResponseOutput2(finalResponse, fallbackOutput),
|
|
14720
16197
|
...metadata ? { metadata } : {},
|
|
14721
|
-
metrics:
|
|
16198
|
+
metrics: aggregateOpenRouterCallModelMetrics2(rounds, finalResponse)
|
|
14722
16199
|
});
|
|
14723
16200
|
span.end();
|
|
14724
16201
|
return;
|
|
@@ -14736,7 +16213,7 @@ function patchOpenRouterCallModelResult(args) {
|
|
|
14736
16213
|
}
|
|
14737
16214
|
ended = true;
|
|
14738
16215
|
span.log({
|
|
14739
|
-
error:
|
|
16216
|
+
error: normalizeError2(error).message
|
|
14740
16217
|
});
|
|
14741
16218
|
span.end();
|
|
14742
16219
|
};
|
|
@@ -14780,7 +16257,7 @@ function patchOpenRouterCallModelResult(args) {
|
|
|
14780
16257
|
});
|
|
14781
16258
|
};
|
|
14782
16259
|
}
|
|
14783
|
-
for (const methodName of
|
|
16260
|
+
for (const methodName of OPENROUTER_CALL_MODEL_CONTEXT_METHODS2) {
|
|
14784
16261
|
if (typeof resultLike[methodName] !== "function") {
|
|
14785
16262
|
continue;
|
|
14786
16263
|
}
|
|
@@ -14791,7 +16268,7 @@ function patchOpenRouterCallModelResult(args) {
|
|
|
14791
16268
|
});
|
|
14792
16269
|
};
|
|
14793
16270
|
}
|
|
14794
|
-
for (const methodName of
|
|
16271
|
+
for (const methodName of OPENROUTER_CALL_MODEL_STREAM_METHODS2) {
|
|
14795
16272
|
if (typeof resultLike[methodName] !== "function") {
|
|
14796
16273
|
continue;
|
|
14797
16274
|
}
|
|
@@ -14801,10 +16278,10 @@ function patchOpenRouterCallModelResult(args) {
|
|
|
14801
16278
|
span,
|
|
14802
16279
|
() => originalMethod.apply(resultLike, args2)
|
|
14803
16280
|
);
|
|
14804
|
-
if (!
|
|
16281
|
+
if (!isAsyncIterable4(stream)) {
|
|
14805
16282
|
return stream;
|
|
14806
16283
|
}
|
|
14807
|
-
return
|
|
16284
|
+
return wrapAsyncIterableWithSpan2({
|
|
14808
16285
|
finalize: finalizeFromResponse,
|
|
14809
16286
|
iteratorFactory: () => stream[Symbol.asyncIterator](),
|
|
14810
16287
|
onError: endSpanWithError,
|
|
@@ -14823,14 +16300,14 @@ function patchOpenRouterCallModelResult(args) {
|
|
|
14823
16300
|
initialTurnTraced = true;
|
|
14824
16301
|
const step = tracedTurnCount + 1;
|
|
14825
16302
|
const stepType = tracedTurnCount === 0 ? "initial" : "continue";
|
|
14826
|
-
const response = await
|
|
16303
|
+
const response = await traceOpenRouterCallModelTurn2({
|
|
14827
16304
|
fn: async () => {
|
|
14828
16305
|
const nextResponse = await originalGetInitialResponse(...args2);
|
|
14829
16306
|
tracedTurnCount++;
|
|
14830
16307
|
return nextResponse;
|
|
14831
16308
|
},
|
|
14832
16309
|
parentSpan: span,
|
|
14833
|
-
request:
|
|
16310
|
+
request: getOpenRouterResolvedRequest2(resultLike, request),
|
|
14834
16311
|
step,
|
|
14835
16312
|
stepType
|
|
14836
16313
|
});
|
|
@@ -14842,15 +16319,15 @@ function patchOpenRouterCallModelResult(args) {
|
|
|
14842
16319
|
const currentResponse = args2[0];
|
|
14843
16320
|
const toolResults = Array.isArray(args2[1]) ? args2[1] : [];
|
|
14844
16321
|
const step = tracedTurnCount + 1;
|
|
14845
|
-
const response = await
|
|
16322
|
+
const response = await traceOpenRouterCallModelTurn2({
|
|
14846
16323
|
fn: async () => {
|
|
14847
16324
|
const nextResponse = await originalMakeFollowupRequest(...args2);
|
|
14848
16325
|
tracedTurnCount++;
|
|
14849
16326
|
return nextResponse;
|
|
14850
16327
|
},
|
|
14851
16328
|
parentSpan: span,
|
|
14852
|
-
request:
|
|
14853
|
-
|
|
16329
|
+
request: buildOpenRouterFollowupRequest2(
|
|
16330
|
+
getOpenRouterResolvedRequest2(resultLike, request),
|
|
14854
16331
|
currentResponse,
|
|
14855
16332
|
toolResults
|
|
14856
16333
|
),
|
|
@@ -14862,7 +16339,7 @@ function patchOpenRouterCallModelResult(args) {
|
|
|
14862
16339
|
}
|
|
14863
16340
|
return true;
|
|
14864
16341
|
}
|
|
14865
|
-
async function
|
|
16342
|
+
async function traceOpenRouterCallModelTurn2(args) {
|
|
14866
16343
|
const context = {
|
|
14867
16344
|
arguments: [args.request],
|
|
14868
16345
|
step: args.step,
|
|
@@ -14873,25 +16350,25 @@ async function traceOpenRouterCallModelTurn(args) {
|
|
|
14873
16350
|
() => openRouterChannels.callModelTurn.tracePromise(args.fn, context)
|
|
14874
16351
|
);
|
|
14875
16352
|
}
|
|
14876
|
-
function
|
|
16353
|
+
function isWrappedCallModelResult2(value) {
|
|
14877
16354
|
return Boolean(
|
|
14878
|
-
isObject(value) && value[
|
|
16355
|
+
isObject(value) && value[OPENROUTER_WRAPPED_CALL_MODEL_RESULT2]
|
|
14879
16356
|
);
|
|
14880
16357
|
}
|
|
14881
|
-
function
|
|
16358
|
+
function extractOpenRouterCallModelResultMetadata2(response, turnCount) {
|
|
14882
16359
|
const combined = {
|
|
14883
|
-
...
|
|
16360
|
+
...extractOpenRouterResponseMetadata2(response) || {},
|
|
14884
16361
|
...turnCount !== void 0 ? { turn_count: turnCount } : {}
|
|
14885
16362
|
};
|
|
14886
16363
|
return Object.keys(combined).length > 0 ? combined : void 0;
|
|
14887
16364
|
}
|
|
14888
|
-
function
|
|
16365
|
+
function getFinalOpenRouterCallModelResponse2(result, response) {
|
|
14889
16366
|
if (isObject(response)) {
|
|
14890
16367
|
return response;
|
|
14891
16368
|
}
|
|
14892
16369
|
return isObject(result.finalResponse) ? result.finalResponse : void 0;
|
|
14893
16370
|
}
|
|
14894
|
-
function
|
|
16371
|
+
function getOpenRouterCallModelRounds2(result) {
|
|
14895
16372
|
if (!Array.isArray(result.allToolExecutionRounds)) {
|
|
14896
16373
|
return [];
|
|
14897
16374
|
}
|
|
@@ -14901,48 +16378,48 @@ function getOpenRouterCallModelRounds(result) {
|
|
|
14901
16378
|
toolResults: Array.isArray(round.toolResults) ? round.toolResults : []
|
|
14902
16379
|
})).filter((round) => round.response !== void 0);
|
|
14903
16380
|
}
|
|
14904
|
-
function
|
|
16381
|
+
function aggregateOpenRouterCallModelMetrics2(rounds, finalResponse) {
|
|
14905
16382
|
const metrics = {};
|
|
14906
16383
|
const responses = [
|
|
14907
16384
|
...rounds.map((round) => round.response).filter(isObject),
|
|
14908
16385
|
finalResponse
|
|
14909
16386
|
];
|
|
14910
16387
|
for (const response of responses) {
|
|
14911
|
-
const responseMetrics =
|
|
16388
|
+
const responseMetrics = parseOpenRouterMetricsFromUsage2(response.usage);
|
|
14912
16389
|
for (const [name, value] of Object.entries(responseMetrics)) {
|
|
14913
16390
|
metrics[name] = (metrics[name] || 0) + value;
|
|
14914
16391
|
}
|
|
14915
16392
|
}
|
|
14916
16393
|
return metrics;
|
|
14917
16394
|
}
|
|
14918
|
-
function
|
|
16395
|
+
function buildNextOpenRouterCallModelInput2(currentInput, response, toolResults) {
|
|
14919
16396
|
const normalizedInput = Array.isArray(currentInput) ? [...currentInput] : currentInput === void 0 ? [] : [currentInput];
|
|
14920
16397
|
const responseOutput = Array.isArray(response.output) ? response.output : response.output === void 0 ? [] : [response.output];
|
|
14921
16398
|
return [...normalizedInput, ...responseOutput, ...toolResults].map(
|
|
14922
|
-
(entry) =>
|
|
16399
|
+
(entry) => sanitizeOpenRouterLoggedValue2(entry)
|
|
14923
16400
|
);
|
|
14924
16401
|
}
|
|
14925
|
-
function
|
|
16402
|
+
function getOpenRouterResolvedRequest2(result, request) {
|
|
14926
16403
|
if (isObject(result.resolvedRequest)) {
|
|
14927
16404
|
return result.resolvedRequest;
|
|
14928
16405
|
}
|
|
14929
16406
|
return request;
|
|
14930
16407
|
}
|
|
14931
|
-
function
|
|
16408
|
+
function buildOpenRouterFollowupRequest2(request, currentResponse, toolResults) {
|
|
14932
16409
|
if (!request) {
|
|
14933
16410
|
return void 0;
|
|
14934
16411
|
}
|
|
14935
16412
|
return {
|
|
14936
16413
|
...request,
|
|
14937
|
-
input:
|
|
14938
|
-
|
|
16414
|
+
input: buildNextOpenRouterCallModelInput2(
|
|
16415
|
+
extractOpenRouterCallModelInput2(request),
|
|
14939
16416
|
isObject(currentResponse) ? currentResponse : {},
|
|
14940
16417
|
toolResults
|
|
14941
16418
|
),
|
|
14942
16419
|
stream: false
|
|
14943
16420
|
};
|
|
14944
16421
|
}
|
|
14945
|
-
function
|
|
16422
|
+
function wrapAsyncIterableWithSpan2(args) {
|
|
14946
16423
|
return {
|
|
14947
16424
|
[Symbol.asyncIterator]() {
|
|
14948
16425
|
const iterator = args.iteratorFactory();
|
|
@@ -14996,11 +16473,516 @@ function wrapAsyncIterableWithSpan(args) {
|
|
|
14996
16473
|
}
|
|
14997
16474
|
};
|
|
14998
16475
|
}
|
|
14999
|
-
function
|
|
15000
|
-
return !!value && (typeof value === "object" || typeof value === "function") && Symbol.asyncIterator in value && typeof value[Symbol.asyncIterator] === "function";
|
|
16476
|
+
function isAsyncIterable4(value) {
|
|
16477
|
+
return !!value && (typeof value === "object" || typeof value === "function") && Symbol.asyncIterator in value && typeof value[Symbol.asyncIterator] === "function";
|
|
16478
|
+
}
|
|
16479
|
+
function normalizeError2(error) {
|
|
16480
|
+
return error instanceof Error ? error : new Error(String(error));
|
|
16481
|
+
}
|
|
16482
|
+
|
|
16483
|
+
// src/instrumentation/plugins/mistral-channels.ts
|
|
16484
|
+
var mistralChannels = defineChannels("@mistralai/mistralai", {
|
|
16485
|
+
chatComplete: channel({
|
|
16486
|
+
channelName: "chat.complete",
|
|
16487
|
+
kind: "async"
|
|
16488
|
+
}),
|
|
16489
|
+
chatStream: channel({
|
|
16490
|
+
channelName: "chat.stream",
|
|
16491
|
+
kind: "async"
|
|
16492
|
+
}),
|
|
16493
|
+
embeddingsCreate: channel({
|
|
16494
|
+
channelName: "embeddings.create",
|
|
16495
|
+
kind: "async"
|
|
16496
|
+
}),
|
|
16497
|
+
fimComplete: channel({
|
|
16498
|
+
channelName: "fim.complete",
|
|
16499
|
+
kind: "async"
|
|
16500
|
+
}),
|
|
16501
|
+
fimStream: channel({
|
|
16502
|
+
channelName: "fim.stream",
|
|
16503
|
+
kind: "async"
|
|
16504
|
+
}),
|
|
16505
|
+
agentsComplete: channel({
|
|
16506
|
+
channelName: "agents.complete",
|
|
16507
|
+
kind: "async"
|
|
16508
|
+
}),
|
|
16509
|
+
agentsStream: channel({
|
|
16510
|
+
channelName: "agents.stream",
|
|
16511
|
+
kind: "async"
|
|
16512
|
+
})
|
|
16513
|
+
});
|
|
16514
|
+
|
|
16515
|
+
// src/instrumentation/plugins/mistral-plugin.ts
|
|
16516
|
+
var MistralPlugin = class extends BasePlugin {
|
|
16517
|
+
onEnable() {
|
|
16518
|
+
this.subscribeToMistralChannels();
|
|
16519
|
+
}
|
|
16520
|
+
onDisable() {
|
|
16521
|
+
this.unsubscribers = unsubscribeAll(this.unsubscribers);
|
|
16522
|
+
}
|
|
16523
|
+
subscribeToMistralChannels() {
|
|
16524
|
+
this.unsubscribers.push(
|
|
16525
|
+
traceStreamingChannel(mistralChannels.chatComplete, {
|
|
16526
|
+
name: "mistral.chat.complete",
|
|
16527
|
+
type: "llm" /* LLM */,
|
|
16528
|
+
extractInput: extractMessagesInputWithMetadata,
|
|
16529
|
+
extractOutput: (result) => {
|
|
16530
|
+
return result?.choices;
|
|
16531
|
+
},
|
|
16532
|
+
extractMetadata: (result) => extractMistralResponseMetadata(result),
|
|
16533
|
+
extractMetrics: (result, startTime) => extractMistralMetrics(result?.usage, startTime)
|
|
16534
|
+
})
|
|
16535
|
+
);
|
|
16536
|
+
this.unsubscribers.push(
|
|
16537
|
+
traceStreamingChannel(mistralChannels.chatStream, {
|
|
16538
|
+
name: "mistral.chat.stream",
|
|
16539
|
+
type: "llm" /* LLM */,
|
|
16540
|
+
extractInput: extractMessagesInputWithMetadata,
|
|
16541
|
+
extractOutput: extractMistralStreamOutput,
|
|
16542
|
+
extractMetadata: (result) => extractMistralResponseMetadata(result),
|
|
16543
|
+
extractMetrics: (result, startTime) => extractMistralStreamingMetrics(result, startTime),
|
|
16544
|
+
aggregateChunks: aggregateMistralStreamChunks
|
|
16545
|
+
})
|
|
16546
|
+
);
|
|
16547
|
+
this.unsubscribers.push(
|
|
16548
|
+
traceAsyncChannel(mistralChannels.embeddingsCreate, {
|
|
16549
|
+
name: "mistral.embeddings.create",
|
|
16550
|
+
type: "llm" /* LLM */,
|
|
16551
|
+
extractInput: extractEmbeddingInputWithMetadata,
|
|
16552
|
+
extractOutput: (result) => {
|
|
16553
|
+
const embedding = result?.data?.[0]?.embedding;
|
|
16554
|
+
return Array.isArray(embedding) ? { embedding_length: embedding.length } : void 0;
|
|
16555
|
+
},
|
|
16556
|
+
extractMetadata: (result) => extractMistralResponseMetadata(result),
|
|
16557
|
+
extractMetrics: (result) => parseMistralMetricsFromUsage(result?.usage)
|
|
16558
|
+
})
|
|
16559
|
+
);
|
|
16560
|
+
this.unsubscribers.push(
|
|
16561
|
+
traceStreamingChannel(mistralChannels.fimComplete, {
|
|
16562
|
+
name: "mistral.fim.complete",
|
|
16563
|
+
type: "llm" /* LLM */,
|
|
16564
|
+
extractInput: extractPromptInputWithMetadata,
|
|
16565
|
+
extractOutput: (result) => {
|
|
16566
|
+
return result?.choices;
|
|
16567
|
+
},
|
|
16568
|
+
extractMetadata: (result) => extractMistralResponseMetadata(result),
|
|
16569
|
+
extractMetrics: (result, startTime) => extractMistralMetrics(result?.usage, startTime)
|
|
16570
|
+
})
|
|
16571
|
+
);
|
|
16572
|
+
this.unsubscribers.push(
|
|
16573
|
+
traceStreamingChannel(mistralChannels.fimStream, {
|
|
16574
|
+
name: "mistral.fim.stream",
|
|
16575
|
+
type: "llm" /* LLM */,
|
|
16576
|
+
extractInput: extractPromptInputWithMetadata,
|
|
16577
|
+
extractOutput: extractMistralStreamOutput,
|
|
16578
|
+
extractMetadata: (result) => extractMistralResponseMetadata(result),
|
|
16579
|
+
extractMetrics: (result, startTime) => extractMistralStreamingMetrics(result, startTime),
|
|
16580
|
+
aggregateChunks: aggregateMistralStreamChunks
|
|
16581
|
+
})
|
|
16582
|
+
);
|
|
16583
|
+
this.unsubscribers.push(
|
|
16584
|
+
traceStreamingChannel(mistralChannels.agentsComplete, {
|
|
16585
|
+
name: "mistral.agents.complete",
|
|
16586
|
+
type: "llm" /* LLM */,
|
|
16587
|
+
extractInput: extractMessagesInputWithMetadata,
|
|
16588
|
+
extractOutput: (result) => {
|
|
16589
|
+
return result?.choices;
|
|
16590
|
+
},
|
|
16591
|
+
extractMetadata: (result) => extractMistralResponseMetadata(result),
|
|
16592
|
+
extractMetrics: (result, startTime) => extractMistralMetrics(result?.usage, startTime)
|
|
16593
|
+
})
|
|
16594
|
+
);
|
|
16595
|
+
this.unsubscribers.push(
|
|
16596
|
+
traceStreamingChannel(mistralChannels.agentsStream, {
|
|
16597
|
+
name: "mistral.agents.stream",
|
|
16598
|
+
type: "llm" /* LLM */,
|
|
16599
|
+
extractInput: extractMessagesInputWithMetadata,
|
|
16600
|
+
extractOutput: extractMistralStreamOutput,
|
|
16601
|
+
extractMetadata: (result) => extractMistralResponseMetadata(result),
|
|
16602
|
+
extractMetrics: (result, startTime) => extractMistralStreamingMetrics(result, startTime),
|
|
16603
|
+
aggregateChunks: aggregateMistralStreamChunks
|
|
16604
|
+
})
|
|
16605
|
+
);
|
|
16606
|
+
}
|
|
16607
|
+
};
|
|
16608
|
+
var TOKEN_NAME_MAP4 = {
|
|
16609
|
+
promptTokens: "prompt_tokens",
|
|
16610
|
+
inputTokens: "prompt_tokens",
|
|
16611
|
+
completionTokens: "completion_tokens",
|
|
16612
|
+
outputTokens: "completion_tokens",
|
|
16613
|
+
totalTokens: "tokens",
|
|
16614
|
+
prompt_tokens: "prompt_tokens",
|
|
16615
|
+
input_tokens: "prompt_tokens",
|
|
16616
|
+
completion_tokens: "completion_tokens",
|
|
16617
|
+
output_tokens: "completion_tokens",
|
|
16618
|
+
total_tokens: "tokens",
|
|
16619
|
+
promptAudioSeconds: "prompt_audio_seconds",
|
|
16620
|
+
prompt_audio_seconds: "prompt_audio_seconds"
|
|
16621
|
+
};
|
|
16622
|
+
var TOKEN_DETAIL_PREFIX_MAP3 = {
|
|
16623
|
+
promptTokensDetails: "prompt",
|
|
16624
|
+
inputTokensDetails: "prompt",
|
|
16625
|
+
completionTokensDetails: "completion",
|
|
16626
|
+
outputTokensDetails: "completion",
|
|
16627
|
+
prompt_tokens_details: "prompt",
|
|
16628
|
+
input_tokens_details: "prompt",
|
|
16629
|
+
completion_tokens_details: "completion",
|
|
16630
|
+
output_tokens_details: "completion"
|
|
16631
|
+
};
|
|
16632
|
+
var MISTRAL_REQUEST_METADATA_ALLOWLIST = /* @__PURE__ */ new Set([
|
|
16633
|
+
"agentId",
|
|
16634
|
+
"agent_id",
|
|
16635
|
+
"encodingFormat",
|
|
16636
|
+
"encoding_format",
|
|
16637
|
+
"frequencyPenalty",
|
|
16638
|
+
"frequency_penalty",
|
|
16639
|
+
"maxTokens",
|
|
16640
|
+
"max_tokens",
|
|
16641
|
+
"model",
|
|
16642
|
+
"n",
|
|
16643
|
+
"presencePenalty",
|
|
16644
|
+
"presence_penalty",
|
|
16645
|
+
"randomSeed",
|
|
16646
|
+
"random_seed",
|
|
16647
|
+
"responseFormat",
|
|
16648
|
+
"response_format",
|
|
16649
|
+
"safePrompt",
|
|
16650
|
+
"safe_prompt",
|
|
16651
|
+
"stream",
|
|
16652
|
+
"stop",
|
|
16653
|
+
"temperature",
|
|
16654
|
+
"toolChoice",
|
|
16655
|
+
"tool_choice",
|
|
16656
|
+
"topP",
|
|
16657
|
+
"top_p"
|
|
16658
|
+
]);
|
|
16659
|
+
var MISTRAL_RESPONSE_METADATA_ALLOWLIST = /* @__PURE__ */ new Set([
|
|
16660
|
+
"agentId",
|
|
16661
|
+
"agent_id",
|
|
16662
|
+
"created",
|
|
16663
|
+
"id",
|
|
16664
|
+
"model",
|
|
16665
|
+
"object"
|
|
16666
|
+
]);
|
|
16667
|
+
function camelToSnake3(value) {
|
|
16668
|
+
return value.replace(/[A-Z]/g, (match) => `_${match.toLowerCase()}`);
|
|
16669
|
+
}
|
|
16670
|
+
function normalizeArgs3(args) {
|
|
16671
|
+
if (Array.isArray(args)) {
|
|
16672
|
+
return args;
|
|
16673
|
+
}
|
|
16674
|
+
if (isArrayLike3(args)) {
|
|
16675
|
+
return Array.from(args);
|
|
16676
|
+
}
|
|
16677
|
+
return [args];
|
|
16678
|
+
}
|
|
16679
|
+
function isArrayLike3(value) {
|
|
16680
|
+
return isObject(value) && "length" in value && typeof value.length === "number" && Number.isInteger(value.length) && value.length >= 0;
|
|
16681
|
+
}
|
|
16682
|
+
function getMistralRequestArg(args) {
|
|
16683
|
+
const firstObjectArg = normalizeArgs3(args).find((arg) => isObject(arg));
|
|
16684
|
+
return isObject(firstObjectArg) ? firstObjectArg : void 0;
|
|
16685
|
+
}
|
|
16686
|
+
function addMistralProviderMetadata(metadata) {
|
|
16687
|
+
return {
|
|
16688
|
+
...metadata,
|
|
16689
|
+
provider: "mistral"
|
|
16690
|
+
};
|
|
16691
|
+
}
|
|
16692
|
+
function pickAllowedMetadata(metadata, allowlist) {
|
|
16693
|
+
if (!metadata) {
|
|
16694
|
+
return {};
|
|
16695
|
+
}
|
|
16696
|
+
const picked = {};
|
|
16697
|
+
for (const key of allowlist) {
|
|
16698
|
+
const value = metadata[key];
|
|
16699
|
+
if (value !== void 0) {
|
|
16700
|
+
picked[key] = value;
|
|
16701
|
+
}
|
|
16702
|
+
}
|
|
16703
|
+
return picked;
|
|
16704
|
+
}
|
|
16705
|
+
function extractMistralRequestMetadata(metadata) {
|
|
16706
|
+
return pickAllowedMetadata(metadata, MISTRAL_REQUEST_METADATA_ALLOWLIST);
|
|
16707
|
+
}
|
|
16708
|
+
function isMistralChatCompletionChunk(value) {
|
|
16709
|
+
return isObject(value);
|
|
16710
|
+
}
|
|
16711
|
+
function isMistralChunkChoice(value) {
|
|
16712
|
+
return isObject(value);
|
|
16713
|
+
}
|
|
16714
|
+
function extractMessagesInputWithMetadata(args) {
|
|
16715
|
+
const params = getMistralRequestArg(args);
|
|
16716
|
+
const { messages, ...rawMetadata } = params || {};
|
|
16717
|
+
return {
|
|
16718
|
+
input: processInputAttachments(messages),
|
|
16719
|
+
metadata: addMistralProviderMetadata(
|
|
16720
|
+
extractMistralRequestMetadata(rawMetadata)
|
|
16721
|
+
)
|
|
16722
|
+
};
|
|
16723
|
+
}
|
|
16724
|
+
function extractEmbeddingInputWithMetadata(args) {
|
|
16725
|
+
const params = getMistralRequestArg(args);
|
|
16726
|
+
const { inputs, ...rawMetadata } = params || {};
|
|
16727
|
+
return {
|
|
16728
|
+
input: inputs,
|
|
16729
|
+
metadata: addMistralProviderMetadata(
|
|
16730
|
+
extractMistralRequestMetadata(rawMetadata)
|
|
16731
|
+
)
|
|
16732
|
+
};
|
|
16733
|
+
}
|
|
16734
|
+
function extractPromptInputWithMetadata(args) {
|
|
16735
|
+
const params = getMistralRequestArg(args);
|
|
16736
|
+
const { prompt, ...rawMetadata } = params || {};
|
|
16737
|
+
return {
|
|
16738
|
+
input: prompt,
|
|
16739
|
+
metadata: addMistralProviderMetadata(
|
|
16740
|
+
extractMistralRequestMetadata(rawMetadata)
|
|
16741
|
+
)
|
|
16742
|
+
};
|
|
16743
|
+
}
|
|
16744
|
+
function extractMistralResponseMetadata(result) {
|
|
16745
|
+
if (!isObject(result)) {
|
|
16746
|
+
return void 0;
|
|
16747
|
+
}
|
|
16748
|
+
const { choices: _choices, usage: _usage, data: _data, ...metadata } = result;
|
|
16749
|
+
const picked = pickAllowedMetadata(
|
|
16750
|
+
metadata,
|
|
16751
|
+
MISTRAL_RESPONSE_METADATA_ALLOWLIST
|
|
16752
|
+
);
|
|
16753
|
+
return Object.keys(picked).length > 0 ? picked : void 0;
|
|
16754
|
+
}
|
|
16755
|
+
function extractMistralMetrics(usage, startTime) {
|
|
16756
|
+
const metrics = parseMistralMetricsFromUsage(usage);
|
|
16757
|
+
if (startTime) {
|
|
16758
|
+
metrics.time_to_first_token = getCurrentUnixTimestamp() - startTime;
|
|
16759
|
+
}
|
|
16760
|
+
return metrics;
|
|
16761
|
+
}
|
|
16762
|
+
function extractMistralStreamOutput(result) {
|
|
16763
|
+
return isObject(result) ? result.choices : void 0;
|
|
16764
|
+
}
|
|
16765
|
+
function extractMistralStreamingMetrics(result, startTime) {
|
|
16766
|
+
const metrics = isObject(result) ? parseMistralMetricsFromUsage(result.usage) : {};
|
|
16767
|
+
if (startTime) {
|
|
16768
|
+
metrics.time_to_first_token = getCurrentUnixTimestamp() - startTime;
|
|
16769
|
+
}
|
|
16770
|
+
return metrics;
|
|
16771
|
+
}
|
|
16772
|
+
function extractDeltaText(content) {
|
|
16773
|
+
if (typeof content === "string") {
|
|
16774
|
+
return content;
|
|
16775
|
+
}
|
|
16776
|
+
if (!Array.isArray(content)) {
|
|
16777
|
+
return void 0;
|
|
16778
|
+
}
|
|
16779
|
+
const textParts = content.map((part) => {
|
|
16780
|
+
if (!isObject(part) || part.type !== "text") {
|
|
16781
|
+
return "";
|
|
16782
|
+
}
|
|
16783
|
+
return typeof part.text === "string" ? part.text : "";
|
|
16784
|
+
}).filter((part) => part.length > 0);
|
|
16785
|
+
return textParts.length > 0 ? textParts.join("") : void 0;
|
|
16786
|
+
}
|
|
16787
|
+
function getDeltaToolCalls(delta) {
|
|
16788
|
+
const toolCalls = Array.isArray(delta.toolCalls) && delta.toolCalls || Array.isArray(delta.tool_calls) && delta.tool_calls || [];
|
|
16789
|
+
return toolCalls.filter((toolCall) => isObject(toolCall));
|
|
16790
|
+
}
|
|
16791
|
+
function getToolCallIndex(toolCall) {
|
|
16792
|
+
return typeof toolCall.index === "number" && toolCall.index >= 0 ? toolCall.index : void 0;
|
|
16793
|
+
}
|
|
16794
|
+
function createMergedToolCallDelta(delta) {
|
|
16795
|
+
return {
|
|
16796
|
+
...delta,
|
|
16797
|
+
function: {
|
|
16798
|
+
...delta.function,
|
|
16799
|
+
arguments: typeof delta.function?.arguments === "string" ? delta.function.arguments : ""
|
|
16800
|
+
}
|
|
16801
|
+
};
|
|
16802
|
+
}
|
|
16803
|
+
function mergeToolCallDeltaPair(current, delta) {
|
|
16804
|
+
const currentArguments = typeof current.function?.arguments === "string" ? current.function.arguments : "";
|
|
16805
|
+
const deltaArguments = typeof delta.function?.arguments === "string" ? delta.function.arguments : "";
|
|
16806
|
+
return {
|
|
16807
|
+
...current,
|
|
16808
|
+
...delta,
|
|
16809
|
+
function: {
|
|
16810
|
+
...current.function || {},
|
|
16811
|
+
...delta.function || {},
|
|
16812
|
+
arguments: `${currentArguments}${deltaArguments}`
|
|
16813
|
+
}
|
|
16814
|
+
};
|
|
15001
16815
|
}
|
|
15002
|
-
function
|
|
15003
|
-
|
|
16816
|
+
function mergeToolCallDeltas(toolCalls, deltas) {
|
|
16817
|
+
if (deltas.length === 0) {
|
|
16818
|
+
return toolCalls;
|
|
16819
|
+
}
|
|
16820
|
+
const merged = toolCalls ? [...toolCalls] : [];
|
|
16821
|
+
const indexToPosition = /* @__PURE__ */ new Map();
|
|
16822
|
+
const idToPosition = /* @__PURE__ */ new Map();
|
|
16823
|
+
for (const [position, toolCall] of merged.entries()) {
|
|
16824
|
+
const index = getToolCallIndex(toolCall);
|
|
16825
|
+
if (index !== void 0 && !indexToPosition.has(index)) {
|
|
16826
|
+
indexToPosition.set(index, position);
|
|
16827
|
+
}
|
|
16828
|
+
if (typeof toolCall.id === "string" && !idToPosition.has(toolCall.id)) {
|
|
16829
|
+
idToPosition.set(toolCall.id, position);
|
|
16830
|
+
}
|
|
16831
|
+
}
|
|
16832
|
+
for (const delta of deltas) {
|
|
16833
|
+
const deltaIndex = getToolCallIndex(delta);
|
|
16834
|
+
const existingByIndex = deltaIndex !== void 0 ? indexToPosition.get(deltaIndex) : void 0;
|
|
16835
|
+
const existingById = typeof delta.id === "string" ? idToPosition.get(delta.id) : void 0;
|
|
16836
|
+
const existingPosition = existingByIndex ?? existingById;
|
|
16837
|
+
if (existingPosition === void 0) {
|
|
16838
|
+
const newToolCall = createMergedToolCallDelta(delta);
|
|
16839
|
+
merged.push(newToolCall);
|
|
16840
|
+
const newPosition = merged.length - 1;
|
|
16841
|
+
const newIndex = getToolCallIndex(newToolCall);
|
|
16842
|
+
if (newIndex !== void 0 && !indexToPosition.has(newIndex)) {
|
|
16843
|
+
indexToPosition.set(newIndex, newPosition);
|
|
16844
|
+
}
|
|
16845
|
+
if (typeof newToolCall.id === "string" && !idToPosition.has(newToolCall.id)) {
|
|
16846
|
+
idToPosition.set(newToolCall.id, newPosition);
|
|
16847
|
+
}
|
|
16848
|
+
continue;
|
|
16849
|
+
}
|
|
16850
|
+
const mergedToolCall = mergeToolCallDeltaPair(
|
|
16851
|
+
merged[existingPosition],
|
|
16852
|
+
delta
|
|
16853
|
+
);
|
|
16854
|
+
merged[existingPosition] = mergedToolCall;
|
|
16855
|
+
const mergedIndex = getToolCallIndex(mergedToolCall);
|
|
16856
|
+
if (mergedIndex !== void 0 && !indexToPosition.has(mergedIndex)) {
|
|
16857
|
+
indexToPosition.set(mergedIndex, existingPosition);
|
|
16858
|
+
}
|
|
16859
|
+
if (typeof mergedToolCall.id === "string" && !idToPosition.has(mergedToolCall.id)) {
|
|
16860
|
+
idToPosition.set(mergedToolCall.id, existingPosition);
|
|
16861
|
+
}
|
|
16862
|
+
}
|
|
16863
|
+
return merged.length > 0 ? merged : void 0;
|
|
16864
|
+
}
|
|
16865
|
+
function getChoiceFinishReason(choice) {
|
|
16866
|
+
if (typeof choice.finishReason === "string" || choice.finishReason === null) {
|
|
16867
|
+
return choice.finishReason;
|
|
16868
|
+
}
|
|
16869
|
+
if (typeof choice.finish_reason === "string" || choice.finish_reason === null) {
|
|
16870
|
+
return choice.finish_reason;
|
|
16871
|
+
}
|
|
16872
|
+
return void 0;
|
|
16873
|
+
}
|
|
16874
|
+
function parseMistralMetricsFromUsage(usage) {
|
|
16875
|
+
if (!isObject(usage)) {
|
|
16876
|
+
return {};
|
|
16877
|
+
}
|
|
16878
|
+
const metrics = {};
|
|
16879
|
+
for (const [name, value] of Object.entries(usage)) {
|
|
16880
|
+
if (typeof value === "number") {
|
|
16881
|
+
metrics[TOKEN_NAME_MAP4[name] || camelToSnake3(name)] = value;
|
|
16882
|
+
continue;
|
|
16883
|
+
}
|
|
16884
|
+
if (!isObject(value)) {
|
|
16885
|
+
continue;
|
|
16886
|
+
}
|
|
16887
|
+
const prefix = TOKEN_DETAIL_PREFIX_MAP3[name];
|
|
16888
|
+
if (!prefix) {
|
|
16889
|
+
continue;
|
|
16890
|
+
}
|
|
16891
|
+
for (const [nestedName, nestedValue] of Object.entries(value)) {
|
|
16892
|
+
if (typeof nestedValue !== "number") {
|
|
16893
|
+
continue;
|
|
16894
|
+
}
|
|
16895
|
+
metrics[`${prefix}_${camelToSnake3(nestedName)}`] = nestedValue;
|
|
16896
|
+
}
|
|
16897
|
+
}
|
|
16898
|
+
return metrics;
|
|
16899
|
+
}
|
|
16900
|
+
function aggregateMistralStreamChunks(chunks) {
|
|
16901
|
+
const choiceAccumulators = /* @__PURE__ */ new Map();
|
|
16902
|
+
const indexToAccumulatorKey = /* @__PURE__ */ new Map();
|
|
16903
|
+
const positionToAccumulatorKey = /* @__PURE__ */ new Map();
|
|
16904
|
+
let nextAccumulatorOrder = 0;
|
|
16905
|
+
let metrics = {};
|
|
16906
|
+
let metadata;
|
|
16907
|
+
for (const event of chunks) {
|
|
16908
|
+
const chunk = isMistralChatCompletionChunk(event?.data) ? event.data : void 0;
|
|
16909
|
+
if (!chunk) {
|
|
16910
|
+
continue;
|
|
16911
|
+
}
|
|
16912
|
+
if (isObject(chunk.usage)) {
|
|
16913
|
+
metrics = {
|
|
16914
|
+
...metrics,
|
|
16915
|
+
...parseMistralMetricsFromUsage(chunk.usage)
|
|
16916
|
+
};
|
|
16917
|
+
}
|
|
16918
|
+
const chunkMetadata = extractMistralResponseMetadata(chunk);
|
|
16919
|
+
if (chunkMetadata) {
|
|
16920
|
+
metadata = { ...metadata || {}, ...chunkMetadata };
|
|
16921
|
+
}
|
|
16922
|
+
for (const [choicePosition, rawChoice] of (chunk.choices || []).entries()) {
|
|
16923
|
+
if (!isMistralChunkChoice(rawChoice)) {
|
|
16924
|
+
continue;
|
|
16925
|
+
}
|
|
16926
|
+
const choice = rawChoice;
|
|
16927
|
+
const choiceIndex = typeof choice.index === "number" && choice.index >= 0 ? choice.index : void 0;
|
|
16928
|
+
let accumulatorKey = choiceIndex !== void 0 ? indexToAccumulatorKey.get(choiceIndex) : void 0;
|
|
16929
|
+
if (!accumulatorKey) {
|
|
16930
|
+
accumulatorKey = positionToAccumulatorKey.get(choicePosition);
|
|
16931
|
+
}
|
|
16932
|
+
if (!accumulatorKey) {
|
|
16933
|
+
const initialIndex = choiceIndex ?? choicePosition;
|
|
16934
|
+
const keyPrefix = choiceIndex !== void 0 ? "index" : "position";
|
|
16935
|
+
accumulatorKey = `${keyPrefix}:${initialIndex}`;
|
|
16936
|
+
choiceAccumulators.set(accumulatorKey, {
|
|
16937
|
+
index: initialIndex,
|
|
16938
|
+
order: nextAccumulatorOrder++
|
|
16939
|
+
});
|
|
16940
|
+
}
|
|
16941
|
+
const accumulator = choiceAccumulators.get(accumulatorKey);
|
|
16942
|
+
if (!accumulator) {
|
|
16943
|
+
continue;
|
|
16944
|
+
}
|
|
16945
|
+
if (choiceIndex !== void 0) {
|
|
16946
|
+
accumulator.index = choiceIndex;
|
|
16947
|
+
indexToAccumulatorKey.set(choiceIndex, accumulatorKey);
|
|
16948
|
+
}
|
|
16949
|
+
positionToAccumulatorKey.set(choicePosition, accumulatorKey);
|
|
16950
|
+
const delta = isObject(choice.delta) ? choice.delta : void 0;
|
|
16951
|
+
if (delta) {
|
|
16952
|
+
if (!accumulator.role && typeof delta.role === "string") {
|
|
16953
|
+
accumulator.role = delta.role;
|
|
16954
|
+
}
|
|
16955
|
+
const deltaText = extractDeltaText(delta.content);
|
|
16956
|
+
if (deltaText) {
|
|
16957
|
+
accumulator.content = `${accumulator.content || ""}${deltaText}`;
|
|
16958
|
+
}
|
|
16959
|
+
accumulator.toolCalls = mergeToolCallDeltas(
|
|
16960
|
+
accumulator.toolCalls,
|
|
16961
|
+
getDeltaToolCalls(delta)
|
|
16962
|
+
);
|
|
16963
|
+
}
|
|
16964
|
+
const choiceFinishReason = getChoiceFinishReason(choice);
|
|
16965
|
+
if (choiceFinishReason !== void 0) {
|
|
16966
|
+
accumulator.finishReason = choiceFinishReason;
|
|
16967
|
+
}
|
|
16968
|
+
}
|
|
16969
|
+
}
|
|
16970
|
+
const output = Array.from(choiceAccumulators.values()).sort(
|
|
16971
|
+
(left, right) => left.index === right.index ? left.order - right.order : left.index - right.index
|
|
16972
|
+
).map((choice) => ({
|
|
16973
|
+
index: choice.index,
|
|
16974
|
+
message: {
|
|
16975
|
+
...choice.role ? { role: choice.role } : {},
|
|
16976
|
+
content: choice.content ?? null,
|
|
16977
|
+
...choice.toolCalls ? { toolCalls: choice.toolCalls } : {}
|
|
16978
|
+
},
|
|
16979
|
+
...choice.finishReason !== void 0 ? { finishReason: choice.finishReason } : {}
|
|
16980
|
+
}));
|
|
16981
|
+
return {
|
|
16982
|
+
output,
|
|
16983
|
+
metrics,
|
|
16984
|
+
...metadata ? { metadata } : {}
|
|
16985
|
+
};
|
|
15004
16986
|
}
|
|
15005
16987
|
|
|
15006
16988
|
// src/instrumentation/braintrust-plugin.ts
|
|
@@ -15012,6 +16994,8 @@ var BraintrustPlugin = class extends BasePlugin {
|
|
|
15012
16994
|
claudeAgentSDKPlugin = null;
|
|
15013
16995
|
googleGenAIPlugin = null;
|
|
15014
16996
|
openRouterPlugin = null;
|
|
16997
|
+
openRouterAgentPlugin = null;
|
|
16998
|
+
mistralPlugin = null;
|
|
15015
16999
|
constructor(config = {}) {
|
|
15016
17000
|
super();
|
|
15017
17001
|
this.config = config;
|
|
@@ -15042,6 +17026,14 @@ var BraintrustPlugin = class extends BasePlugin {
|
|
|
15042
17026
|
this.openRouterPlugin = new OpenRouterPlugin();
|
|
15043
17027
|
this.openRouterPlugin.enable();
|
|
15044
17028
|
}
|
|
17029
|
+
if (integrations.openrouterAgent !== false) {
|
|
17030
|
+
this.openRouterAgentPlugin = new OpenRouterAgentPlugin();
|
|
17031
|
+
this.openRouterAgentPlugin.enable();
|
|
17032
|
+
}
|
|
17033
|
+
if (integrations.mistral !== false) {
|
|
17034
|
+
this.mistralPlugin = new MistralPlugin();
|
|
17035
|
+
this.mistralPlugin.enable();
|
|
17036
|
+
}
|
|
15045
17037
|
}
|
|
15046
17038
|
onDisable() {
|
|
15047
17039
|
if (this.openaiPlugin) {
|
|
@@ -15068,6 +17060,14 @@ var BraintrustPlugin = class extends BasePlugin {
|
|
|
15068
17060
|
this.openRouterPlugin.disable();
|
|
15069
17061
|
this.openRouterPlugin = null;
|
|
15070
17062
|
}
|
|
17063
|
+
if (this.openRouterAgentPlugin) {
|
|
17064
|
+
this.openRouterAgentPlugin.disable();
|
|
17065
|
+
this.openRouterAgentPlugin = null;
|
|
17066
|
+
}
|
|
17067
|
+
if (this.mistralPlugin) {
|
|
17068
|
+
this.mistralPlugin.disable();
|
|
17069
|
+
this.mistralPlugin = null;
|
|
17070
|
+
}
|
|
15071
17071
|
}
|
|
15072
17072
|
};
|
|
15073
17073
|
|
|
@@ -15140,7 +17140,9 @@ var PluginRegistry = class {
|
|
|
15140
17140
|
aisdk: true,
|
|
15141
17141
|
google: true,
|
|
15142
17142
|
claudeAgentSDK: true,
|
|
15143
|
-
openrouter: true
|
|
17143
|
+
openrouter: true,
|
|
17144
|
+
openrouterAgent: true,
|
|
17145
|
+
mistral: true
|
|
15144
17146
|
};
|
|
15145
17147
|
}
|
|
15146
17148
|
/**
|
|
@@ -15287,6 +17289,7 @@ var exports_exports = {};
|
|
|
15287
17289
|
__export(exports_exports, {
|
|
15288
17290
|
Attachment: () => Attachment,
|
|
15289
17291
|
AttachmentReference: () => AttachmentReference,
|
|
17292
|
+
BRAINTRUST_CURRENT_SPAN_STORE: () => BRAINTRUST_CURRENT_SPAN_STORE,
|
|
15290
17293
|
BaseAttachment: () => BaseAttachment,
|
|
15291
17294
|
BaseExperiment: () => BaseExperiment,
|
|
15292
17295
|
BraintrustMiddleware: () => BraintrustMiddleware,
|
|
@@ -15413,9 +17416,11 @@ __export(exports_exports, {
|
|
|
15413
17416
|
wrapClaudeAgentSDK: () => wrapClaudeAgentSDK,
|
|
15414
17417
|
wrapGoogleGenAI: () => wrapGoogleGenAI,
|
|
15415
17418
|
wrapMastraAgent: () => wrapMastraAgent,
|
|
17419
|
+
wrapMistral: () => wrapMistral,
|
|
15416
17420
|
wrapOpenAI: () => wrapOpenAI,
|
|
15417
17421
|
wrapOpenAIv4: () => wrapOpenAIv4,
|
|
15418
17422
|
wrapOpenRouter: () => wrapOpenRouter,
|
|
17423
|
+
wrapOpenRouterAgent: () => wrapOpenRouterAgent,
|
|
15419
17424
|
wrapTraced: () => wrapTraced,
|
|
15420
17425
|
wrapVitest: () => wrapVitest
|
|
15421
17426
|
});
|
|
@@ -15672,21 +17677,26 @@ function responsesProxy(openai) {
|
|
|
15672
17677
|
}
|
|
15673
17678
|
return new Proxy(openai.responses, {
|
|
15674
17679
|
get(target, name, receiver) {
|
|
15675
|
-
if (name === "create") {
|
|
17680
|
+
if (name === "create" && typeof target.create === "function") {
|
|
15676
17681
|
return wrapResponsesAsync(
|
|
15677
17682
|
target.create.bind(target),
|
|
15678
17683
|
openAIChannels.responsesCreate
|
|
15679
17684
|
);
|
|
15680
|
-
} else if (name === "stream") {
|
|
17685
|
+
} else if (name === "stream" && typeof target.stream === "function") {
|
|
15681
17686
|
return wrapResponsesSyncStream(
|
|
15682
17687
|
target.stream.bind(target),
|
|
15683
17688
|
openAIChannels.responsesStream
|
|
15684
17689
|
);
|
|
15685
|
-
} else if (name === "parse") {
|
|
17690
|
+
} else if (name === "parse" && typeof target.parse === "function") {
|
|
15686
17691
|
return wrapResponsesAsync(
|
|
15687
17692
|
target.parse.bind(target),
|
|
15688
17693
|
openAIChannels.responsesParse
|
|
15689
17694
|
);
|
|
17695
|
+
} else if (name === "compact" && typeof target.compact === "function") {
|
|
17696
|
+
return wrapResponsesAsync(
|
|
17697
|
+
target.compact.bind(target),
|
|
17698
|
+
openAIChannels.responsesCompact
|
|
17699
|
+
);
|
|
15690
17700
|
}
|
|
15691
17701
|
return Reflect.get(target, name, receiver);
|
|
15692
17702
|
}
|
|
@@ -15747,7 +17757,7 @@ function wrapOpenAIv4(openai) {
|
|
|
15747
17757
|
return baseVal;
|
|
15748
17758
|
}
|
|
15749
17759
|
});
|
|
15750
|
-
const
|
|
17760
|
+
const chatProxy3 = new Proxy(typedOpenai.chat, {
|
|
15751
17761
|
get(target, name, receiver) {
|
|
15752
17762
|
if (name === "completions") {
|
|
15753
17763
|
return completionProxy;
|
|
@@ -15794,7 +17804,7 @@ function wrapOpenAIv4(openai) {
|
|
|
15794
17804
|
get(target, name) {
|
|
15795
17805
|
switch (name) {
|
|
15796
17806
|
case "chat":
|
|
15797
|
-
return
|
|
17807
|
+
return chatProxy3;
|
|
15798
17808
|
case "embeddings":
|
|
15799
17809
|
return embeddingProxy;
|
|
15800
17810
|
case "moderations":
|
|
@@ -15963,6 +17973,10 @@ function wrapAISDK(aiSDK, options = {}) {
|
|
|
15963
17973
|
);
|
|
15964
17974
|
case "streamObject":
|
|
15965
17975
|
return wrapStreamObject(typedAISDK.streamObject, options, typedAISDK);
|
|
17976
|
+
case "embed":
|
|
17977
|
+
return wrapEmbed(typedAISDK.embed, options, typedAISDK);
|
|
17978
|
+
case "embedMany":
|
|
17979
|
+
return wrapEmbedMany(typedAISDK.embedMany, options, typedAISDK);
|
|
15966
17980
|
case "Agent":
|
|
15967
17981
|
case "Experimental_Agent":
|
|
15968
17982
|
case "ToolLoopAgent":
|
|
@@ -16063,6 +18077,44 @@ var wrapGenerateObject = (generateObject, options = {}, aiSDK) => {
|
|
|
16063
18077
|
options
|
|
16064
18078
|
);
|
|
16065
18079
|
};
|
|
18080
|
+
var makeEmbedWrapper = (channel2, name, embed, contextOptions = {}, options = {}) => {
|
|
18081
|
+
const wrapper = async function(allParams) {
|
|
18082
|
+
const { span_info, ...params } = allParams;
|
|
18083
|
+
const tracedParams = { ...params };
|
|
18084
|
+
return channel2.tracePromise(
|
|
18085
|
+
() => embed(tracedParams),
|
|
18086
|
+
createAISDKChannelContext(tracedParams, {
|
|
18087
|
+
aiSDK: contextOptions.aiSDK,
|
|
18088
|
+
denyOutputPaths: options.denyOutputPaths,
|
|
18089
|
+
self: contextOptions.self,
|
|
18090
|
+
span_info: mergeSpanInfo(span_info, {
|
|
18091
|
+
name,
|
|
18092
|
+
spanType: contextOptions.spanType
|
|
18093
|
+
})
|
|
18094
|
+
})
|
|
18095
|
+
);
|
|
18096
|
+
};
|
|
18097
|
+
Object.defineProperty(wrapper, "name", { value: name, writable: false });
|
|
18098
|
+
return wrapper;
|
|
18099
|
+
};
|
|
18100
|
+
var wrapEmbed = (embed, options = {}, aiSDK) => {
|
|
18101
|
+
return makeEmbedWrapper(
|
|
18102
|
+
aiSDKChannels.embed,
|
|
18103
|
+
"embed",
|
|
18104
|
+
embed,
|
|
18105
|
+
{ aiSDK },
|
|
18106
|
+
options
|
|
18107
|
+
);
|
|
18108
|
+
};
|
|
18109
|
+
var wrapEmbedMany = (embedMany, options = {}, aiSDK) => {
|
|
18110
|
+
return makeEmbedWrapper(
|
|
18111
|
+
aiSDKChannels.embedMany,
|
|
18112
|
+
"embedMany",
|
|
18113
|
+
embedMany,
|
|
18114
|
+
{ aiSDK },
|
|
18115
|
+
options
|
|
18116
|
+
);
|
|
18117
|
+
};
|
|
16066
18118
|
var makeStreamWrapper = (channel2, name, streamText, contextOptions = {}, options = {}) => {
|
|
16067
18119
|
const wrapper = function(allParams) {
|
|
16068
18120
|
const { span_info, ...params } = allParams;
|
|
@@ -16417,14 +18469,14 @@ function extractModelFromResult(result) {
|
|
|
16417
18469
|
function extractModelFromWrapGenerateCallback(model) {
|
|
16418
18470
|
return model?.modelId;
|
|
16419
18471
|
}
|
|
16420
|
-
function
|
|
18472
|
+
function camelToSnake4(str) {
|
|
16421
18473
|
return str.replace(/[A-Z]/g, (letter) => `_${letter.toLowerCase()}`);
|
|
16422
18474
|
}
|
|
16423
18475
|
function extractModelParameters(params, excludeKeys) {
|
|
16424
18476
|
const modelParams = {};
|
|
16425
18477
|
for (const [key, value] of Object.entries(params)) {
|
|
16426
18478
|
if (value !== void 0 && !excludeKeys.has(key)) {
|
|
16427
|
-
const snakeKey =
|
|
18479
|
+
const snakeKey = camelToSnake4(key);
|
|
16428
18480
|
modelParams[snakeKey] = value;
|
|
16429
18481
|
}
|
|
16430
18482
|
}
|
|
@@ -16802,20 +18854,80 @@ function wrapClaudeAgentQuery(queryFn, defaultThis) {
|
|
|
16802
18854
|
const proxy = new Proxy(queryFn, {
|
|
16803
18855
|
apply(target, thisArg, argArray) {
|
|
16804
18856
|
const params = argArray[0] ?? {};
|
|
18857
|
+
const wrappedParams = {
|
|
18858
|
+
...params,
|
|
18859
|
+
options: {
|
|
18860
|
+
...params.options ?? {},
|
|
18861
|
+
[CLAUDE_AGENT_SDK_SKIP_LOCAL_TOOL_HOOKS_OPTION]: true
|
|
18862
|
+
}
|
|
18863
|
+
};
|
|
16805
18864
|
const invocationTarget = thisArg === proxy || thisArg === void 0 ? defaultThis ?? thisArg : thisArg;
|
|
16806
18865
|
return claudeAgentSDKChannels.query.traceSync(
|
|
16807
|
-
|
|
16808
|
-
() => Reflect.apply(target, invocationTarget, [params]),
|
|
18866
|
+
() => Reflect.apply(target, invocationTarget, [wrappedParams]),
|
|
16809
18867
|
// The channel carries no extra context fields, but the generated
|
|
16810
18868
|
// StartOf<> type for Record<string, never> is overly strict here.
|
|
16811
|
-
{ arguments: [
|
|
18869
|
+
{ arguments: [wrappedParams] }
|
|
18870
|
+
);
|
|
18871
|
+
}
|
|
18872
|
+
});
|
|
18873
|
+
return proxy;
|
|
18874
|
+
}
|
|
18875
|
+
function wrapClaudeAgentTool(toolFn, localToolMetadataByTool, defaultThis) {
|
|
18876
|
+
const proxy = new Proxy(toolFn, {
|
|
18877
|
+
apply(target, thisArg, argArray) {
|
|
18878
|
+
const invocationTarget = thisArg === proxy || thisArg === void 0 ? defaultThis ?? thisArg : thisArg;
|
|
18879
|
+
const wrappedArgs = [...argArray];
|
|
18880
|
+
const toolName = wrappedArgs[0];
|
|
18881
|
+
let handlerIndex = -1;
|
|
18882
|
+
for (let i = wrappedArgs.length - 1; i >= 0; i -= 1) {
|
|
18883
|
+
if (typeof wrappedArgs[i] === "function") {
|
|
18884
|
+
handlerIndex = i;
|
|
18885
|
+
break;
|
|
18886
|
+
}
|
|
18887
|
+
}
|
|
18888
|
+
if (typeof toolName !== "string" || handlerIndex === -1) {
|
|
18889
|
+
return Reflect.apply(target, invocationTarget, wrappedArgs);
|
|
18890
|
+
}
|
|
18891
|
+
const localToolMetadata = { toolName };
|
|
18892
|
+
const originalHandler = wrappedArgs[handlerIndex];
|
|
18893
|
+
wrappedArgs[handlerIndex] = wrapLocalClaudeToolHandler(
|
|
18894
|
+
originalHandler,
|
|
18895
|
+
() => localToolMetadata
|
|
16812
18896
|
);
|
|
18897
|
+
const wrappedTool = Reflect.apply(target, invocationTarget, wrappedArgs);
|
|
18898
|
+
if (wrappedTool && typeof wrappedTool === "object") {
|
|
18899
|
+
localToolMetadataByTool.set(wrappedTool, localToolMetadata);
|
|
18900
|
+
}
|
|
18901
|
+
return wrappedTool;
|
|
18902
|
+
}
|
|
18903
|
+
});
|
|
18904
|
+
return proxy;
|
|
18905
|
+
}
|
|
18906
|
+
function wrapCreateSdkMcpServer(createSdkMcpServerFn, localToolMetadataByTool, defaultThis) {
|
|
18907
|
+
const proxy = new Proxy(createSdkMcpServerFn, {
|
|
18908
|
+
apply(target, thisArg, argArray) {
|
|
18909
|
+
const invocationTarget = thisArg === proxy || thisArg === void 0 ? defaultThis ?? thisArg : thisArg;
|
|
18910
|
+
const config = argArray[0];
|
|
18911
|
+
const serverName = config?.name;
|
|
18912
|
+
if (typeof serverName === "string" && Array.isArray(config?.tools)) {
|
|
18913
|
+
for (const tool of config.tools) {
|
|
18914
|
+
if (!tool || typeof tool !== "object") {
|
|
18915
|
+
continue;
|
|
18916
|
+
}
|
|
18917
|
+
const metadata = localToolMetadataByTool.get(tool);
|
|
18918
|
+
if (metadata) {
|
|
18919
|
+
metadata.serverName = serverName;
|
|
18920
|
+
}
|
|
18921
|
+
}
|
|
18922
|
+
}
|
|
18923
|
+
return Reflect.apply(target, invocationTarget, argArray);
|
|
16813
18924
|
}
|
|
16814
18925
|
});
|
|
16815
18926
|
return proxy;
|
|
16816
18927
|
}
|
|
16817
18928
|
function claudeAgentSDKProxy(sdk) {
|
|
16818
18929
|
const cache = /* @__PURE__ */ new Map();
|
|
18930
|
+
const localToolMetadataByTool = /* @__PURE__ */ new WeakMap();
|
|
16819
18931
|
return new Proxy(sdk, {
|
|
16820
18932
|
get(target, prop, receiver) {
|
|
16821
18933
|
if (cache.has(prop)) {
|
|
@@ -16827,6 +18939,24 @@ function claudeAgentSDKProxy(sdk) {
|
|
|
16827
18939
|
cache.set(prop, wrappedQuery);
|
|
16828
18940
|
return wrappedQuery;
|
|
16829
18941
|
}
|
|
18942
|
+
if (prop === "tool" && typeof value === "function") {
|
|
18943
|
+
const wrappedTool = wrapClaudeAgentTool(
|
|
18944
|
+
target.tool,
|
|
18945
|
+
localToolMetadataByTool,
|
|
18946
|
+
target
|
|
18947
|
+
);
|
|
18948
|
+
cache.set(prop, wrappedTool);
|
|
18949
|
+
return wrappedTool;
|
|
18950
|
+
}
|
|
18951
|
+
if (prop === "createSdkMcpServer" && typeof value === "function") {
|
|
18952
|
+
const wrappedCreateSdkMcpServer = wrapCreateSdkMcpServer(
|
|
18953
|
+
value,
|
|
18954
|
+
localToolMetadataByTool,
|
|
18955
|
+
target
|
|
18956
|
+
);
|
|
18957
|
+
cache.set(prop, wrappedCreateSdkMcpServer);
|
|
18958
|
+
return wrappedCreateSdkMcpServer;
|
|
18959
|
+
}
|
|
16830
18960
|
if (typeof value === "function") {
|
|
16831
18961
|
const bound = value.bind(target);
|
|
16832
18962
|
cache.set(prop, bound);
|
|
@@ -16912,6 +19042,62 @@ function wrapGenerateContentStream(original) {
|
|
|
16912
19042
|
};
|
|
16913
19043
|
}
|
|
16914
19044
|
|
|
19045
|
+
// src/wrappers/openrouter-agent.ts
|
|
19046
|
+
function wrapOpenRouterAgent(agent) {
|
|
19047
|
+
const candidate = agent;
|
|
19048
|
+
if (candidate && typeof candidate === "object" && "callModel" in candidate && typeof candidate.callModel === "function") {
|
|
19049
|
+
return openRouterAgentProxy(candidate);
|
|
19050
|
+
}
|
|
19051
|
+
console.warn("Unsupported OpenRouter Agent library. Not wrapping.");
|
|
19052
|
+
return agent;
|
|
19053
|
+
}
|
|
19054
|
+
function openRouterAgentProxy(agent) {
|
|
19055
|
+
const cache = /* @__PURE__ */ new Map();
|
|
19056
|
+
return new Proxy(agent, {
|
|
19057
|
+
get(target, prop, receiver) {
|
|
19058
|
+
if (cache.has(prop)) {
|
|
19059
|
+
return cache.get(prop);
|
|
19060
|
+
}
|
|
19061
|
+
const value = Reflect.get(target, prop, receiver);
|
|
19062
|
+
if (prop === "callModel" && typeof value === "function") {
|
|
19063
|
+
const wrapped = wrapCallModel(
|
|
19064
|
+
value,
|
|
19065
|
+
target
|
|
19066
|
+
);
|
|
19067
|
+
cache.set(prop, wrapped);
|
|
19068
|
+
return wrapped;
|
|
19069
|
+
}
|
|
19070
|
+
if (typeof value === "function") {
|
|
19071
|
+
const bound = value.bind(target);
|
|
19072
|
+
cache.set(prop, bound);
|
|
19073
|
+
return bound;
|
|
19074
|
+
}
|
|
19075
|
+
return value;
|
|
19076
|
+
}
|
|
19077
|
+
});
|
|
19078
|
+
}
|
|
19079
|
+
function wrapCallModel(callModelFn, defaultThis) {
|
|
19080
|
+
return new Proxy(callModelFn, {
|
|
19081
|
+
apply(target, thisArg, argArray) {
|
|
19082
|
+
const request = cloneCallModelRequest(argArray[0]);
|
|
19083
|
+
const options = argArray[1];
|
|
19084
|
+
const invocationTarget = thisArg === void 0 ? defaultThis ?? thisArg : thisArg;
|
|
19085
|
+
return openRouterAgentChannels.callModel.traceSync(
|
|
19086
|
+
() => Reflect.apply(target, invocationTarget, [request, options]),
|
|
19087
|
+
{
|
|
19088
|
+
arguments: [request]
|
|
19089
|
+
}
|
|
19090
|
+
);
|
|
19091
|
+
}
|
|
19092
|
+
});
|
|
19093
|
+
}
|
|
19094
|
+
function cloneCallModelRequest(request) {
|
|
19095
|
+
if (!request || typeof request !== "object") {
|
|
19096
|
+
return request;
|
|
19097
|
+
}
|
|
19098
|
+
return { ...request };
|
|
19099
|
+
}
|
|
19100
|
+
|
|
16915
19101
|
// src/wrappers/openrouter.ts
|
|
16916
19102
|
function wrapOpenRouter(openrouter) {
|
|
16917
19103
|
const or = openrouter;
|
|
@@ -16932,7 +19118,7 @@ function openRouterProxy(openrouter) {
|
|
|
16932
19118
|
case "beta":
|
|
16933
19119
|
return target.beta ? betaProxy2(target.beta) : target.beta;
|
|
16934
19120
|
case "callModel":
|
|
16935
|
-
return typeof target.callModel === "function" ?
|
|
19121
|
+
return typeof target.callModel === "function" ? wrapCallModel2(target.callModel.bind(target)) : target.callModel;
|
|
16936
19122
|
default:
|
|
16937
19123
|
return Reflect.get(target, prop, receiver);
|
|
16938
19124
|
}
|
|
@@ -16996,7 +19182,7 @@ function wrapResponsesSend(send) {
|
|
|
16996
19182
|
{ arguments: [request] }
|
|
16997
19183
|
);
|
|
16998
19184
|
}
|
|
16999
|
-
function
|
|
19185
|
+
function wrapCallModel2(callModel) {
|
|
17000
19186
|
return (request, options) => {
|
|
17001
19187
|
const tracedRequest = { ...request };
|
|
17002
19188
|
return openRouterChannels.callModel.traceSync(
|
|
@@ -17008,6 +19194,148 @@ function wrapCallModel(callModel) {
|
|
|
17008
19194
|
};
|
|
17009
19195
|
}
|
|
17010
19196
|
|
|
19197
|
+
// src/wrappers/mistral.ts
|
|
19198
|
+
function wrapMistral(mistral) {
|
|
19199
|
+
if (isSupportedMistralClient(mistral)) {
|
|
19200
|
+
return mistralProxy(mistral);
|
|
19201
|
+
}
|
|
19202
|
+
console.warn("Unsupported Mistral library. Not wrapping.");
|
|
19203
|
+
return mistral;
|
|
19204
|
+
}
|
|
19205
|
+
function isRecord(value) {
|
|
19206
|
+
return typeof value === "object" && value !== null;
|
|
19207
|
+
}
|
|
19208
|
+
function hasFunction(value, methodName) {
|
|
19209
|
+
return isRecord(value) && methodName in value && typeof value[methodName] === "function";
|
|
19210
|
+
}
|
|
19211
|
+
function isSupportedMistralClient(value) {
|
|
19212
|
+
if (!isRecord(value)) {
|
|
19213
|
+
return false;
|
|
19214
|
+
}
|
|
19215
|
+
return value.chat !== void 0 && hasChat(value.chat) || value.embeddings !== void 0 && hasEmbeddings(value.embeddings) || value.fim !== void 0 && hasFim(value.fim) || value.agents !== void 0 && hasAgents(value.agents);
|
|
19216
|
+
}
|
|
19217
|
+
function hasChat(value) {
|
|
19218
|
+
return hasFunction(value, "complete") && hasFunction(value, "stream");
|
|
19219
|
+
}
|
|
19220
|
+
function hasEmbeddings(value) {
|
|
19221
|
+
return hasFunction(value, "create");
|
|
19222
|
+
}
|
|
19223
|
+
function hasFim(value) {
|
|
19224
|
+
return hasFunction(value, "complete") && hasFunction(value, "stream");
|
|
19225
|
+
}
|
|
19226
|
+
function hasAgents(value) {
|
|
19227
|
+
return hasFunction(value, "complete") && hasFunction(value, "stream");
|
|
19228
|
+
}
|
|
19229
|
+
function mistralProxy(mistral) {
|
|
19230
|
+
return new Proxy(mistral, {
|
|
19231
|
+
get(target, prop, receiver) {
|
|
19232
|
+
switch (prop) {
|
|
19233
|
+
case "chat":
|
|
19234
|
+
return target.chat ? chatProxy2(target.chat) : target.chat;
|
|
19235
|
+
case "fim":
|
|
19236
|
+
return target.fim ? fimProxy(target.fim) : target.fim;
|
|
19237
|
+
case "agents":
|
|
19238
|
+
return target.agents ? agentsProxy(target.agents) : target.agents;
|
|
19239
|
+
case "embeddings":
|
|
19240
|
+
return target.embeddings ? embeddingsProxy2(target.embeddings) : target.embeddings;
|
|
19241
|
+
default:
|
|
19242
|
+
return Reflect.get(target, prop, receiver);
|
|
19243
|
+
}
|
|
19244
|
+
}
|
|
19245
|
+
});
|
|
19246
|
+
}
|
|
19247
|
+
function chatProxy2(chat) {
|
|
19248
|
+
return new Proxy(chat, {
|
|
19249
|
+
get(target, prop, receiver) {
|
|
19250
|
+
if (prop === "complete") {
|
|
19251
|
+
return wrapChatComplete(target.complete.bind(target));
|
|
19252
|
+
}
|
|
19253
|
+
if (prop === "stream") {
|
|
19254
|
+
return wrapChatStream(target.stream.bind(target));
|
|
19255
|
+
}
|
|
19256
|
+
return Reflect.get(target, prop, receiver);
|
|
19257
|
+
}
|
|
19258
|
+
});
|
|
19259
|
+
}
|
|
19260
|
+
function embeddingsProxy2(embeddings) {
|
|
19261
|
+
return new Proxy(embeddings, {
|
|
19262
|
+
get(target, prop, receiver) {
|
|
19263
|
+
if (prop === "create") {
|
|
19264
|
+
return wrapEmbeddingsCreate(target.create.bind(target));
|
|
19265
|
+
}
|
|
19266
|
+
return Reflect.get(target, prop, receiver);
|
|
19267
|
+
}
|
|
19268
|
+
});
|
|
19269
|
+
}
|
|
19270
|
+
function fimProxy(fim) {
|
|
19271
|
+
return new Proxy(fim, {
|
|
19272
|
+
get(target, prop, receiver) {
|
|
19273
|
+
if (prop === "complete") {
|
|
19274
|
+
return wrapFimComplete(target.complete.bind(target));
|
|
19275
|
+
}
|
|
19276
|
+
if (prop === "stream") {
|
|
19277
|
+
return wrapFimStream(target.stream.bind(target));
|
|
19278
|
+
}
|
|
19279
|
+
return Reflect.get(target, prop, receiver);
|
|
19280
|
+
}
|
|
19281
|
+
});
|
|
19282
|
+
}
|
|
19283
|
+
function agentsProxy(agents) {
|
|
19284
|
+
return new Proxy(agents, {
|
|
19285
|
+
get(target, prop, receiver) {
|
|
19286
|
+
if (prop === "complete") {
|
|
19287
|
+
return wrapAgentsComplete(target.complete.bind(target));
|
|
19288
|
+
}
|
|
19289
|
+
if (prop === "stream") {
|
|
19290
|
+
return wrapAgentsStream(target.stream.bind(target));
|
|
19291
|
+
}
|
|
19292
|
+
return Reflect.get(target, prop, receiver);
|
|
19293
|
+
}
|
|
19294
|
+
});
|
|
19295
|
+
}
|
|
19296
|
+
function wrapChatComplete(complete) {
|
|
19297
|
+
return (request, options) => mistralChannels.chatComplete.tracePromise(
|
|
19298
|
+
() => complete(request, options),
|
|
19299
|
+
{
|
|
19300
|
+
arguments: [request]
|
|
19301
|
+
}
|
|
19302
|
+
);
|
|
19303
|
+
}
|
|
19304
|
+
function wrapChatStream(stream) {
|
|
19305
|
+
return (request, options) => mistralChannels.chatStream.tracePromise(() => stream(request, options), {
|
|
19306
|
+
arguments: [request]
|
|
19307
|
+
});
|
|
19308
|
+
}
|
|
19309
|
+
function wrapEmbeddingsCreate(create) {
|
|
19310
|
+
return (request, options) => mistralChannels.embeddingsCreate.tracePromise(
|
|
19311
|
+
() => create(request, options),
|
|
19312
|
+
{ arguments: [request] }
|
|
19313
|
+
);
|
|
19314
|
+
}
|
|
19315
|
+
function wrapFimComplete(complete) {
|
|
19316
|
+
return (request, options) => mistralChannels.fimComplete.tracePromise(() => complete(request, options), {
|
|
19317
|
+
arguments: [request]
|
|
19318
|
+
});
|
|
19319
|
+
}
|
|
19320
|
+
function wrapFimStream(stream) {
|
|
19321
|
+
return (request, options) => mistralChannels.fimStream.tracePromise(() => stream(request, options), {
|
|
19322
|
+
arguments: [request]
|
|
19323
|
+
});
|
|
19324
|
+
}
|
|
19325
|
+
function wrapAgentsComplete(complete) {
|
|
19326
|
+
return (request, options) => mistralChannels.agentsComplete.tracePromise(
|
|
19327
|
+
() => complete(request, options),
|
|
19328
|
+
{
|
|
19329
|
+
arguments: [request]
|
|
19330
|
+
}
|
|
19331
|
+
);
|
|
19332
|
+
}
|
|
19333
|
+
function wrapAgentsStream(stream) {
|
|
19334
|
+
return (request, options) => mistralChannels.agentsStream.tracePromise(() => stream(request, options), {
|
|
19335
|
+
arguments: [request]
|
|
19336
|
+
});
|
|
19337
|
+
}
|
|
19338
|
+
|
|
17011
19339
|
// src/wrappers/vitest/context-manager.ts
|
|
17012
19340
|
var VitestContextManager = class {
|
|
17013
19341
|
/**
|
|
@@ -17978,7 +20306,7 @@ function isAsync(fn) {
|
|
|
17978
20306
|
function isAsyncGenerator2(fn) {
|
|
17979
20307
|
return fn[Symbol.toStringTag] === "AsyncGenerator";
|
|
17980
20308
|
}
|
|
17981
|
-
function
|
|
20309
|
+
function isAsyncIterable5(obj) {
|
|
17982
20310
|
return typeof obj[Symbol.asyncIterator] === "function";
|
|
17983
20311
|
}
|
|
17984
20312
|
function wrapAsync(asyncFn) {
|
|
@@ -18028,7 +20356,7 @@ function _asyncMap(eachfn, arr, iteratee, callback) {
|
|
|
18028
20356
|
callback(err, results);
|
|
18029
20357
|
});
|
|
18030
20358
|
}
|
|
18031
|
-
function
|
|
20359
|
+
function isArrayLike4(value) {
|
|
18032
20360
|
return value && typeof value.length === "number" && value.length >= 0 && value.length % 1 === 0;
|
|
18033
20361
|
}
|
|
18034
20362
|
var breakLoop = {};
|
|
@@ -18076,7 +20404,7 @@ function createObjectIterator(obj) {
|
|
|
18076
20404
|
};
|
|
18077
20405
|
}
|
|
18078
20406
|
function createIterator(coll) {
|
|
18079
|
-
if (
|
|
20407
|
+
if (isArrayLike4(coll)) {
|
|
18080
20408
|
return createArrayIterator(coll);
|
|
18081
20409
|
}
|
|
18082
20410
|
var iterator = getIterator(coll);
|
|
@@ -18150,7 +20478,7 @@ var eachOfLimit$2 = (limit) => {
|
|
|
18150
20478
|
if (isAsyncGenerator2(obj)) {
|
|
18151
20479
|
return asyncEachOfLimit(obj, limit, iteratee, callback);
|
|
18152
20480
|
}
|
|
18153
|
-
if (
|
|
20481
|
+
if (isAsyncIterable5(obj)) {
|
|
18154
20482
|
return asyncEachOfLimit(obj[Symbol.asyncIterator](), limit, iteratee, callback);
|
|
18155
20483
|
}
|
|
18156
20484
|
var nextElem = createIterator(obj);
|
|
@@ -18222,7 +20550,7 @@ function eachOfGeneric(coll, iteratee, callback) {
|
|
|
18222
20550
|
return eachOfLimit$1(coll, Infinity, iteratee, callback);
|
|
18223
20551
|
}
|
|
18224
20552
|
function eachOf(coll, iteratee, callback) {
|
|
18225
|
-
var eachOfImplementation =
|
|
20553
|
+
var eachOfImplementation = isArrayLike4(coll) ? eachOfArrayLike : eachOfGeneric;
|
|
18226
20554
|
return eachOfImplementation(coll, wrapAsync(iteratee), callback);
|
|
18227
20555
|
}
|
|
18228
20556
|
var eachOf$1 = awaitify(eachOf, 3);
|
|
@@ -18737,7 +21065,7 @@ function filterGeneric(eachfn, coll, iteratee, callback) {
|
|
|
18737
21065
|
});
|
|
18738
21066
|
}
|
|
18739
21067
|
function _filter(eachfn, coll, iteratee, callback) {
|
|
18740
|
-
var filter2 =
|
|
21068
|
+
var filter2 = isArrayLike4(coll) ? filterArray : filterGeneric;
|
|
18741
21069
|
return filter2(eachfn, coll, wrapAsync(iteratee), callback);
|
|
18742
21070
|
}
|
|
18743
21071
|
function filter(coll, iteratee, callback) {
|
|
@@ -18812,7 +21140,7 @@ if (hasNextTick) {
|
|
|
18812
21140
|
}
|
|
18813
21141
|
var nextTick = wrap(_defer);
|
|
18814
21142
|
var _parallel = awaitify((eachfn, tasks, callback) => {
|
|
18815
|
-
var results =
|
|
21143
|
+
var results = isArrayLike4(tasks) ? [] : {};
|
|
18816
21144
|
eachfn(tasks, (task, key, taskCb) => {
|
|
18817
21145
|
wrapAsync(task)((err, ...result) => {
|
|
18818
21146
|
if (result.length < 2) {
|
|
@@ -19438,7 +21766,7 @@ function callEvaluatorData(data) {
|
|
|
19438
21766
|
baseExperiment
|
|
19439
21767
|
};
|
|
19440
21768
|
}
|
|
19441
|
-
function
|
|
21769
|
+
function isAsyncIterable6(value) {
|
|
19442
21770
|
return typeof value === "object" && value !== null && Symbol.asyncIterator in value && typeof value[Symbol.asyncIterator] === "function";
|
|
19443
21771
|
}
|
|
19444
21772
|
function isIterable(value) {
|
|
@@ -19662,7 +21990,7 @@ async function runEvaluatorInternal(experiment, evaluator, progressReporter, fil
|
|
|
19662
21990
|
}
|
|
19663
21991
|
const resolvedDataResult = dataResult instanceof Promise ? await dataResult : dataResult;
|
|
19664
21992
|
const dataIterable = (() => {
|
|
19665
|
-
if (
|
|
21993
|
+
if (isAsyncIterable6(resolvedDataResult)) {
|
|
19666
21994
|
return resolvedDataResult;
|
|
19667
21995
|
}
|
|
19668
21996
|
if (Array.isArray(resolvedDataResult) || isIterable(resolvedDataResult)) {
|
|
@@ -20721,7 +23049,7 @@ var parametersContainerSchema = z13.object({
|
|
|
20721
23049
|
var staticParametersContainerSchema = z13.object({
|
|
20722
23050
|
type: z13.literal("braintrust.staticParameters"),
|
|
20723
23051
|
schema: staticParametersSchema,
|
|
20724
|
-
source: z13.null()
|
|
23052
|
+
source: z13.null().nullish()
|
|
20725
23053
|
});
|
|
20726
23054
|
var serializedParametersContainerSchema = z13.union([
|
|
20727
23055
|
parametersContainerSchema,
|
|
@@ -20743,6 +23071,7 @@ configureBrowser();
|
|
|
20743
23071
|
export {
|
|
20744
23072
|
Attachment,
|
|
20745
23073
|
AttachmentReference,
|
|
23074
|
+
BRAINTRUST_CURRENT_SPAN_STORE,
|
|
20746
23075
|
BaseAttachment,
|
|
20747
23076
|
BaseExperiment,
|
|
20748
23077
|
BraintrustMiddleware,
|
|
@@ -20870,9 +23199,11 @@ export {
|
|
|
20870
23199
|
wrapClaudeAgentSDK,
|
|
20871
23200
|
wrapGoogleGenAI,
|
|
20872
23201
|
wrapMastraAgent,
|
|
23202
|
+
wrapMistral,
|
|
20873
23203
|
wrapOpenAI,
|
|
20874
23204
|
wrapOpenAIv4,
|
|
20875
23205
|
wrapOpenRouter,
|
|
23206
|
+
wrapOpenRouterAgent,
|
|
20876
23207
|
wrapTraced,
|
|
20877
23208
|
wrapVitest
|
|
20878
23209
|
};
|