agents 0.20.1 → 0.22.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/README.md +51 -12
- package/dist/{agent-tool-types-BC-WFlsz.d.ts → agent-routing-CnkaHb-v.d.ts} +3305 -3138
- package/dist/agent-routing.d.ts +14 -0
- package/dist/agent-routing.js +187 -0
- package/dist/agent-routing.js.map +1 -0
- package/dist/agent-tool-types.d.ts +26 -26
- package/dist/{agent-tools-DeHe9Xov.d.ts → agent-tools-C0XJqWzB.d.ts} +7 -7
- package/dist/agent-tools.d.ts +44 -28
- package/dist/agent-tools.js +16 -7
- package/dist/agent-tools.js.map +1 -1
- package/dist/browser/ai.d.ts +5 -3
- package/dist/browser/ai.js +88 -8
- package/dist/browser/ai.js.map +1 -1
- package/dist/browser/index.d.ts +1 -1
- package/dist/browser/index.js +1 -1
- package/dist/browser/tanstack-ai.js +13 -1
- package/dist/browser/tanstack-ai.js.map +1 -1
- package/dist/capability-BjSKYpzg.js +42 -0
- package/dist/capability-BjSKYpzg.js.map +1 -0
- package/dist/capability-runner-CvHGZqUu.d.ts +150 -0
- package/dist/chat/index.d.ts +51 -15
- package/dist/chat/index.js +59 -4
- package/dist/chat/index.js.map +1 -1
- package/dist/chat/react.d.ts +19 -180
- package/dist/chat/react.js +93 -600
- package/dist/chat/react.js.map +1 -1
- package/dist/chat/transport.d.ts +10 -0
- package/dist/chat/transport.js +2 -0
- package/dist/chat-sdk/index.d.ts +4 -4
- package/dist/chat-sdk/index.js +1 -1
- package/dist/{client-zqKcsyFa.js → client-jagG8a9_.js} +129 -37
- package/dist/client-jagG8a9_.js.map +1 -0
- package/dist/client.d.ts +1 -1
- package/dist/client.js +1 -1
- package/dist/{cloudflare-BduZwmYK.js → cloudflare-Dzvc7V2N.js} +10 -3
- package/dist/{cloudflare-BduZwmYK.js.map → cloudflare-Dzvc7V2N.js.map} +1 -1
- package/dist/{connector-v2M1zlZp.d.ts → connector-CkQD4MK3.d.ts} +20 -3
- package/dist/{connector-KEJnl6e5.js → connector-CptFKzRh.js} +158 -40
- package/dist/connector-CptFKzRh.js.map +1 -0
- package/dist/current-agent-CuMErtly.d.ts +283 -0
- package/dist/current-agent-DhoDkSnH.js +51 -0
- package/dist/current-agent-DhoDkSnH.js.map +1 -0
- package/dist/diagnostics-CaBjfz4J.js +41 -0
- package/dist/diagnostics-CaBjfz4J.js.map +1 -0
- package/dist/{do-oauth-client-provider-VTZj2VtM.d.ts → do-oauth-client-provider-Tmf1vgKz.d.ts} +2 -2
- package/dist/durable-object-lifecycle-D6nNQJJd.js +862 -0
- package/dist/durable-object-lifecycle-D6nNQJJd.js.map +1 -0
- package/dist/{email-CL27preh.d.ts → email-7TatiTnl.d.ts} +38 -9
- package/dist/email-send.d.ts +15 -0
- package/dist/email-send.js +32 -0
- package/dist/email-send.js.map +1 -0
- package/dist/email.d.ts +14 -10
- package/dist/email.js.map +1 -1
- package/dist/experimental/memory/session/index.d.ts +3 -2
- package/dist/experimental/memory/session/index.js +15 -10
- package/dist/experimental/memory/session/index.js.map +1 -1
- package/dist/{handler-stateless-C_bo-Ytq.d.ts → handler-stateless-DxYpJ_XF.d.ts} +3 -3
- package/dist/{handler-stateless-CIkKPETH.js → handler-stateless-VvrWSAVA.js} +5 -5
- package/dist/handler-stateless-VvrWSAVA.js.map +1 -0
- package/dist/{index-BRnybD6X.d.ts → index-DcSAZKsB.d.ts} +19 -31
- package/dist/index.d.ts +102 -91
- package/dist/index.js +12 -7235
- package/dist/internal_context-BlxFEWfn.d.ts +19 -0
- package/dist/internal_context.d.ts +10 -4
- package/dist/internal_context.js +1 -10
- package/dist/{client-invoker-BNSZxAkv.d.ts → invoker-CG0_p_Wq.d.ts} +2 -2
- package/dist/{client-invoker-VNZ7X0nn.js → invoker-CHMnoxIA.js} +2 -2
- package/dist/invoker-CHMnoxIA.js.map +1 -0
- package/dist/lifecycle/index.d.ts +48 -0
- package/dist/lifecycle/index.js +4 -0
- package/dist/mcp/{do-oauth-client-provider.d.ts → client/do-oauth-client-provider.d.ts} +1 -1
- package/dist/mcp/{do-oauth-client-provider.js → client/do-oauth-client-provider.js} +1 -1
- package/dist/mcp/client/do-oauth-client-provider.js.map +1 -0
- package/dist/mcp/client/index.d.ts +42 -0
- package/dist/mcp/{client.js → client/index.js} +1 -1
- package/dist/mcp/{x402.d.ts → client/x402.d.ts} +2 -2
- package/dist/mcp/{x402.js → client/x402.js} +2 -2
- package/dist/mcp/client/x402.js.map +1 -0
- package/dist/mcp/index.d.ts +36 -36
- package/dist/mcp/index.js +14 -16
- package/dist/mcp/index.js.map +1 -1
- package/dist/mcp/{server.d.ts → server/index.d.ts} +1 -1
- package/dist/mcp/{server.js → server/index.js} +1 -1
- package/dist/observability/ai/index.d.ts +1 -130
- package/dist/observability/ai/index.js +88 -433
- package/dist/observability/ai/index.js.map +1 -1
- package/dist/observability/index.d.ts +4 -4
- package/dist/observability/index.js +3 -50
- package/dist/observability/index.js.map +1 -1
- package/dist/{wire-types-CU9rLoeS.js → protocol-B0nh6KNf.js} +20 -66
- package/dist/protocol-B0nh6KNf.js.map +1 -0
- package/dist/react.d.ts +4 -4
- package/dist/react.js +6 -9
- package/dist/react.js.map +1 -1
- package/dist/schedule.d.ts +25 -94
- package/dist/schedule.js +1 -98
- package/dist/schedule.js.map +1 -1
- package/dist/scheduler-CR9RHGos.js +857 -0
- package/dist/scheduler-CR9RHGos.js.map +1 -0
- package/dist/scheduler-DQoTGoAW.d.ts +224 -0
- package/dist/schedules/index.d.ts +22 -0
- package/dist/schedules/index.js +2 -0
- package/dist/schedules/parser.d.ts +79 -0
- package/dist/schedules/parser.js +103 -0
- package/dist/schedules/parser.js.map +1 -0
- package/dist/serializable.d.ts +1 -1
- package/dist/sql-error-CPY-GXyI.d.ts +12 -0
- package/dist/sql-error.d.ts +2 -0
- package/dist/sql-error.js +16 -0
- package/dist/sql-error.js.map +1 -0
- package/dist/src-5W6JNKVb.js +6613 -0
- package/dist/src-5W6JNKVb.js.map +1 -0
- package/dist/sub-routing.d.ts +18 -6
- package/dist/sub-routing.js +92 -2
- package/dist/sub-routing.js.map +1 -1
- package/dist/wire-types-CnMt6_HR.js +47 -0
- package/dist/wire-types-CnMt6_HR.js.map +1 -0
- package/dist/workflow-types.d.ts +25 -25
- package/dist/workflow-types.js.map +1 -1
- package/dist/workflows.d.ts +22 -22
- package/dist/workflows.js +2 -1
- package/dist/workflows.js.map +1 -1
- package/dist/ws-chat-transport-UNRIS2xl.d.ts +184 -0
- package/dist/ws-chat-transport-rWwta645.js +698 -0
- package/dist/ws-chat-transport-rWwta645.js.map +1 -0
- package/docs/adding-to-existing-project.md +4 -2
- package/docs/agent-class.md +29 -87
- package/docs/agent-tools.md +29 -0
- package/docs/browse-the-web.md +16 -1
- package/docs/chat-agents.md +16 -13
- package/docs/client-sdk.md +12 -8
- package/docs/configuration.md +7 -1
- package/docs/cross-domain-authentication.md +7 -35
- package/docs/durable-execution.md +1 -1
- package/docs/email.md +2 -13
- package/docs/http-websockets.md +1 -11
- package/docs/human-in-the-loop.md +16 -13
- package/docs/index.md +1 -0
- package/docs/lifecycle.md +323 -0
- package/docs/long-running-agents.md +13 -15
- package/docs/mcp-client.md +55 -0
- package/docs/mcp-servers.md +6 -0
- package/docs/mcp-transports.md +18 -12
- package/docs/migration-to-ai-sdk-v5.md +2 -2
- package/docs/migration-to-ai-sdk-v6.md +5 -1
- package/docs/observability.md +33 -77
- package/docs/resumable-streaming.md +1 -1
- package/docs/routing.md +27 -0
- package/docs/scheduling.md +175 -15
- package/docs/server-driven-messages.md +1 -1
- package/docs/sub-agents.md +47 -2
- package/docs/webhooks.md +109 -136
- package/docs/workflows.md +9 -1
- package/package.json +41 -23
- package/dist/cli/index.d.ts +0 -1
- package/dist/cli/index.js +0 -26
- package/dist/cli/index.js.map +0 -1
- package/dist/client-invoker-VNZ7X0nn.js.map +0 -1
- package/dist/client-zqKcsyFa.js.map +0 -1
- package/dist/connector-KEJnl6e5.js.map +0 -1
- package/dist/handler-stateless-CIkKPETH.js.map +0 -1
- package/dist/index.js.map +0 -1
- package/dist/internal_context-Dg4Cgjcu.d.ts +0 -37
- package/dist/internal_context.js.map +0 -1
- package/dist/mcp/client.d.ts +0 -42
- package/dist/mcp/do-oauth-client-provider.js.map +0 -1
- package/dist/mcp/x402.js.map +0 -1
- package/dist/wire-types-CU9rLoeS.js.map +0 -1
- package/dist/workflow-types-Baz_PO5v.d.ts +0 -280
|
@@ -1,5 +1,6 @@
|
|
|
1
|
-
import { __DO_NOT_USE_WILL_BREAK__agentContext } from "../../
|
|
2
|
-
import
|
|
1
|
+
import { t as __DO_NOT_USE_WILL_BREAK__agentContext } from "../../current-agent-DhoDkSnH.js";
|
|
2
|
+
import "../../internal_context.js";
|
|
3
|
+
import { r as writeSpanAttributes, t as tracer } from "../../cloudflare-Dzvc7V2N.js";
|
|
3
4
|
import { AsyncLocalStorage } from "node:async_hooks";
|
|
4
5
|
//#region src/observability/ai/read.ts
|
|
5
6
|
/** Narrows an unknown value to a string. */
|
|
@@ -38,7 +39,6 @@ function readNestedTokenField(value, key) {
|
|
|
38
39
|
const TraceAttribute = {
|
|
39
40
|
Cloudflare: {
|
|
40
41
|
AIGatewayLogID: "cloudflare.ai_gateway.log.id",
|
|
41
|
-
CallID: "cloudflare.agents.call.id",
|
|
42
42
|
IntegrationName: "cloudflare.agents.integration.name",
|
|
43
43
|
MetadataPrefix: "cloudflare.agents.metadata.",
|
|
44
44
|
OperationName: "cloudflare.agents.operation.name",
|
|
@@ -190,17 +190,22 @@ function metadataAttributes(metadata, passthroughPrefix = TraceAttribute.Cloudfl
|
|
|
190
190
|
function operationSpanName(agentName) {
|
|
191
191
|
return spanName(TraceAttribute.GenAI.OperationNameValueInvokeAgent, agentName);
|
|
192
192
|
}
|
|
193
|
+
function semanticContextAttributes(context) {
|
|
194
|
+
return {
|
|
195
|
+
[TraceAttribute.GenAI.AgentID]: context?.agentId,
|
|
196
|
+
[TraceAttribute.GenAI.AgentName]: context?.agentName,
|
|
197
|
+
[TraceAttribute.GenAI.AgentVersion]: context?.agentVersion,
|
|
198
|
+
[TraceAttribute.GenAI.ConversationID]: context?.conversationId
|
|
199
|
+
};
|
|
200
|
+
}
|
|
193
201
|
/** Builds the root span for an SDK operation such as generateText or streamText. */
|
|
194
202
|
function operationSpan(input) {
|
|
195
203
|
return {
|
|
196
204
|
attributes: {
|
|
197
205
|
...input.attributes,
|
|
198
|
-
[TraceAttribute.Cloudflare.IntegrationName]:
|
|
206
|
+
[TraceAttribute.Cloudflare.IntegrationName]: "ai-sdk",
|
|
199
207
|
[TraceAttribute.Cloudflare.OperationName]: input.operation,
|
|
200
|
-
|
|
201
|
-
[TraceAttribute.GenAI.AgentName]: input.context?.agentName,
|
|
202
|
-
[TraceAttribute.GenAI.AgentVersion]: input.context?.agentVersion,
|
|
203
|
-
[TraceAttribute.GenAI.ConversationID]: input.context?.conversationId,
|
|
208
|
+
...semanticContextAttributes(input.context),
|
|
204
209
|
[TraceAttribute.GenAI.OperationName]: TraceAttribute.GenAI.OperationNameValueInvokeAgent,
|
|
205
210
|
[TraceAttribute.GenAI.ProviderName]: normalizeProviderName(input.provider),
|
|
206
211
|
...requestAttributes(input.request, input.model)
|
|
@@ -213,8 +218,9 @@ function modelCallSpan(input) {
|
|
|
213
218
|
return {
|
|
214
219
|
attributes: {
|
|
215
220
|
...input.attributes,
|
|
216
|
-
[TraceAttribute.Cloudflare.IntegrationName]:
|
|
221
|
+
[TraceAttribute.Cloudflare.IntegrationName]: "ai-sdk",
|
|
217
222
|
[TraceAttribute.Cloudflare.OperationName]: input.operation,
|
|
223
|
+
...semanticContextAttributes(input.context),
|
|
218
224
|
[TraceAttribute.GenAI.OperationName]: TraceAttribute.GenAI.OperationNameValueChat,
|
|
219
225
|
[TraceAttribute.GenAI.ProviderName]: normalizeProviderName(input.provider),
|
|
220
226
|
...requestAttributes(input.request, input.model)
|
|
@@ -240,8 +246,9 @@ function requestAttributes(request, model) {
|
|
|
240
246
|
function toolCallSpan(input) {
|
|
241
247
|
return {
|
|
242
248
|
attributes: {
|
|
243
|
-
[TraceAttribute.Cloudflare.IntegrationName]:
|
|
249
|
+
[TraceAttribute.Cloudflare.IntegrationName]: "ai-sdk",
|
|
244
250
|
[TraceAttribute.Cloudflare.OperationName]: input.operation,
|
|
251
|
+
...semanticContextAttributes(input.context),
|
|
245
252
|
[TraceAttribute.GenAI.OperationName]: TraceAttribute.GenAI.OperationNameValueExecuteTool,
|
|
246
253
|
[TraceAttribute.GenAI.ToolCallID]: input.toolCallId,
|
|
247
254
|
[TraceAttribute.GenAI.ToolName]: input.toolName,
|
|
@@ -257,6 +264,7 @@ function toolApprovalSpan(input) {
|
|
|
257
264
|
[TraceAttribute.Cloudflare.IntegrationName]: "ai-sdk",
|
|
258
265
|
[TraceAttribute.Cloudflare.OperationName]: "tool.approval",
|
|
259
266
|
[TraceAttribute.Cloudflare.ToolApprovalState]: input.state,
|
|
267
|
+
...semanticContextAttributes(input.context),
|
|
260
268
|
[TraceAttribute.GenAI.OperationName]: TraceAttribute.GenAI.OperationNameValueExecuteTool,
|
|
261
269
|
[TraceAttribute.GenAI.ToolCallID]: input.toolCallId,
|
|
262
270
|
[TraceAttribute.GenAI.ToolName]: input.toolName,
|
|
@@ -291,14 +299,14 @@ function totalTokens(usage) {
|
|
|
291
299
|
return usage?.inputTokens !== void 0 && usage.outputTokens !== void 0 ? usage.inputTokens + usage.outputTokens : void 0;
|
|
292
300
|
}
|
|
293
301
|
//#endregion
|
|
294
|
-
//#region src/observability/ai/
|
|
302
|
+
//#region src/observability/ai/wrapper/extract.ts
|
|
295
303
|
function finishAttributesFromResult(result, options = {}) {
|
|
296
304
|
return finishAttributes({
|
|
297
305
|
aiGatewayLogId: options.aiGatewayLogId,
|
|
298
|
-
finishReason: extractFinishReason
|
|
306
|
+
finishReason: extractFinishReason(result),
|
|
299
307
|
response: options.includeResponse ? extractResponseInfo(result) : void 0,
|
|
300
308
|
toolCallCount: extractToolCallCount(result),
|
|
301
|
-
usage:
|
|
309
|
+
usage: extractAISDKTokenUsage(result)
|
|
302
310
|
});
|
|
303
311
|
}
|
|
304
312
|
function extractRequestSummary(params, operation) {
|
|
@@ -314,7 +322,7 @@ function extractRequestSummary(params, operation) {
|
|
|
314
322
|
topP: readNumber(params.topP)
|
|
315
323
|
};
|
|
316
324
|
}
|
|
317
|
-
/** Extracts model identity from an AI SDK
|
|
325
|
+
/** Extracts model identity from an AI SDK model object. */
|
|
318
326
|
function extractModelInfo(value) {
|
|
319
327
|
if (typeof value === "string") return value.length > 0 ? {
|
|
320
328
|
modelId: value,
|
|
@@ -331,13 +339,11 @@ function extractModelInfo(value) {
|
|
|
331
339
|
};
|
|
332
340
|
}
|
|
333
341
|
/**
|
|
334
|
-
* Extracts token usage from an AI SDK
|
|
335
|
-
*
|
|
336
|
-
*
|
|
337
|
-
* where `inputTokens`/`outputTokens` may be plain numbers or nested objects
|
|
338
|
-
* like `{ total, cacheRead, cacheWrite }` / `{ total, reasoning }`.
|
|
342
|
+
* Extracts token usage from an AI SDK result or stream chunk across supported
|
|
343
|
+
* majors. Token counts may be plain numbers or nested objects such as
|
|
344
|
+
* `{ total, cacheRead, cacheWrite }` / `{ total, reasoning }`.
|
|
339
345
|
*/
|
|
340
|
-
function
|
|
346
|
+
function extractAISDKTokenUsage(value) {
|
|
341
347
|
if (typeof value !== "object" || value === null) return;
|
|
342
348
|
const record = value;
|
|
343
349
|
const raw = record.totalUsage ?? record.usage;
|
|
@@ -365,9 +371,9 @@ function extractToolCallCount(value) {
|
|
|
365
371
|
return Array.isArray(toolCalls) && toolCalls.length > 0 ? toolCalls.length : void 0;
|
|
366
372
|
}
|
|
367
373
|
/**
|
|
368
|
-
* Reads a finish reason from an AI SDK
|
|
374
|
+
* Reads a finish reason from an AI SDK result or `finish`-type stream chunk.
|
|
369
375
|
*/
|
|
370
|
-
function extractFinishReason
|
|
376
|
+
function extractFinishReason(value) {
|
|
371
377
|
if (typeof value !== "object" || value === null) return;
|
|
372
378
|
const finishReason = value.finishReason;
|
|
373
379
|
if (typeof finishReason === "string") return finishReason;
|
|
@@ -805,7 +811,7 @@ function byteLength(value) {
|
|
|
805
811
|
return new TextEncoder().encode(value).length;
|
|
806
812
|
}
|
|
807
813
|
//#endregion
|
|
808
|
-
//#region src/observability/ai/
|
|
814
|
+
//#region src/observability/ai/wrapper/streams.ts
|
|
809
815
|
function finishWhenStreamCompletes(result, span, options = {}) {
|
|
810
816
|
return patchStreamFields(result, {
|
|
811
817
|
onComplete: (summary) => {
|
|
@@ -1043,8 +1049,8 @@ function createStreamState(hooks, startedAtMs, initialAIGatewayLogId, storeMessa
|
|
|
1043
1049
|
if (isErrorChunk(chunk)) observedError = { cause: chunk.error };
|
|
1044
1050
|
if (isAbortChunk(chunk)) observedAbort = true;
|
|
1045
1051
|
if (isToolCallChunk(chunk)) toolCallCount += 1;
|
|
1046
|
-
finishReason = extractFinishReason
|
|
1047
|
-
usage =
|
|
1052
|
+
finishReason = extractFinishReason(chunk) ?? finishReason;
|
|
1053
|
+
usage = extractAISDKTokenUsage(chunk) ?? usage;
|
|
1048
1054
|
response = extractResponseInfo(chunk) ?? response;
|
|
1049
1055
|
}
|
|
1050
1056
|
};
|
|
@@ -1087,8 +1093,8 @@ function isAsyncIterable$1(value) {
|
|
|
1087
1093
|
return typeof value === "object" && value !== null && Symbol.asyncIterator in value && typeof value[Symbol.asyncIterator] === "function";
|
|
1088
1094
|
}
|
|
1089
1095
|
//#endregion
|
|
1090
|
-
//#region src/observability/ai/
|
|
1091
|
-
function wrapModel(tracer, wrapLanguageModel, model, parentOperation, storeMessages, boundToInvocation = false) {
|
|
1096
|
+
//#region src/observability/ai/wrapper/model.ts
|
|
1097
|
+
function wrapModel(tracer, wrapLanguageModel, model, parentOperation, storeMessages, context, boundToInvocation = false) {
|
|
1092
1098
|
if (!wrapLanguageModel) return model;
|
|
1093
1099
|
if (typeof model !== "object" || model === null) return model;
|
|
1094
1100
|
const modelInfo = extractModelInfo(model);
|
|
@@ -1097,7 +1103,7 @@ function wrapModel(tracer, wrapLanguageModel, model, parentOperation, storeMessa
|
|
|
1097
1103
|
model: aiGatewayLog.model,
|
|
1098
1104
|
middleware: {
|
|
1099
1105
|
wrapGenerate: async ({ doGenerate, params }) => {
|
|
1100
|
-
const span = modelCallSpanForModel("doGenerate", modelInfo, params, parentOperation, storeMessages);
|
|
1106
|
+
const span = modelCallSpanForModel("doGenerate", modelInfo, params, parentOperation, storeMessages, context);
|
|
1101
1107
|
return tracer.withSpan(span.name, span.attributes, async (modelCall) => {
|
|
1102
1108
|
aiGatewayLog.reset();
|
|
1103
1109
|
try {
|
|
@@ -1117,7 +1123,7 @@ function wrapModel(tracer, wrapLanguageModel, model, parentOperation, storeMessa
|
|
|
1117
1123
|
}, boundToInvocation ? { boundToInvocation: true } : void 0);
|
|
1118
1124
|
},
|
|
1119
1125
|
wrapStream: async ({ doStream, params }) => {
|
|
1120
|
-
const span = modelCallSpanForModel("doStream", modelInfo, params, parentOperation, storeMessages);
|
|
1126
|
+
const span = modelCallSpanForModel("doStream", modelInfo, params, parentOperation, storeMessages, context);
|
|
1121
1127
|
return tracer.openSpan(span.name, span.attributes, async (modelCall) => {
|
|
1122
1128
|
aiGatewayLog.reset();
|
|
1123
1129
|
try {
|
|
@@ -1143,10 +1149,10 @@ function wrapModel(tracer, wrapLanguageModel, model, parentOperation, storeMessa
|
|
|
1143
1149
|
function recordAIGatewayLogOnError(span, cause, capturedLogId) {
|
|
1144
1150
|
writeSpanAttributes(span, aiGatewayLogAttributes(extractAIGatewayLogId(cause) ?? capturedLogId));
|
|
1145
1151
|
}
|
|
1146
|
-
function modelCallSpanForModel(operation, model, params, parentOperation, storeMessages) {
|
|
1152
|
+
function modelCallSpanForModel(operation, model, params, parentOperation, storeMessages, context) {
|
|
1147
1153
|
const record = typeof params === "object" && params !== null ? params : {};
|
|
1148
1154
|
const span = modelCallSpan({
|
|
1149
|
-
|
|
1155
|
+
context,
|
|
1150
1156
|
model: model?.modelId,
|
|
1151
1157
|
operation,
|
|
1152
1158
|
provider: model?.provider,
|
|
@@ -1161,29 +1167,29 @@ function modelCallSpanForModel(operation, model, params, parentOperation, storeM
|
|
|
1161
1167
|
};
|
|
1162
1168
|
}
|
|
1163
1169
|
//#endregion
|
|
1164
|
-
//#region src/observability/ai/
|
|
1165
|
-
function wrapTools(tracer, tools, storeTools, boundToInvocation = false, approvedToolCalls) {
|
|
1170
|
+
//#region src/observability/ai/wrapper/tools.ts
|
|
1171
|
+
function wrapTools(tracer, tools, storeTools, context, boundToInvocation = false, approvedToolCalls) {
|
|
1166
1172
|
if (typeof tools !== "object" || tools === null) return tools;
|
|
1167
1173
|
const toolRecord = tools;
|
|
1168
1174
|
const wrappedTools = {};
|
|
1169
|
-
for (const [toolName, tool] of Object.entries(toolRecord)) wrappedTools[toolName] = wrapTool(tracer, toolName, tool, storeTools, boundToInvocation, approvedToolCalls);
|
|
1175
|
+
for (const [toolName, tool] of Object.entries(toolRecord)) wrappedTools[toolName] = wrapTool(tracer, toolName, tool, storeTools, context, boundToInvocation, approvedToolCalls);
|
|
1170
1176
|
return wrappedTools;
|
|
1171
1177
|
}
|
|
1172
|
-
function wrapTool(tracer, toolName, tool, storeTools, boundToInvocation, approvedToolCalls) {
|
|
1178
|
+
function wrapTool(tracer, toolName, tool, storeTools, context, boundToInvocation, approvedToolCalls) {
|
|
1173
1179
|
if (typeof tool !== "object" || tool === null) return tool;
|
|
1174
1180
|
const toolRecord = tool;
|
|
1175
1181
|
const hasExecute = typeof toolRecord.execute === "function";
|
|
1176
1182
|
const hasApproval = typeof toolRecord.needsApproval === "boolean" || typeof toolRecord.needsApproval === "function";
|
|
1177
1183
|
if (!hasExecute && !hasApproval) return tool;
|
|
1178
1184
|
const wrappedTool = Object.assign(Object.create(Object.getPrototypeOf(tool)), tool);
|
|
1179
|
-
if (hasApproval) wrapApprovalCheck(tracer, wrappedTool, toolRecord, tool, toolName, boundToInvocation);
|
|
1185
|
+
if (hasApproval) wrapApprovalCheck(tracer, wrappedTool, toolRecord, tool, toolName, context, boundToInvocation);
|
|
1180
1186
|
if (!hasExecute) return wrappedTool;
|
|
1181
1187
|
const execute = toolRecord.execute;
|
|
1182
1188
|
if (typeof execute !== "function") return wrappedTool;
|
|
1183
1189
|
const originalExecute = execute.bind(tool);
|
|
1184
1190
|
wrappedTool.execute = (...args) => {
|
|
1185
1191
|
const span = toolCallSpan({
|
|
1186
|
-
|
|
1192
|
+
context,
|
|
1187
1193
|
operation: "tool.execute",
|
|
1188
1194
|
toolCallId: extractToolCallId(args[1]),
|
|
1189
1195
|
toolName
|
|
@@ -1196,7 +1202,7 @@ function wrapTool(tracer, toolName, tool, storeTools, boundToInvocation, approve
|
|
|
1196
1202
|
const inSpanContext = AsyncLocalStorage.snapshot();
|
|
1197
1203
|
const toolCallId = extractToolCallId(args[1]);
|
|
1198
1204
|
if (approvalResponseForOptions(args[1], toolCallId)?.approved === true || toolCallId !== void 0 && approvedToolCalls?.get(toolCallId) === toolName) {
|
|
1199
|
-
recordApprovalChild(tracer, toolName, toolCallId, "approved", boundToInvocation);
|
|
1205
|
+
recordApprovalChild(tracer, toolName, toolCallId, "approved", context, boundToInvocation);
|
|
1200
1206
|
if (toolCallId !== void 0) approvedToolCalls?.delete(toolCallId);
|
|
1201
1207
|
}
|
|
1202
1208
|
const result = originalExecute(...args);
|
|
@@ -1209,55 +1215,56 @@ function wrapTool(tracer, toolName, tool, storeTools, boundToInvocation, approve
|
|
|
1209
1215
|
};
|
|
1210
1216
|
return wrappedTool;
|
|
1211
1217
|
}
|
|
1212
|
-
function wrapApprovalCheck(tracer, wrappedTool, toolRecord, tool, toolName, boundToInvocation) {
|
|
1218
|
+
function wrapApprovalCheck(tracer, wrappedTool, toolRecord, tool, toolName, context, boundToInvocation) {
|
|
1213
1219
|
const approval = toolRecord.needsApproval;
|
|
1214
1220
|
const original = typeof approval === "function" ? approval.bind(tool) : void 0;
|
|
1215
1221
|
wrappedTool.needsApproval = (...args) => {
|
|
1216
1222
|
const result = original ? original(...args) : approval;
|
|
1217
1223
|
const recordRequested = (needed) => {
|
|
1218
1224
|
const toolCallId = extractToolCallId(args[1]);
|
|
1219
|
-
if (needed === true && !hasApprovalResponse(args[1], toolCallId)) recordApprovalSegment(tracer, toolName, toolCallId, "requested", boundToInvocation);
|
|
1225
|
+
if (needed === true && !hasApprovalResponse(args[1], toolCallId)) recordApprovalSegment(tracer, toolName, toolCallId, "requested", context, boundToInvocation);
|
|
1220
1226
|
return needed;
|
|
1221
1227
|
};
|
|
1222
1228
|
return isPromiseLike(result) ? Promise.resolve(result).then(recordRequested) : recordRequested(result);
|
|
1223
1229
|
};
|
|
1224
1230
|
}
|
|
1225
1231
|
/** Instruments AI SDK v7's top-level tool approval policy. */
|
|
1226
|
-
function wrapToolApprovalPolicy(tracer, policy, approvedToolCalls, boundToInvocation = false) {
|
|
1232
|
+
function wrapToolApprovalPolicy(tracer, policy, approvedToolCalls, context, boundToInvocation = false) {
|
|
1227
1233
|
if (typeof policy === "function") return (...args) => {
|
|
1228
|
-
const toolCall = recordValue
|
|
1229
|
-
return observePolicyResult(policy(...args), readString(toolCall?.toolName) ?? "tool", readString(toolCall?.toolCallId), tracer, approvedToolCalls, boundToInvocation);
|
|
1234
|
+
const toolCall = recordValue(recordValue(args[0])?.toolCall);
|
|
1235
|
+
return observePolicyResult(policy(...args), readString(toolCall?.toolName) ?? "tool", readString(toolCall?.toolCallId), tracer, approvedToolCalls, context, boundToInvocation);
|
|
1230
1236
|
};
|
|
1231
1237
|
if (typeof policy !== "object" || policy === null) return policy;
|
|
1232
|
-
return Object.fromEntries(Object.entries(policy).map(([toolName, setting]) => [toolName, (...args) => observePolicyResult(typeof setting === "function" ? setting(...args) : setting, toolName, extractToolCallId(args[1]), tracer, approvedToolCalls, boundToInvocation)]));
|
|
1238
|
+
return Object.fromEntries(Object.entries(policy).map(([toolName, setting]) => [toolName, (...args) => observePolicyResult(typeof setting === "function" ? setting(...args) : setting, toolName, extractToolCallId(args[1]), tracer, approvedToolCalls, context, boundToInvocation)]));
|
|
1233
1239
|
}
|
|
1234
|
-
function observePolicyResult(result, toolName, toolCallId, tracer, approvedToolCalls, boundToInvocation = false) {
|
|
1240
|
+
function observePolicyResult(result, toolName, toolCallId, tracer, approvedToolCalls, context, boundToInvocation = false) {
|
|
1235
1241
|
const observe = (status) => {
|
|
1236
1242
|
if (toolCallId === void 0) return status;
|
|
1237
|
-
const type = typeof status === "string" ? status : readString(recordValue
|
|
1243
|
+
const type = typeof status === "string" ? status : readString(recordValue(status)?.type);
|
|
1238
1244
|
if (type === "approved") approvedToolCalls.set(toolCallId, toolName);
|
|
1239
|
-
else if (type === "user-approval" || type === "denied") recordApprovalSegment(tracer, toolName, toolCallId, type === "denied" ? "denied" : "requested", boundToInvocation);
|
|
1245
|
+
else if (type === "user-approval" || type === "denied") recordApprovalSegment(tracer, toolName, toolCallId, type === "denied" ? "denied" : "requested", context, boundToInvocation);
|
|
1240
1246
|
return status;
|
|
1241
1247
|
};
|
|
1242
1248
|
return isPromiseLike(result) ? Promise.resolve(result).then(observe) : observe(result);
|
|
1243
1249
|
}
|
|
1244
1250
|
/** Records denied responses, whose tool never reaches execute(). */
|
|
1245
|
-
function recordDeniedApprovalResponses(tracer, messages) {
|
|
1246
|
-
for (const response of approvalResponses(messages)) if (!response.approved) recordApprovalSegment(tracer, response.toolName, response.toolCallId, "denied");
|
|
1251
|
+
function recordDeniedApprovalResponses(tracer, messages, context) {
|
|
1252
|
+
for (const response of approvalResponses(messages)) if (!response.approved) recordApprovalSegment(tracer, response.toolName, response.toolCallId, "denied", context);
|
|
1247
1253
|
}
|
|
1248
|
-
function recordApprovalSegment(tracer, toolName, toolCallId, state, boundToInvocation = false) {
|
|
1254
|
+
function recordApprovalSegment(tracer, toolName, toolCallId, state, context, boundToInvocation = false) {
|
|
1249
1255
|
const tool = toolCallSpan({
|
|
1250
|
-
|
|
1256
|
+
context,
|
|
1251
1257
|
operation: "tool.approval",
|
|
1252
1258
|
toolCallId,
|
|
1253
1259
|
toolName
|
|
1254
1260
|
});
|
|
1255
1261
|
tracer.withSpan(tool.name, tool.attributes, () => {
|
|
1256
|
-
recordApprovalChild(tracer, toolName, toolCallId, state, boundToInvocation);
|
|
1262
|
+
recordApprovalChild(tracer, toolName, toolCallId, state, context, boundToInvocation);
|
|
1257
1263
|
}, boundToInvocation ? { boundToInvocation: true } : void 0);
|
|
1258
1264
|
}
|
|
1259
|
-
function recordApprovalChild(tracer, toolName, toolCallId, state, boundToInvocation = false) {
|
|
1265
|
+
function recordApprovalChild(tracer, toolName, toolCallId, state, context, boundToInvocation = false) {
|
|
1260
1266
|
const approval = toolApprovalSpan({
|
|
1267
|
+
context,
|
|
1261
1268
|
state,
|
|
1262
1269
|
toolCallId,
|
|
1263
1270
|
toolName
|
|
@@ -1361,19 +1368,19 @@ function extractToolCallId(options) {
|
|
|
1361
1368
|
function isAsyncIterable(value) {
|
|
1362
1369
|
return typeof value === "object" && value !== null && Symbol.asyncIterator in value && typeof value[Symbol.asyncIterator] === "function";
|
|
1363
1370
|
}
|
|
1364
|
-
function recordValue
|
|
1371
|
+
function recordValue(value) {
|
|
1365
1372
|
return typeof value === "object" && value !== null ? value : void 0;
|
|
1366
1373
|
}
|
|
1367
1374
|
function isPromiseLike(value) {
|
|
1368
1375
|
return value !== null && value !== void 0 && (typeof value === "object" || typeof value === "function") && "then" in value && typeof value.then === "function";
|
|
1369
1376
|
}
|
|
1370
1377
|
//#endregion
|
|
1371
|
-
//#region src/observability/ai/
|
|
1378
|
+
//#region src/observability/ai/wrapper/wrap.ts
|
|
1372
1379
|
/**
|
|
1373
|
-
* Wraps an AI SDK namespace object with
|
|
1374
|
-
* shape and overloaded call signatures.
|
|
1380
|
+
* Wraps an AI SDK namespace object with tracing while preserving its public
|
|
1381
|
+
* shape and overloaded call signatures across supported majors.
|
|
1375
1382
|
*/
|
|
1376
|
-
function
|
|
1383
|
+
function createAISDKWrapper(ai, instrumentation) {
|
|
1377
1384
|
const target = isModuleNamespace(ai) ? Object.setPrototypeOf({}, ai) : ai;
|
|
1378
1385
|
const wrapperCache = /* @__PURE__ */ new Map();
|
|
1379
1386
|
return new Proxy(target, { get(proxyTarget, property, receiver) {
|
|
@@ -1381,7 +1388,7 @@ function createAISDKV6Wrapper(ai, instrumentation) {
|
|
|
1381
1388
|
if (isWrappedOperationName(property) && typeof original === "function") {
|
|
1382
1389
|
let wrapper = wrapperCache.get(property);
|
|
1383
1390
|
if (!wrapper) {
|
|
1384
|
-
wrapper = createOperationWrapper(property,
|
|
1391
|
+
wrapper = createOperationWrapper(property, toAISDKOperation(original), readWrapLanguageModel(ai), instrumentation);
|
|
1385
1392
|
wrapperCache.set(property, wrapper);
|
|
1386
1393
|
}
|
|
1387
1394
|
return wrapper;
|
|
@@ -1394,7 +1401,7 @@ function readWrapLanguageModel(ai) {
|
|
|
1394
1401
|
if (typeof value !== "function") return;
|
|
1395
1402
|
return value;
|
|
1396
1403
|
}
|
|
1397
|
-
function
|
|
1404
|
+
function toAISDKOperation(value) {
|
|
1398
1405
|
return value;
|
|
1399
1406
|
}
|
|
1400
1407
|
function isModuleNamespace(value) {
|
|
@@ -1414,17 +1421,18 @@ function createOperationWrapper(operationName, operation, wrapLanguageModel, ins
|
|
|
1414
1421
|
storeMessages: instrumentation.options?.storeMessages === true,
|
|
1415
1422
|
storeTools: instrumentation.options?.storeTools === true
|
|
1416
1423
|
};
|
|
1417
|
-
if (isStreamOperation
|
|
1424
|
+
if (isStreamOperation(operationName)) return (params, ...args) => {
|
|
1418
1425
|
const boundToInvocation = isAISDKInvocationBounded(params);
|
|
1419
1426
|
return instrumentation.tracer.openSpan(operationSpanName(agentNameForCall(params)), {}, (operationSpan) => {
|
|
1420
1427
|
if (!operationSpan.isTraced) {
|
|
1421
1428
|
operationSpan.finish();
|
|
1422
1429
|
return operation(params, ...args);
|
|
1423
1430
|
}
|
|
1431
|
+
const context = semanticContext(params);
|
|
1424
1432
|
writeSpanAttributes(operationSpan, operationSpanForCall(operationName, extractModelInfo(params.model), params, instrumentation.options).attributes);
|
|
1425
|
-
recordDeniedApprovalResponses(instrumentation.tracer, params.messages);
|
|
1433
|
+
recordDeniedApprovalResponses(instrumentation.tracer, params.messages, context);
|
|
1426
1434
|
const startedAtMs = Date.now();
|
|
1427
|
-
const result = operation(operationParamsForCall(params, operationName, wrapLanguageModel, instrumentation.tracer, storage, boundToInvocation), ...args);
|
|
1435
|
+
const result = operation(operationParamsForCall(params, operationName, wrapLanguageModel, instrumentation.tracer, storage, context, boundToInvocation), ...args);
|
|
1428
1436
|
const hasModelSpan = canWrapModel(wrapLanguageModel, params.model);
|
|
1429
1437
|
return finishWhenStreamCompletes(result, operationSpan, {
|
|
1430
1438
|
includeResponse: !hasModelSpan,
|
|
@@ -1436,9 +1444,10 @@ function createOperationWrapper(operationName, operation, wrapLanguageModel, ins
|
|
|
1436
1444
|
const boundToInvocation = isAISDKInvocationBounded(params);
|
|
1437
1445
|
return instrumentation.tracer.withSpan(operationSpanName(agentNameForCall(params)), {}, async (operationSpan) => {
|
|
1438
1446
|
if (!operationSpan.isTraced) return operation(params, ...args);
|
|
1447
|
+
const context = semanticContext(params);
|
|
1439
1448
|
writeSpanAttributes(operationSpan, operationSpanForCall(operationName, extractModelInfo(params.model), params, instrumentation.options).attributes);
|
|
1440
|
-
recordDeniedApprovalResponses(instrumentation.tracer, params.messages);
|
|
1441
|
-
const result = await operation(operationParamsForCall(params, operationName, wrapLanguageModel, instrumentation.tracer, storage, boundToInvocation), ...args);
|
|
1449
|
+
recordDeniedApprovalResponses(instrumentation.tracer, params.messages, context);
|
|
1450
|
+
const result = await operation(operationParamsForCall(params, operationName, wrapLanguageModel, instrumentation.tracer, storage, context, boundToInvocation), ...args);
|
|
1442
1451
|
operationSpan.finish(finishAttributesFromResult(result, { includeResponse: !canWrapModel(wrapLanguageModel, params.model) }));
|
|
1443
1452
|
return result;
|
|
1444
1453
|
}, boundToInvocation ? { boundToInvocation: true } : void 0);
|
|
@@ -1454,21 +1463,21 @@ function agentNameForCall(params) {
|
|
|
1454
1463
|
const telemetry = telemetryOptions(params);
|
|
1455
1464
|
const metadata = telemetryMetadata(params);
|
|
1456
1465
|
const runtimeContext = runtimeContextRecord(params);
|
|
1457
|
-
return metadataValue
|
|
1466
|
+
return metadataValue(metadata, "agentName", "gen_ai.agent.name") ?? metadataValue(runtimeContext, "agentName", "gen_ai.agent.name") ?? readString(telemetry?.functionId);
|
|
1458
1467
|
}
|
|
1459
|
-
function operationParamsForCall(params, operationName, wrapLanguageModel, tracer, storage, boundToInvocation = false) {
|
|
1468
|
+
function operationParamsForCall(params, operationName, wrapLanguageModel, tracer, storage, context, boundToInvocation = false) {
|
|
1460
1469
|
const approvedToolCalls = /* @__PURE__ */ new Map();
|
|
1461
1470
|
return {
|
|
1462
1471
|
...params,
|
|
1463
|
-
...shouldWrapTools(operationName) && params.tools !== void 0 ? { tools: wrapTools(tracer, params.tools, storage.storeTools, boundToInvocation, approvedToolCalls) } : {},
|
|
1464
|
-
...params.toolApproval !== void 0 ? { toolApproval: wrapToolApprovalPolicy(tracer, params.toolApproval, approvedToolCalls) } : {},
|
|
1465
|
-
...params.model !== void 0 ? { model: wrapModel(tracer, wrapLanguageModel, params.model, operationName, storage.storeMessages, boundToInvocation) } : {}
|
|
1472
|
+
...shouldWrapTools(operationName) && params.tools !== void 0 ? { tools: wrapTools(tracer, params.tools, storage.storeTools, context, boundToInvocation, approvedToolCalls) } : {},
|
|
1473
|
+
...params.toolApproval !== void 0 ? { toolApproval: wrapToolApprovalPolicy(tracer, params.toolApproval, approvedToolCalls, context, boundToInvocation) } : {},
|
|
1474
|
+
...params.model !== void 0 ? { model: wrapModel(tracer, wrapLanguageModel, params.model, operationName, storage.storeMessages, context, boundToInvocation) } : {}
|
|
1466
1475
|
};
|
|
1467
1476
|
}
|
|
1468
1477
|
function canWrapModel(wrapLanguageModel, model) {
|
|
1469
1478
|
return wrapLanguageModel !== void 0 && typeof model === "object" && model !== null;
|
|
1470
1479
|
}
|
|
1471
|
-
function isStreamOperation
|
|
1480
|
+
function isStreamOperation(operationName) {
|
|
1472
1481
|
return operationName === "streamObject" || operationName === "streamText";
|
|
1473
1482
|
}
|
|
1474
1483
|
function shouldWrapTools(operationName) {
|
|
@@ -1485,7 +1494,6 @@ function operationSpanForCall(operation, model, params, options) {
|
|
|
1485
1494
|
...contextAttributes(params, options)
|
|
1486
1495
|
},
|
|
1487
1496
|
context: semanticContext(params),
|
|
1488
|
-
integration: "ai-sdk",
|
|
1489
1497
|
model: model?.modelId,
|
|
1490
1498
|
operation,
|
|
1491
1499
|
provider: model?.provider,
|
|
@@ -1573,15 +1581,15 @@ function semanticContext(params) {
|
|
|
1573
1581
|
const telemetry = telemetryOptions(params);
|
|
1574
1582
|
const metadata = telemetryMetadata(params);
|
|
1575
1583
|
const runtimeContext = runtimeContextRecord(params);
|
|
1576
|
-
const fromContext = (key, semanticKey) => isExcludedFromContext(params, key) ? void 0 : metadataValue
|
|
1584
|
+
const fromContext = (key, semanticKey) => isExcludedFromContext(params, key) ? void 0 : metadataValue(runtimeContext, key, semanticKey);
|
|
1577
1585
|
return {
|
|
1578
|
-
agentId: metadataValue
|
|
1579
|
-
agentName: metadataValue
|
|
1580
|
-
agentVersion: metadataValue
|
|
1581
|
-
conversationId: metadataValue
|
|
1586
|
+
agentId: metadataValue(metadata, "agentId", "gen_ai.agent.id") ?? fromContext("agentId", "gen_ai.agent.id"),
|
|
1587
|
+
agentName: metadataValue(metadata, "agentName", "gen_ai.agent.name") ?? fromContext("agentName", "gen_ai.agent.name") ?? readString(telemetry?.functionId),
|
|
1588
|
+
agentVersion: metadataValue(metadata, "agentVersion", "gen_ai.agent.version") ?? fromContext("agentVersion", "gen_ai.agent.version"),
|
|
1589
|
+
conversationId: metadataValue(metadata, "conversationId", "gen_ai.conversation.id") ?? fromContext("conversationId", "gen_ai.conversation.id")
|
|
1582
1590
|
};
|
|
1583
1591
|
}
|
|
1584
|
-
function metadataValue
|
|
1592
|
+
function metadataValue(metadata, key, semanticKey) {
|
|
1585
1593
|
return readString(metadata?.[key] ?? metadata?.[semanticKey]);
|
|
1586
1594
|
}
|
|
1587
1595
|
/**
|
|
@@ -1604,370 +1612,17 @@ function isAISDKInvocationBounded(params) {
|
|
|
1604
1612
|
return params[invocationBounded] === true || __DO_NOT_USE_WILL_BREAK__agentContext.getStore()?.connection !== void 0;
|
|
1605
1613
|
}
|
|
1606
1614
|
//#endregion
|
|
1607
|
-
//#region src/observability/ai/v7/extract.ts
|
|
1608
|
-
/** Extracts the safe operation name from an AI SDK v7 operation id. */
|
|
1609
|
-
function operationNameFromId(operationId) {
|
|
1610
|
-
const value = readString(operationId);
|
|
1611
|
-
if (value === void 0) return "ai-sdk";
|
|
1612
|
-
return value.startsWith("ai.") ? value.slice(3) : value;
|
|
1613
|
-
}
|
|
1614
|
-
/**
|
|
1615
|
-
* Extracts safe GenAI semantic context from an AI SDK v7 event. The AI SDK's
|
|
1616
|
-
* canonical OpenTelemetry projection maps `functionId` to agent name. v7 has
|
|
1617
|
-
* no telemetry metadata bag, so other identity fields come from the SDK-
|
|
1618
|
-
* filtered runtime context only when the caller explicitly includes them.
|
|
1619
|
-
*/
|
|
1620
|
-
function semanticContextFromEvent(event) {
|
|
1621
|
-
const record = eventRecord(event);
|
|
1622
|
-
const runtimeContext = typeof record.runtimeContext === "object" && record.runtimeContext !== null ? record.runtimeContext : void 0;
|
|
1623
|
-
return {
|
|
1624
|
-
agentId: metadataValue(runtimeContext, "agentId", "gen_ai.agent.id"),
|
|
1625
|
-
agentName: metadataValue(runtimeContext, "agentName", "gen_ai.agent.name") ?? readString(record.functionId),
|
|
1626
|
-
agentVersion: metadataValue(runtimeContext, "agentVersion", "gen_ai.agent.version"),
|
|
1627
|
-
conversationId: metadataValue(runtimeContext, "conversationId", "gen_ai.conversation.id")
|
|
1628
|
-
};
|
|
1629
|
-
}
|
|
1630
|
-
/** Extracts safe request settings from an AI SDK v7 event. */
|
|
1631
|
-
function requestSummaryFromEvent(event, operationName) {
|
|
1632
|
-
const record = eventRecord(event);
|
|
1633
|
-
return {
|
|
1634
|
-
frequencyPenalty: readNumber(record.frequencyPenalty),
|
|
1635
|
-
maxTokens: readNumber(record.maxOutputTokens ?? record.maxTokens),
|
|
1636
|
-
outputType: operationName === "generateObject" || operationName === "streamObject" ? "json" : "text",
|
|
1637
|
-
presencePenalty: readNumber(record.presencePenalty),
|
|
1638
|
-
seed: readNumber(record.seed),
|
|
1639
|
-
stream: operationName === "streamText" || operationName === "streamObject",
|
|
1640
|
-
temperature: readNumber(record.temperature),
|
|
1641
|
-
topK: readNumber(record.topK),
|
|
1642
|
-
topP: readNumber(record.topP)
|
|
1643
|
-
};
|
|
1644
|
-
}
|
|
1645
|
-
/** Extracts safe finish attributes from an AI SDK v7 result-like event. */
|
|
1646
|
-
function finishAttributesFromEvent(event, options = {}) {
|
|
1647
|
-
const record = eventRecord(event);
|
|
1648
|
-
return finishAttributes({
|
|
1649
|
-
aiGatewayLogId: options.includeAIGatewayLog ? extractAIGatewayLogId(record) : void 0,
|
|
1650
|
-
finishReason: extractFinishReason(record),
|
|
1651
|
-
response: options.includeResponse ? responseSummaryFromEvent(record) : void 0,
|
|
1652
|
-
timeToFirstChunkSeconds: options.includePerformance ? timeToFirstChunkSeconds(record) : void 0,
|
|
1653
|
-
usage: tokenUsageFromEvent(record)
|
|
1654
|
-
});
|
|
1655
|
-
}
|
|
1656
|
-
/** Builds correlation attributes for AI SDK v7 callback ids. */
|
|
1657
|
-
function correlationAttributes(input) {
|
|
1658
|
-
return {
|
|
1659
|
-
[TraceAttribute.Cloudflare.CallID]: input.callId,
|
|
1660
|
-
[TraceAttribute.GenAI.ToolCallID]: input.toolCallId
|
|
1661
|
-
};
|
|
1662
|
-
}
|
|
1663
|
-
function metadataValue(metadata, key, semanticKey) {
|
|
1664
|
-
return readString(metadata?.[key] ?? metadata?.[semanticKey]);
|
|
1665
|
-
}
|
|
1666
|
-
function eventRecord(event) {
|
|
1667
|
-
return event;
|
|
1668
|
-
}
|
|
1669
|
-
function extractFinishReason(event) {
|
|
1670
|
-
const finishReason = event.finishReason;
|
|
1671
|
-
if (typeof finishReason === "string") return finishReason;
|
|
1672
|
-
if (typeof finishReason === "object" && finishReason !== null) return readString(finishReason.unified);
|
|
1673
|
-
}
|
|
1674
|
-
function responseSummaryFromEvent(event) {
|
|
1675
|
-
const response = typeof event.response === "object" && event.response !== null ? event.response : void 0;
|
|
1676
|
-
const id = readString(event.responseId ?? response?.id);
|
|
1677
|
-
const model = readString(event.responseModel ?? response?.modelId ?? response?.model);
|
|
1678
|
-
if (id === void 0 && model === void 0) return;
|
|
1679
|
-
return {
|
|
1680
|
-
...id !== void 0 ? { id } : {},
|
|
1681
|
-
...model !== void 0 ? { model } : {}
|
|
1682
|
-
};
|
|
1683
|
-
}
|
|
1684
|
-
function tokenUsageFromEvent(event) {
|
|
1685
|
-
const raw = event.totalUsage ?? event.usage;
|
|
1686
|
-
if (typeof raw !== "object" || raw === null) return;
|
|
1687
|
-
const usage = raw;
|
|
1688
|
-
const inputTokens = readTokenCount(usage.inputTokens);
|
|
1689
|
-
const outputTokens = readTokenCount(usage.outputTokens);
|
|
1690
|
-
const cacheReadInputTokens = readNestedTokenField(usage.inputTokenDetails, "cacheReadTokens") ?? readNestedTokenField(usage.inputTokens, "cacheRead") ?? readNumber(usage.cachedInputTokens);
|
|
1691
|
-
const cacheCreationInputTokens = readNestedTokenField(usage.inputTokenDetails, "cacheWriteTokens") ?? readNestedTokenField(usage.inputTokens, "cacheWrite");
|
|
1692
|
-
const reasoningTokens = readNestedTokenField(usage.outputTokenDetails, "reasoningTokens") ?? readNestedTokenField(usage.outputTokens, "reasoning") ?? readNumber(usage.reasoningTokens);
|
|
1693
|
-
if (inputTokens === void 0 && outputTokens === void 0 && cacheReadInputTokens === void 0 && cacheCreationInputTokens === void 0 && reasoningTokens === void 0) return;
|
|
1694
|
-
return {
|
|
1695
|
-
...cacheCreationInputTokens !== void 0 ? { cacheCreationInputTokens } : {},
|
|
1696
|
-
...cacheReadInputTokens !== void 0 ? { cacheReadInputTokens } : {},
|
|
1697
|
-
...inputTokens !== void 0 ? { inputTokens } : {},
|
|
1698
|
-
...outputTokens !== void 0 ? { outputTokens } : {},
|
|
1699
|
-
...reasoningTokens !== void 0 ? { reasoningTokens } : {}
|
|
1700
|
-
};
|
|
1701
|
-
}
|
|
1702
|
-
function timeToFirstChunkSeconds(event) {
|
|
1703
|
-
const milliseconds = readNumber((typeof event.performance === "object" && event.performance !== null ? event.performance : void 0)?.timeToFirstOutputMs);
|
|
1704
|
-
return milliseconds === void 0 ? void 0 : milliseconds / 1e3;
|
|
1705
|
-
}
|
|
1706
|
-
//#endregion
|
|
1707
|
-
//#region src/observability/ai/v7/telemetry.ts
|
|
1708
|
-
/**
|
|
1709
|
-
* Creates an AI SDK v7 `Telemetry` object that projects callback events into
|
|
1710
|
-
* Cloudflare-compatible GenAI spans without recording raw prompts or outputs.
|
|
1711
|
-
*/
|
|
1712
|
-
function createAISDKV7Telemetry(instrumentation) {
|
|
1713
|
-
const storeMessages = instrumentation.options?.storeMessages === true;
|
|
1714
|
-
const storeTools = instrumentation.options?.storeTools === true;
|
|
1715
|
-
const operations = /* @__PURE__ */ new Map();
|
|
1716
|
-
const modelSpans = /* @__PURE__ */ new Map();
|
|
1717
|
-
const toolSpans = /* @__PURE__ */ new Map();
|
|
1718
|
-
const toolSpanKey = (callId, toolCallId) => `${callId}:${toolCallId}`;
|
|
1719
|
-
const finishOperation = (event) => {
|
|
1720
|
-
const state = operations.get(event.callId);
|
|
1721
|
-
if (!state) return;
|
|
1722
|
-
finishOpenModelSpans(event.callId, void 0, modelSpans, instrumentation.tracer);
|
|
1723
|
-
finishOpenToolSpans(event.callId, void 0, toolSpans, instrumentation.tracer);
|
|
1724
|
-
state.span.finish(finishAttributesFromEvent(event));
|
|
1725
|
-
operations.delete(event.callId);
|
|
1726
|
-
};
|
|
1727
|
-
return {
|
|
1728
|
-
onStart(event) {
|
|
1729
|
-
const operationName = supportedOperationName(operationNameFromId(event.operationId));
|
|
1730
|
-
if (!operationName) return;
|
|
1731
|
-
const span = operationSpan({
|
|
1732
|
-
attributes: {
|
|
1733
|
-
...correlationAttributes({ callId: event.callId }),
|
|
1734
|
-
...runtimeContextAttributes(event.runtimeContext)
|
|
1735
|
-
},
|
|
1736
|
-
context: semanticContextFromEvent(event),
|
|
1737
|
-
integration: "ai-sdk",
|
|
1738
|
-
model: readString(event.modelId),
|
|
1739
|
-
operation: operationName,
|
|
1740
|
-
provider: readString(event.provider),
|
|
1741
|
-
request: requestSummaryFromEvent(event, operationName)
|
|
1742
|
-
});
|
|
1743
|
-
const operation = instrumentation.tracer.openSpan(span.name, span.attributes, (activeSpan) => activeSpan);
|
|
1744
|
-
operations.set(event.callId, {
|
|
1745
|
-
callId: event.callId,
|
|
1746
|
-
operationName,
|
|
1747
|
-
span: operation
|
|
1748
|
-
});
|
|
1749
|
-
},
|
|
1750
|
-
onLanguageModelCallStart(event) {
|
|
1751
|
-
const state = operations.get(event.callId);
|
|
1752
|
-
if (!state) return;
|
|
1753
|
-
const span = modelCallSpan({
|
|
1754
|
-
attributes: {
|
|
1755
|
-
...correlationAttributes({ callId: event.callId }),
|
|
1756
|
-
...inputMessageAttributes(event, storeMessages)
|
|
1757
|
-
},
|
|
1758
|
-
integration: "ai-sdk",
|
|
1759
|
-
model: readString(event.modelId),
|
|
1760
|
-
operation: isStreamOperation(state.operationName) ? "doStream" : "doGenerate",
|
|
1761
|
-
provider: readString(event.provider),
|
|
1762
|
-
request: requestSummaryFromEvent(event, state.operationName)
|
|
1763
|
-
});
|
|
1764
|
-
const spans = modelSpans.get(event.callId) ?? [];
|
|
1765
|
-
spans.push({ spanSpec: span });
|
|
1766
|
-
modelSpans.set(event.callId, spans);
|
|
1767
|
-
},
|
|
1768
|
-
onLanguageModelCallEnd(event) {
|
|
1769
|
-
const state = shiftModelSpan(modelSpans, event.callId);
|
|
1770
|
-
if (!state) return;
|
|
1771
|
-
(state.span ?? instrumentation.tracer.openSpan(state.spanSpec.name, state.spanSpec.attributes, (activeSpan) => activeSpan)).finish({
|
|
1772
|
-
...finishAttributesFromEvent(event, {
|
|
1773
|
-
includeAIGatewayLog: true,
|
|
1774
|
-
includePerformance: true,
|
|
1775
|
-
includeResponse: true
|
|
1776
|
-
}),
|
|
1777
|
-
...outputMessageAttributes(event, storeMessages)
|
|
1778
|
-
});
|
|
1779
|
-
},
|
|
1780
|
-
onToolExecutionStart(event) {
|
|
1781
|
-
const toolCallId = readString(event.toolCall.toolCallId);
|
|
1782
|
-
if (toolCallId === void 0 || !operations.has(event.callId)) return;
|
|
1783
|
-
const toolName = readString(event.toolCall.toolName) ?? "tool";
|
|
1784
|
-
const span = toolCallSpan({
|
|
1785
|
-
integration: "ai-sdk",
|
|
1786
|
-
operation: "tool.execute",
|
|
1787
|
-
toolName
|
|
1788
|
-
});
|
|
1789
|
-
toolSpans.set(toolSpanKey(event.callId, toolCallId), {
|
|
1790
|
-
callId: event.callId,
|
|
1791
|
-
spanSpec: {
|
|
1792
|
-
name: span.name,
|
|
1793
|
-
attributes: {
|
|
1794
|
-
...span.attributes,
|
|
1795
|
-
...correlationAttributes({
|
|
1796
|
-
callId: event.callId,
|
|
1797
|
-
toolCallId
|
|
1798
|
-
}),
|
|
1799
|
-
...toolInputAttributes(event.toolCall.input, storeTools),
|
|
1800
|
-
...toolContextAttributes(toolName, event.toolContext)
|
|
1801
|
-
}
|
|
1802
|
-
}
|
|
1803
|
-
});
|
|
1804
|
-
},
|
|
1805
|
-
onToolExecutionEnd(event) {
|
|
1806
|
-
const toolCallId = readString(event.toolCall.toolCallId);
|
|
1807
|
-
if (toolCallId === void 0) return;
|
|
1808
|
-
const state = toolSpans.get(toolSpanKey(event.callId, toolCallId));
|
|
1809
|
-
if (!state) return;
|
|
1810
|
-
const span = state.span ?? instrumentation.tracer.openSpan(state.spanSpec.name, state.spanSpec.attributes, (activeSpan) => activeSpan);
|
|
1811
|
-
if (event.toolOutput?.type === "tool-error") span.fail(event.toolOutput.error);
|
|
1812
|
-
else span.finish(toolOutputAttributes(event.toolOutput?.output, storeTools));
|
|
1813
|
-
toolSpans.delete(toolSpanKey(event.callId, toolCallId));
|
|
1814
|
-
},
|
|
1815
|
-
onAbort(event) {
|
|
1816
|
-
const cause = { name: "AbortError" };
|
|
1817
|
-
finishOpenModelSpans(event.callId, cause, modelSpans, instrumentation.tracer);
|
|
1818
|
-
finishOpenToolSpans(event.callId, cause, toolSpans, instrumentation.tracer);
|
|
1819
|
-
const state = operations.get(event.callId);
|
|
1820
|
-
if (!state) return;
|
|
1821
|
-
state.span.fail(cause);
|
|
1822
|
-
operations.delete(event.callId);
|
|
1823
|
-
},
|
|
1824
|
-
onEnd: finishOperation,
|
|
1825
|
-
onError(event) {
|
|
1826
|
-
const errorEvent = eventObject(event);
|
|
1827
|
-
const callId = readString(errorEvent.callId);
|
|
1828
|
-
if (callId === void 0) return;
|
|
1829
|
-
const cause = errorEvent.error ?? event;
|
|
1830
|
-
finishOpenModelSpans(callId, cause, modelSpans, instrumentation.tracer);
|
|
1831
|
-
finishOpenToolSpans(callId, cause, toolSpans, instrumentation.tracer);
|
|
1832
|
-
const state = operations.get(callId);
|
|
1833
|
-
if (!state) return;
|
|
1834
|
-
state.span.fail(cause);
|
|
1835
|
-
operations.delete(callId);
|
|
1836
|
-
},
|
|
1837
|
-
executeLanguageModelCall(options) {
|
|
1838
|
-
const state = modelSpans.get(options.callId)?.find((candidate) => candidate.span === void 0);
|
|
1839
|
-
if (!state) return options.execute();
|
|
1840
|
-
return instrumentation.tracer.openSpan(state.spanSpec.name, state.spanSpec.attributes, (span) => {
|
|
1841
|
-
state.span = span;
|
|
1842
|
-
try {
|
|
1843
|
-
return Promise.resolve(options.execute()).catch((cause) => {
|
|
1844
|
-
writeSpanAttributes(span, aiGatewayLogAttributes(extractAIGatewayLogId(cause)));
|
|
1845
|
-
span.fail(cause);
|
|
1846
|
-
removeModelState(modelSpans, options.callId, state);
|
|
1847
|
-
throw cause;
|
|
1848
|
-
});
|
|
1849
|
-
} catch (cause) {
|
|
1850
|
-
writeSpanAttributes(span, aiGatewayLogAttributes(extractAIGatewayLogId(cause)));
|
|
1851
|
-
span.fail(cause);
|
|
1852
|
-
removeModelState(modelSpans, options.callId, state);
|
|
1853
|
-
throw cause;
|
|
1854
|
-
}
|
|
1855
|
-
});
|
|
1856
|
-
},
|
|
1857
|
-
executeTool(options) {
|
|
1858
|
-
const state = toolSpans.get(toolSpanKey(options.callId, options.toolCallId));
|
|
1859
|
-
if (!state) return options.execute();
|
|
1860
|
-
return instrumentation.tracer.openSpan(state.spanSpec.name, state.spanSpec.attributes, (span) => {
|
|
1861
|
-
state.span = span;
|
|
1862
|
-
try {
|
|
1863
|
-
return Promise.resolve(options.execute()).catch((cause) => {
|
|
1864
|
-
span.fail(cause);
|
|
1865
|
-
toolSpans.delete(toolSpanKey(options.callId, options.toolCallId));
|
|
1866
|
-
throw cause;
|
|
1867
|
-
});
|
|
1868
|
-
} catch (cause) {
|
|
1869
|
-
span.fail(cause);
|
|
1870
|
-
toolSpans.delete(toolSpanKey(options.callId, options.toolCallId));
|
|
1871
|
-
throw cause;
|
|
1872
|
-
}
|
|
1873
|
-
});
|
|
1874
|
-
}
|
|
1875
|
-
};
|
|
1876
|
-
}
|
|
1877
|
-
function supportedOperationName(operationName) {
|
|
1878
|
-
if (operationName === "generateObject" || operationName === "generateText" || operationName === "streamObject" || operationName === "streamText") return operationName;
|
|
1879
|
-
}
|
|
1880
|
-
function isStreamOperation(operationName) {
|
|
1881
|
-
return operationName === "streamObject" || operationName === "streamText";
|
|
1882
|
-
}
|
|
1883
|
-
function shiftModelSpan(spansByCallId, callId) {
|
|
1884
|
-
const spans = spansByCallId.get(callId);
|
|
1885
|
-
const span = spans?.shift();
|
|
1886
|
-
if (spans && spans.length === 0) spansByCallId.delete(callId);
|
|
1887
|
-
return span;
|
|
1888
|
-
}
|
|
1889
|
-
function removeModelState(statesByCallId, callId, state) {
|
|
1890
|
-
const states = statesByCallId.get(callId);
|
|
1891
|
-
if (!states) return;
|
|
1892
|
-
const index = states.indexOf(state);
|
|
1893
|
-
if (index !== -1) states.splice(index, 1);
|
|
1894
|
-
if (states.length === 0) statesByCallId.delete(callId);
|
|
1895
|
-
}
|
|
1896
|
-
function finishOpenModelSpans(callId, cause, spansByCallId, tracer) {
|
|
1897
|
-
const states = spansByCallId.get(callId);
|
|
1898
|
-
if (!states) return;
|
|
1899
|
-
for (const state of states) {
|
|
1900
|
-
const span = state.span ?? tracer.openSpan(state.spanSpec.name, state.spanSpec.attributes, (activeSpan) => activeSpan);
|
|
1901
|
-
if (cause === void 0) span.finish();
|
|
1902
|
-
else span.fail(cause);
|
|
1903
|
-
}
|
|
1904
|
-
spansByCallId.delete(callId);
|
|
1905
|
-
}
|
|
1906
|
-
function finishOpenToolSpans(callId, cause, spansByToolCallId, tracer) {
|
|
1907
|
-
for (const [toolCallId, state] of spansByToolCallId) {
|
|
1908
|
-
if (state.callId !== callId) continue;
|
|
1909
|
-
const span = state.span ?? tracer.openSpan(state.spanSpec.name, state.spanSpec.attributes, (activeSpan) => activeSpan);
|
|
1910
|
-
if (cause === void 0) span.finish();
|
|
1911
|
-
else span.fail(cause);
|
|
1912
|
-
spansByToolCallId.delete(toolCallId);
|
|
1913
|
-
}
|
|
1914
|
-
}
|
|
1915
|
-
function eventObject(event) {
|
|
1916
|
-
return typeof event === "object" && event !== null ? event : {};
|
|
1917
|
-
}
|
|
1918
|
-
const SEMANTIC_CONTEXT_KEYS = /* @__PURE__ */ new Set([
|
|
1919
|
-
"agentId",
|
|
1920
|
-
"agentName",
|
|
1921
|
-
"agentVersion",
|
|
1922
|
-
"conversationId",
|
|
1923
|
-
"gen_ai.agent.id",
|
|
1924
|
-
"gen_ai.agent.name",
|
|
1925
|
-
"gen_ai.agent.version",
|
|
1926
|
-
"gen_ai.conversation.id"
|
|
1927
|
-
]);
|
|
1928
|
-
function runtimeContextAttributes(runtimeContextValue) {
|
|
1929
|
-
const attributes = {};
|
|
1930
|
-
const runtimeContext = recordValue(runtimeContextValue);
|
|
1931
|
-
for (const [key, value] of Object.entries(runtimeContext ?? {})) if (!SEMANTIC_CONTEXT_KEYS.has(key) && isScalarAttributeValue(value)) attributes[key.startsWith("cloudflare.agents.") ? key : `cloudflare.agents.runtime_context.${key}`] = value;
|
|
1932
|
-
return attributes;
|
|
1933
|
-
}
|
|
1934
|
-
function toolContextAttributes(toolName, toolContextValue) {
|
|
1935
|
-
const attributes = {};
|
|
1936
|
-
const toolContext = recordValue(toolContextValue);
|
|
1937
|
-
for (const [key, value] of Object.entries(toolContext ?? {})) if (isScalarAttributeValue(value)) attributes[`cloudflare.agents.tool_context.${toolName}.${key}`] = value;
|
|
1938
|
-
return attributes;
|
|
1939
|
-
}
|
|
1940
|
-
function recordValue(value) {
|
|
1941
|
-
return typeof value === "object" && value !== null ? value : void 0;
|
|
1942
|
-
}
|
|
1943
|
-
function isScalarAttributeValue(value) {
|
|
1944
|
-
return typeof value === "string" || typeof value === "number" || typeof value === "boolean";
|
|
1945
|
-
}
|
|
1946
|
-
//#endregion
|
|
1947
1615
|
//#region src/observability/ai/index.ts
|
|
1948
|
-
const agentsAISDKTelemetryBrand = Symbol.for("cloudflare.agents.ai-sdk-telemetry");
|
|
1949
1616
|
/**
|
|
1950
1617
|
* Wraps an AI SDK namespace with tracing.
|
|
1951
1618
|
*/
|
|
1952
1619
|
function wrapAISDK(ai, options = {}) {
|
|
1953
|
-
return
|
|
1954
|
-
options,
|
|
1955
|
-
tracer
|
|
1956
|
-
});
|
|
1957
|
-
}
|
|
1958
|
-
/**
|
|
1959
|
-
* Creates an AI SDK v7 telemetry adapter for use with `registerTelemetry` or
|
|
1960
|
-
* per-call telemetry configuration.
|
|
1961
|
-
*/
|
|
1962
|
-
function createAISDKTelemetry(options = {}) {
|
|
1963
|
-
const telemetry = createAISDKV7Telemetry({
|
|
1620
|
+
return createAISDKWrapper(ai, {
|
|
1964
1621
|
options,
|
|
1965
1622
|
tracer
|
|
1966
1623
|
});
|
|
1967
|
-
Object.defineProperty(telemetry, agentsAISDKTelemetryBrand, { value: true });
|
|
1968
|
-
return telemetry;
|
|
1969
1624
|
}
|
|
1970
1625
|
//#endregion
|
|
1971
|
-
export {
|
|
1626
|
+
export { wrapAISDK };
|
|
1972
1627
|
|
|
1973
1628
|
//# sourceMappingURL=index.js.map
|