@mastra/observability 1.0.0-beta.2 → 1.0.0-beta.4
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/CHANGELOG.md +40 -0
- package/dist/index.cjs +176 -3
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.ts +1 -0
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +176 -4
- package/dist/index.js.map +1 -1
- package/dist/model-tracing.d.ts +4 -9
- package/dist/model-tracing.d.ts.map +1 -1
- package/dist/spans/base.d.ts.map +1 -1
- package/dist/tracing-options.d.ts +27 -0
- package/dist/tracing-options.d.ts.map +1 -0
- package/dist/usage.d.ts +21 -0
- package/dist/usage.d.ts.map +1 -0
- package/package.json +2 -2
package/dist/index.d.ts
CHANGED
package/dist/index.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AAGH,OAAO,EAAE,aAAa,EAAE,MAAM,WAAW,CAAC;AAG1C,cAAc,UAAU,CAAC;AAGzB,cAAc,aAAa,CAAC;AAC5B,cAAc,SAAS,CAAC;AACxB,cAAc,aAAa,CAAC;AAC5B,cAAc,mBAAmB,CAAC;AAClC,cAAc,iBAAiB,CAAC"}
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AAGH,OAAO,EAAE,aAAa,EAAE,MAAM,WAAW,CAAC;AAG1C,cAAc,UAAU,CAAC;AAGzB,cAAc,aAAa,CAAC;AAC5B,cAAc,SAAS,CAAC;AACxB,cAAc,aAAa,CAAC;AAC5B,cAAc,mBAAmB,CAAC;AAClC,cAAc,iBAAiB,CAAC;AAGhC,cAAc,mBAAmB,CAAC"}
|
package/dist/index.js
CHANGED
|
@@ -946,6 +946,58 @@ var TestExporter = class extends BaseExporter {
|
|
|
946
946
|
this.logger.info("TestExporter shutdown");
|
|
947
947
|
}
|
|
948
948
|
};
|
|
949
|
+
|
|
950
|
+
// src/usage.ts
|
|
951
|
+
function extractUsageMetrics(usage, providerMetadata) {
|
|
952
|
+
if (!usage) {
|
|
953
|
+
return {};
|
|
954
|
+
}
|
|
955
|
+
const inputDetails = {};
|
|
956
|
+
const outputDetails = {};
|
|
957
|
+
let inputTokens = usage.inputTokens;
|
|
958
|
+
const outputTokens = usage.outputTokens;
|
|
959
|
+
if (usage.cachedInputTokens) {
|
|
960
|
+
inputDetails.cacheRead = usage.cachedInputTokens;
|
|
961
|
+
}
|
|
962
|
+
if (usage.reasoningTokens) {
|
|
963
|
+
outputDetails.reasoning = usage.reasoningTokens;
|
|
964
|
+
}
|
|
965
|
+
const anthropic = providerMetadata?.anthropic;
|
|
966
|
+
if (anthropic) {
|
|
967
|
+
if (anthropic.cacheReadInputTokens) {
|
|
968
|
+
inputDetails.cacheRead = anthropic.cacheReadInputTokens;
|
|
969
|
+
}
|
|
970
|
+
if (anthropic.cacheCreationInputTokens) {
|
|
971
|
+
inputDetails.cacheWrite = anthropic.cacheCreationInputTokens;
|
|
972
|
+
}
|
|
973
|
+
if (anthropic.cacheReadInputTokens || anthropic.cacheCreationInputTokens) {
|
|
974
|
+
inputDetails.text = usage.inputTokens;
|
|
975
|
+
inputTokens = (usage.inputTokens ?? 0) + (anthropic.cacheReadInputTokens ?? 0) + (anthropic.cacheCreationInputTokens ?? 0);
|
|
976
|
+
}
|
|
977
|
+
}
|
|
978
|
+
const google = providerMetadata?.google;
|
|
979
|
+
if (google?.usageMetadata) {
|
|
980
|
+
if (google.usageMetadata.cachedContentTokenCount) {
|
|
981
|
+
inputDetails.cacheRead = google.usageMetadata.cachedContentTokenCount;
|
|
982
|
+
}
|
|
983
|
+
if (google.usageMetadata.thoughtsTokenCount) {
|
|
984
|
+
outputDetails.reasoning = google.usageMetadata.thoughtsTokenCount;
|
|
985
|
+
}
|
|
986
|
+
}
|
|
987
|
+
const result = {
|
|
988
|
+
inputTokens,
|
|
989
|
+
outputTokens
|
|
990
|
+
};
|
|
991
|
+
if (Object.keys(inputDetails).length > 0) {
|
|
992
|
+
result.inputDetails = inputDetails;
|
|
993
|
+
}
|
|
994
|
+
if (Object.keys(outputDetails).length > 0) {
|
|
995
|
+
result.outputDetails = outputDetails;
|
|
996
|
+
}
|
|
997
|
+
return result;
|
|
998
|
+
}
|
|
999
|
+
|
|
1000
|
+
// src/model-tracing.ts
|
|
949
1001
|
var ModelSpanTracker = class {
|
|
950
1002
|
#modelSpan;
|
|
951
1003
|
#currentStepSpan;
|
|
@@ -953,9 +1005,23 @@ var ModelSpanTracker = class {
|
|
|
953
1005
|
#accumulator = {};
|
|
954
1006
|
#stepIndex = 0;
|
|
955
1007
|
#chunkSequence = 0;
|
|
1008
|
+
#completionStartTime;
|
|
1009
|
+
/** Tracks tool output accumulators by toolCallId for consolidating sub-agent streams */
|
|
1010
|
+
#toolOutputAccumulators = /* @__PURE__ */ new Map();
|
|
1011
|
+
/** Tracks toolCallIds that had streaming output (to skip redundant tool-result spans) */
|
|
1012
|
+
#streamedToolCallIds = /* @__PURE__ */ new Set();
|
|
956
1013
|
constructor(modelSpan) {
|
|
957
1014
|
this.#modelSpan = modelSpan;
|
|
958
1015
|
}
|
|
1016
|
+
/**
|
|
1017
|
+
* Capture the completion start time (time to first token) when the first content chunk arrives.
|
|
1018
|
+
*/
|
|
1019
|
+
#captureCompletionStartTime() {
|
|
1020
|
+
if (this.#completionStartTime) {
|
|
1021
|
+
return;
|
|
1022
|
+
}
|
|
1023
|
+
this.#completionStartTime = /* @__PURE__ */ new Date();
|
|
1024
|
+
}
|
|
959
1025
|
/**
|
|
960
1026
|
* Get the tracing context for creating child spans.
|
|
961
1027
|
* Returns the current step span if active, otherwise the model span.
|
|
@@ -972,10 +1038,16 @@ var ModelSpanTracker = class {
|
|
|
972
1038
|
this.#modelSpan?.error(options);
|
|
973
1039
|
}
|
|
974
1040
|
/**
|
|
975
|
-
* End the generation span
|
|
1041
|
+
* End the generation span with optional raw usage data.
|
|
1042
|
+
* If usage is provided, it will be converted to UsageStats with cache token details.
|
|
976
1043
|
*/
|
|
977
1044
|
endGeneration(options) {
|
|
978
|
-
|
|
1045
|
+
const { usage, providerMetadata, ...spanOptions } = options ?? {};
|
|
1046
|
+
if (spanOptions.attributes) {
|
|
1047
|
+
spanOptions.attributes.completionStartTime = this.#completionStartTime;
|
|
1048
|
+
spanOptions.attributes.usage = extractUsageMetrics(usage, providerMetadata);
|
|
1049
|
+
}
|
|
1050
|
+
this.#modelSpan?.end(spanOptions);
|
|
979
1051
|
}
|
|
980
1052
|
/**
|
|
981
1053
|
* Update the generation span
|
|
@@ -1005,9 +1077,10 @@ var ModelSpanTracker = class {
|
|
|
1005
1077
|
#endStepSpan(payload) {
|
|
1006
1078
|
if (!this.#currentStepSpan) return;
|
|
1007
1079
|
const output = payload.output;
|
|
1008
|
-
const { usage, ...otherOutput } = output;
|
|
1080
|
+
const { usage: rawUsage, ...otherOutput } = output;
|
|
1009
1081
|
const stepResult = payload.stepResult;
|
|
1010
1082
|
const metadata = payload.metadata;
|
|
1083
|
+
const usage = extractUsageMetrics(rawUsage, metadata?.providerMetadata);
|
|
1011
1084
|
const cleanMetadata = metadata ? { ...metadata } : void 0;
|
|
1012
1085
|
if (cleanMetadata?.request) {
|
|
1013
1086
|
delete cleanMetadata.request;
|
|
@@ -1180,6 +1253,77 @@ var ModelSpanTracker = class {
|
|
|
1180
1253
|
break;
|
|
1181
1254
|
}
|
|
1182
1255
|
}
|
|
1256
|
+
/**
|
|
1257
|
+
* Handle tool-output chunks from sub-agents.
|
|
1258
|
+
* Consolidates streaming text/reasoning deltas into a single span per tool call.
|
|
1259
|
+
*/
|
|
1260
|
+
#handleToolOutputChunk(chunk) {
|
|
1261
|
+
if (chunk.type !== "tool-output") return;
|
|
1262
|
+
const payload = chunk.payload;
|
|
1263
|
+
const { output, toolCallId, toolName } = payload;
|
|
1264
|
+
let acc = this.#toolOutputAccumulators.get(toolCallId);
|
|
1265
|
+
if (!acc) {
|
|
1266
|
+
if (!this.#currentStepSpan) {
|
|
1267
|
+
this.#startStepSpan();
|
|
1268
|
+
}
|
|
1269
|
+
acc = {
|
|
1270
|
+
toolName: toolName || "unknown",
|
|
1271
|
+
toolCallId,
|
|
1272
|
+
text: "",
|
|
1273
|
+
reasoning: "",
|
|
1274
|
+
sequenceNumber: this.#chunkSequence++,
|
|
1275
|
+
// Name the span 'tool-result' for consistency (tool-call → tool-result)
|
|
1276
|
+
span: this.#currentStepSpan?.createChildSpan({
|
|
1277
|
+
name: `chunk: 'tool-result'`,
|
|
1278
|
+
type: SpanType.MODEL_CHUNK,
|
|
1279
|
+
attributes: {
|
|
1280
|
+
chunkType: "tool-result",
|
|
1281
|
+
sequenceNumber: this.#chunkSequence - 1
|
|
1282
|
+
}
|
|
1283
|
+
})
|
|
1284
|
+
};
|
|
1285
|
+
this.#toolOutputAccumulators.set(toolCallId, acc);
|
|
1286
|
+
}
|
|
1287
|
+
if (output && typeof output === "object" && "type" in output) {
|
|
1288
|
+
const innerType = output.type;
|
|
1289
|
+
switch (innerType) {
|
|
1290
|
+
case "text-delta":
|
|
1291
|
+
if (output.payload?.text) {
|
|
1292
|
+
acc.text += output.payload.text;
|
|
1293
|
+
}
|
|
1294
|
+
break;
|
|
1295
|
+
case "reasoning-delta":
|
|
1296
|
+
if (output.payload?.text) {
|
|
1297
|
+
acc.reasoning += output.payload.text;
|
|
1298
|
+
}
|
|
1299
|
+
break;
|
|
1300
|
+
case "finish":
|
|
1301
|
+
case "workflow-finish":
|
|
1302
|
+
this.#endToolOutputSpan(toolCallId);
|
|
1303
|
+
break;
|
|
1304
|
+
}
|
|
1305
|
+
}
|
|
1306
|
+
}
|
|
1307
|
+
/**
|
|
1308
|
+
* End a tool output span and clean up the accumulator
|
|
1309
|
+
*/
|
|
1310
|
+
#endToolOutputSpan(toolCallId) {
|
|
1311
|
+
const acc = this.#toolOutputAccumulators.get(toolCallId);
|
|
1312
|
+
if (!acc) return;
|
|
1313
|
+
const output = {
|
|
1314
|
+
toolCallId: acc.toolCallId,
|
|
1315
|
+
toolName: acc.toolName
|
|
1316
|
+
};
|
|
1317
|
+
if (acc.text) {
|
|
1318
|
+
output.text = acc.text;
|
|
1319
|
+
}
|
|
1320
|
+
if (acc.reasoning) {
|
|
1321
|
+
output.reasoning = acc.reasoning;
|
|
1322
|
+
}
|
|
1323
|
+
acc.span?.end({ output });
|
|
1324
|
+
this.#toolOutputAccumulators.delete(toolCallId);
|
|
1325
|
+
this.#streamedToolCallIds.add(toolCallId);
|
|
1326
|
+
}
|
|
1183
1327
|
/**
|
|
1184
1328
|
* Wraps a stream with model tracing transform to track MODEL_STEP and MODEL_CHUNK spans.
|
|
1185
1329
|
*
|
|
@@ -1190,6 +1334,13 @@ var ModelSpanTracker = class {
|
|
|
1190
1334
|
return stream.pipeThrough(
|
|
1191
1335
|
new TransformStream({
|
|
1192
1336
|
transform: (chunk, controller) => {
|
|
1337
|
+
switch (chunk.type) {
|
|
1338
|
+
case "text-delta":
|
|
1339
|
+
case "tool-call-delta":
|
|
1340
|
+
case "reasoning-delta":
|
|
1341
|
+
this.#captureCompletionStartTime();
|
|
1342
|
+
break;
|
|
1343
|
+
}
|
|
1193
1344
|
controller.enqueue(chunk);
|
|
1194
1345
|
switch (chunk.type) {
|
|
1195
1346
|
case "text-start":
|
|
@@ -1223,6 +1374,19 @@ var ModelSpanTracker = class {
|
|
|
1223
1374
|
case "start":
|
|
1224
1375
|
case "finish":
|
|
1225
1376
|
break;
|
|
1377
|
+
case "tool-output":
|
|
1378
|
+
this.#handleToolOutputChunk(chunk);
|
|
1379
|
+
break;
|
|
1380
|
+
case "tool-result": {
|
|
1381
|
+
const toolCallId = chunk.payload?.toolCallId;
|
|
1382
|
+
if (toolCallId && this.#streamedToolCallIds.has(toolCallId)) {
|
|
1383
|
+
this.#streamedToolCallIds.delete(toolCallId);
|
|
1384
|
+
break;
|
|
1385
|
+
}
|
|
1386
|
+
const { args, ...cleanPayload } = chunk.payload || {};
|
|
1387
|
+
this.#createEventSpan(chunk.type, cleanPayload);
|
|
1388
|
+
break;
|
|
1389
|
+
}
|
|
1226
1390
|
// Default: auto-create event span for all other chunk types
|
|
1227
1391
|
default: {
|
|
1228
1392
|
let outputPayload = chunk.payload;
|
|
@@ -1434,6 +1598,9 @@ function deepClean(value, options = {}, _seen = /* @__PURE__ */ new WeakSet(), _
|
|
|
1434
1598
|
return "[Circular]";
|
|
1435
1599
|
}
|
|
1436
1600
|
_seen.add(value);
|
|
1601
|
+
if (value instanceof Date) {
|
|
1602
|
+
return value;
|
|
1603
|
+
}
|
|
1437
1604
|
if (Array.isArray(value)) {
|
|
1438
1605
|
return value.map((item) => deepClean(item, options, _seen, _depth + 1));
|
|
1439
1606
|
}
|
|
@@ -2322,6 +2489,11 @@ var Observability = class extends MastraBase {
|
|
|
2322
2489
|
}
|
|
2323
2490
|
};
|
|
2324
2491
|
|
|
2325
|
-
|
|
2492
|
+
// src/tracing-options.ts
|
|
2493
|
+
function buildTracingOptions(...updaters) {
|
|
2494
|
+
return updaters.reduce((opts, updater) => updater(opts), {});
|
|
2495
|
+
}
|
|
2496
|
+
|
|
2497
|
+
export { BaseExporter, BaseObservabilityInstance, BaseSpan, CloudExporter, ConsoleExporter, DefaultExporter, DefaultObservabilityInstance, DefaultSpan, ModelSpanTracker, NoOpSpan, Observability, SamplingStrategyType, SensitiveDataFilter, TestExporter, buildTracingOptions, deepClean, getExternalParentId, observabilityConfigValueSchema, observabilityInstanceConfigSchema, observabilityRegistryConfigSchema, samplingStrategySchema };
|
|
2326
2498
|
//# sourceMappingURL=index.js.map
|
|
2327
2499
|
//# sourceMappingURL=index.js.map
|