@axlsdk/axl 0.24.1 → 0.24.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/index.cjs +186 -85
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +17 -15
- package/dist/index.d.ts +17 -15
- package/dist/index.js +186 -85
- package/dist/index.js.map +1 -1
- package/package.json +2 -2
package/dist/index.js
CHANGED
|
@@ -120,12 +120,14 @@ function preserveErrorCause(error, cause) {
|
|
|
120
120
|
});
|
|
121
121
|
return error;
|
|
122
122
|
}
|
|
123
|
+
var TOOL_FAILURE_MARKER = /* @__PURE__ */ Symbol.for("axl.toolFailure.v1");
|
|
123
124
|
var ToolFailure = class extends AxlError {
|
|
124
125
|
modelMessage;
|
|
125
126
|
constructor(options) {
|
|
126
127
|
super(options.code ?? "TOOL_FAILURE", options.message);
|
|
127
128
|
this.name = "ToolFailure";
|
|
128
129
|
this.modelMessage = options.modelMessage;
|
|
130
|
+
Object.defineProperty(this, TOOL_FAILURE_MARKER, { value: true });
|
|
129
131
|
if (options.cause !== void 0) {
|
|
130
132
|
Object.defineProperty(this, "cause", {
|
|
131
133
|
configurable: true,
|
|
@@ -135,6 +137,13 @@ var ToolFailure = class extends AxlError {
|
|
|
135
137
|
}
|
|
136
138
|
}
|
|
137
139
|
};
|
|
140
|
+
function isToolFailureError(error) {
|
|
141
|
+
try {
|
|
142
|
+
return error instanceof ToolFailure || typeof error === "object" && error !== null && error[TOOL_FAILURE_MARKER] === true && typeof error.modelMessage === "string";
|
|
143
|
+
} catch {
|
|
144
|
+
return false;
|
|
145
|
+
}
|
|
146
|
+
}
|
|
138
147
|
var ToolModelOutputError = class extends AxlError {
|
|
139
148
|
toolName;
|
|
140
149
|
cause;
|
|
@@ -316,7 +325,7 @@ var sharedGuard = typeof installedGuard === "object" && installedGuard !== null
|
|
|
316
325
|
var buildPath = typeof __AXL_BUILD_PATH__ === "string" ? __AXL_BUILD_PATH__ : "<source>";
|
|
317
326
|
var thisCopy = {
|
|
318
327
|
path: buildPath.startsWith("file:") ? fileURLToPath(buildPath) : buildPath,
|
|
319
|
-
version: true ? "0.24.
|
|
328
|
+
version: true ? "0.24.2" : "unknown"
|
|
320
329
|
};
|
|
321
330
|
function warnCrossCopy(other, joined) {
|
|
322
331
|
if (other === thisCopy) return;
|
|
@@ -417,10 +426,16 @@ var AccountingScope = class {
|
|
|
417
426
|
reasons = /* @__PURE__ */ new Map();
|
|
418
427
|
breakdown = { generation: 0, judging: 0, external: 0 };
|
|
419
428
|
provenance = /* @__PURE__ */ new Map();
|
|
429
|
+
modelCalls = /* @__PURE__ */ new Map();
|
|
430
|
+
modelTiming = /* @__PURE__ */ new Map();
|
|
431
|
+
diagnosticTokens = { input: 0, output: 0, reasoning: 0 };
|
|
432
|
+
agentCalls = 0;
|
|
433
|
+
captureTimingSamples;
|
|
420
434
|
constructor(options) {
|
|
421
435
|
this.parent = options.parent;
|
|
422
436
|
this.purpose = options.purpose;
|
|
423
437
|
this.admission = options.admission;
|
|
438
|
+
this.captureTimingSamples = options.captureTimingSamples === true;
|
|
424
439
|
}
|
|
425
440
|
get isFinalized() {
|
|
426
441
|
return this.finalized;
|
|
@@ -449,7 +464,7 @@ var AccountingScope = class {
|
|
|
449
464
|
else this.byKind.delete(op.kind);
|
|
450
465
|
this.denied += 1;
|
|
451
466
|
}
|
|
452
|
-
recordSettled(op, cost, provenance, usage) {
|
|
467
|
+
recordSettled(op, cost, provenance, usage, timing) {
|
|
453
468
|
this.seen.add(op.id);
|
|
454
469
|
this.openOps.delete(op.id);
|
|
455
470
|
this.settled += 1;
|
|
@@ -458,13 +473,57 @@ var AccountingScope = class {
|
|
|
458
473
|
else this.breakdown[op.purpose] += cost;
|
|
459
474
|
this.provenance.set(provenance, (this.provenance.get(provenance) ?? 0) + cost);
|
|
460
475
|
if (usage) this.addUsage(usage);
|
|
476
|
+
this.recordAgentCall(op, usage, timing);
|
|
461
477
|
}
|
|
462
|
-
recordUnknown(op, reason, usage) {
|
|
478
|
+
recordUnknown(op, reason, usage, timing) {
|
|
463
479
|
this.seen.add(op.id);
|
|
464
480
|
this.openOps.delete(op.id);
|
|
465
481
|
this.unknown += 1;
|
|
466
482
|
this.reasons.set(reason, (this.reasons.get(reason) ?? 0) + 1);
|
|
467
483
|
if (usage) this.addUsage(usage);
|
|
484
|
+
this.recordAgentCall(op, usage, timing);
|
|
485
|
+
}
|
|
486
|
+
recordAgentCall(op, usage, timing) {
|
|
487
|
+
if (!op.agentCall) return;
|
|
488
|
+
this.agentCalls++;
|
|
489
|
+
const model = op.diagnosticModelUri ?? op.model;
|
|
490
|
+
if (!model) return;
|
|
491
|
+
this.modelCalls.set(model, (this.modelCalls.get(model) ?? 0) + 1);
|
|
492
|
+
if (usage) {
|
|
493
|
+
const finite = (value) => typeof value === "number" && Number.isFinite(value) ? value : 0;
|
|
494
|
+
this.diagnosticTokens.input += finite(usage.inputTokens);
|
|
495
|
+
this.diagnosticTokens.output += finite(usage.outputTokens);
|
|
496
|
+
this.diagnosticTokens.reasoning += finite(usage.reasoningTokens);
|
|
497
|
+
}
|
|
498
|
+
if (!timing) return;
|
|
499
|
+
let bucket = this.modelTiming.get(model);
|
|
500
|
+
if (!bucket) {
|
|
501
|
+
bucket = {
|
|
502
|
+
calls: 0,
|
|
503
|
+
queuedMs: 0,
|
|
504
|
+
retryMs: 0,
|
|
505
|
+
wireMs: 0,
|
|
506
|
+
...this.captureTimingSamples ? { samples: [] } : {}
|
|
507
|
+
};
|
|
508
|
+
this.modelTiming.set(model, bucket);
|
|
509
|
+
}
|
|
510
|
+
bucket.calls++;
|
|
511
|
+
bucket.queuedMs += timing.queuedMs;
|
|
512
|
+
bucket.retryMs += timing.retryMs;
|
|
513
|
+
bucket.wireMs += timing.wireMs;
|
|
514
|
+
bucket.samples?.push(timing);
|
|
515
|
+
if (timing.firstTokenMs != null) {
|
|
516
|
+
bucket.firstTokenMs = (bucket.firstTokenMs ?? 0) + timing.firstTokenMs;
|
|
517
|
+
bucket.firstTokenCalls = (bucket.firstTokenCalls ?? 0) + 1;
|
|
518
|
+
}
|
|
519
|
+
}
|
|
520
|
+
toDiagnostics() {
|
|
521
|
+
return {
|
|
522
|
+
modelCallCounts: Object.fromEntries(this.modelCalls),
|
|
523
|
+
tokens: { ...this.diagnosticTokens },
|
|
524
|
+
agentCalls: this.agentCalls,
|
|
525
|
+
modelTiming: Object.fromEntries(this.modelTiming)
|
|
526
|
+
};
|
|
468
527
|
}
|
|
469
528
|
hasSeen(id) {
|
|
470
529
|
return this.seen.has(id);
|
|
@@ -536,14 +595,14 @@ function settleOperationUp(start, op, outcome) {
|
|
|
536
595
|
if (scope.isFinalized) return;
|
|
537
596
|
switch (outcome.outcome) {
|
|
538
597
|
case "settled":
|
|
539
|
-
scope.recordSettled(op, outcome.cost, outcome.provenance, outcome.usage);
|
|
598
|
+
scope.recordSettled(op, outcome.cost, outcome.provenance, outcome.usage, outcome.timing);
|
|
540
599
|
if (scope.admission && !chargedControllers.has(scope.admission)) {
|
|
541
600
|
chargedControllers.add(scope.admission);
|
|
542
601
|
recordSpend(scope.admission, outcome.cost);
|
|
543
602
|
}
|
|
544
603
|
break;
|
|
545
604
|
case "unknown":
|
|
546
|
-
scope.recordUnknown(op, outcome.reason, outcome.usage);
|
|
605
|
+
scope.recordUnknown(op, outcome.reason, outcome.usage, outcome.timing);
|
|
547
606
|
break;
|
|
548
607
|
case "retracted":
|
|
549
608
|
scope.recordRetracted(op);
|
|
@@ -595,6 +654,8 @@ function openOperation(descriptor) {
|
|
|
595
654
|
kind: descriptor.kind,
|
|
596
655
|
purpose: scope.purpose,
|
|
597
656
|
model: descriptor.model,
|
|
657
|
+
diagnosticModelUri: descriptor.diagnosticModelUri,
|
|
658
|
+
agentCall: descriptor.agentCall === true,
|
|
598
659
|
dispatched: false,
|
|
599
660
|
dispatchObservable: false
|
|
600
661
|
};
|
|
@@ -635,25 +696,31 @@ function openOperation(descriptor) {
|
|
|
635
696
|
outcome: "settled",
|
|
636
697
|
cost: input.cost,
|
|
637
698
|
provenance: input.provenance ?? "adapter_reported",
|
|
638
|
-
usage: input.usage
|
|
699
|
+
usage: input.usage,
|
|
700
|
+
timing: input.timing
|
|
639
701
|
});
|
|
640
702
|
return;
|
|
641
703
|
}
|
|
642
704
|
if (input.cost !== void 0 || input.usage !== void 0) {
|
|
643
|
-
finish({
|
|
705
|
+
finish({
|
|
706
|
+
outcome: "unknown",
|
|
707
|
+
reason: "unpriced_model",
|
|
708
|
+
usage: input.usage,
|
|
709
|
+
timing: input.timing
|
|
710
|
+
});
|
|
644
711
|
return;
|
|
645
712
|
}
|
|
646
|
-
handle.settleFailure();
|
|
713
|
+
handle.settleFailure(void 0, input.timing);
|
|
647
714
|
},
|
|
648
715
|
settleUnknown(reason, usage) {
|
|
649
716
|
finish({ outcome: "unknown", reason, usage });
|
|
650
717
|
},
|
|
651
|
-
settleFailure(usage) {
|
|
718
|
+
settleFailure(usage, timing) {
|
|
652
719
|
if (op.dispatchObservable && !op.dispatched) {
|
|
653
|
-
finish({ outcome: "settled", cost: 0, provenance: "adapter_reported", usage });
|
|
720
|
+
finish({ outcome: "settled", cost: 0, provenance: "adapter_reported", usage, timing });
|
|
654
721
|
return;
|
|
655
722
|
}
|
|
656
|
-
finish({ outcome: "unknown", reason: "usage_missing", usage });
|
|
723
|
+
finish({ outcome: "unknown", reason: "usage_missing", usage, timing });
|
|
657
724
|
},
|
|
658
725
|
run(fn) {
|
|
659
726
|
return runWithDispatchAdmission(handle.dispatchAdmission, fn);
|
|
@@ -666,7 +733,8 @@ async function runInAccountingScope(options, fn) {
|
|
|
666
733
|
const scope = new AccountingScope({
|
|
667
734
|
parent,
|
|
668
735
|
purpose: options.purpose ?? parent?.purpose ?? "generation",
|
|
669
|
-
admission: options.admission
|
|
736
|
+
admission: options.admission,
|
|
737
|
+
captureTimingSamples: options.captureTimingSamples
|
|
670
738
|
});
|
|
671
739
|
const inheritedGuard = sharedGuard.storage.getStore();
|
|
672
740
|
const enclosingGuard = inheritedGuard && (inheritedGuard.isActive?.() ?? true) ? inheritedGuard : void 0;
|
|
@@ -684,7 +752,8 @@ async function runInAccountingScope(options, fn) {
|
|
|
684
752
|
"The active @axlsdk/axl accounting scope uses an incompatible loaded copy; paid work was refused before dispatch."
|
|
685
753
|
)
|
|
686
754
|
},
|
|
687
|
-
accounting: scope.toAccounting()
|
|
755
|
+
accounting: scope.toAccounting(),
|
|
756
|
+
diagnostics: scope.toDiagnostics()
|
|
688
757
|
};
|
|
689
758
|
}
|
|
690
759
|
const markUninstrumented = () => {
|
|
@@ -708,10 +777,18 @@ async function runInAccountingScope(options, fn) {
|
|
|
708
777
|
() => accountingStorage.run(scope, fn)
|
|
709
778
|
);
|
|
710
779
|
scope.finalize();
|
|
711
|
-
return {
|
|
780
|
+
return {
|
|
781
|
+
outcome: { status: "fulfilled", value },
|
|
782
|
+
accounting: scope.toAccounting(),
|
|
783
|
+
diagnostics: scope.toDiagnostics()
|
|
784
|
+
};
|
|
712
785
|
} catch (error) {
|
|
713
786
|
scope.finalize();
|
|
714
|
-
return {
|
|
787
|
+
return {
|
|
788
|
+
outcome: { status: "rejected", error },
|
|
789
|
+
accounting: scope.toAccounting(),
|
|
790
|
+
diagnostics: scope.toDiagnostics()
|
|
791
|
+
};
|
|
715
792
|
}
|
|
716
793
|
}
|
|
717
794
|
function validateReportedCost(amountUsd) {
|
|
@@ -1090,10 +1167,12 @@ function toolArgumentIssues(error) {
|
|
|
1090
1167
|
}
|
|
1091
1168
|
return [{ path: [], code: "invalid_arguments", message: "Tool arguments are invalid." }];
|
|
1092
1169
|
}
|
|
1093
|
-
var TOOL_INTERNALS = /* @__PURE__ */
|
|
1170
|
+
var TOOL_INTERNALS = /* @__PURE__ */ Symbol.for("axl.tool.internals.v1");
|
|
1094
1171
|
function getToolInternals(tool2) {
|
|
1095
|
-
const internals = TOOL_INTERNALS
|
|
1096
|
-
if (!internals
|
|
1172
|
+
const internals = tool2[TOOL_INTERNALS];
|
|
1173
|
+
if (!internals || typeof internals.prepareInput !== "function" || typeof internals.executePrepared !== "function") {
|
|
1174
|
+
throw new Error(`Tool "${tool2.name}" was not created by a compatible tool()`);
|
|
1175
|
+
}
|
|
1097
1176
|
return internals;
|
|
1098
1177
|
}
|
|
1099
1178
|
function prepareToolInput(tool2, input) {
|
|
@@ -1194,9 +1273,11 @@ function tool(config) {
|
|
|
1194
1273
|
},
|
|
1195
1274
|
_execute: execute
|
|
1196
1275
|
};
|
|
1197
|
-
|
|
1198
|
-
|
|
1199
|
-
|
|
1276
|
+
Object.defineProperty(instance, TOOL_INTERNALS, {
|
|
1277
|
+
value: {
|
|
1278
|
+
prepareInput,
|
|
1279
|
+
executePrepared
|
|
1280
|
+
}
|
|
1200
1281
|
});
|
|
1201
1282
|
return instance;
|
|
1202
1283
|
}
|
|
@@ -1227,6 +1308,7 @@ async function resolveApiKey(source) {
|
|
|
1227
1308
|
// src/providers/default-endpoints.ts
|
|
1228
1309
|
var OPENAI_DEFAULT_BASE_URL = "https://api.openai.com/v1";
|
|
1229
1310
|
var ANTHROPIC_DEFAULT_BASE_URL = "https://api.anthropic.com/v1";
|
|
1311
|
+
var GEMINI_DEFAULT_BASE_URL = "https://generativelanguage.googleapis.com/v1beta";
|
|
1230
1312
|
|
|
1231
1313
|
// src/providers/rate-limiter.ts
|
|
1232
1314
|
function sanitizeRateLimitConfig(config) {
|
|
@@ -1624,12 +1706,36 @@ var anthropicQuotaDialect = makeDialect(
|
|
|
1624
1706
|
return "unknown";
|
|
1625
1707
|
}
|
|
1626
1708
|
);
|
|
1709
|
+
var geminiQuotaDialect = makeDialect([], (error) => {
|
|
1710
|
+
if (error.code === "quota_exceeded") return "spend_cap";
|
|
1711
|
+
if (Array.isArray(error.details)) {
|
|
1712
|
+
for (const detail of error.details) {
|
|
1713
|
+
if (typeof detail !== "object" || detail === null) continue;
|
|
1714
|
+
const violations = detail.violations;
|
|
1715
|
+
if (!Array.isArray(violations)) continue;
|
|
1716
|
+
if (violations.some((violation) => {
|
|
1717
|
+
if (typeof violation !== "object" || violation === null) return false;
|
|
1718
|
+
const id = violation.quotaId;
|
|
1719
|
+
return typeof id === "string" && /perday|daily|spend|billing/i.test(id);
|
|
1720
|
+
}))
|
|
1721
|
+
return "spend_cap";
|
|
1722
|
+
}
|
|
1723
|
+
}
|
|
1724
|
+
const message = error.message;
|
|
1725
|
+
if (typeof message === "string" && /monthly spending cap|spend(?:-based|ing)? (?:cap|limit)|prepay(?:ment)? credits? (?:are )?depleted/i.test(
|
|
1726
|
+
message
|
|
1727
|
+
)) {
|
|
1728
|
+
return "spend_cap";
|
|
1729
|
+
}
|
|
1730
|
+
return "unknown";
|
|
1731
|
+
});
|
|
1627
1732
|
var DIALECTS = /* @__PURE__ */ new Map([
|
|
1628
1733
|
["openai", { origin: new URL(OPENAI_DEFAULT_BASE_URL).origin, dialect: openaiQuotaDialect }],
|
|
1629
1734
|
[
|
|
1630
1735
|
"anthropic",
|
|
1631
1736
|
{ origin: new URL(ANTHROPIC_DEFAULT_BASE_URL).origin, dialect: anthropicQuotaDialect }
|
|
1632
|
-
]
|
|
1737
|
+
],
|
|
1738
|
+
["google", { origin: new URL(GEMINI_DEFAULT_BASE_URL).origin, dialect: geminiQuotaDialect }]
|
|
1633
1739
|
]);
|
|
1634
1740
|
function quotaDialectFor(family, origin) {
|
|
1635
1741
|
const entry = DIALECTS.get(family);
|
|
@@ -5820,7 +5926,7 @@ var GEMINI_PRICING = {
|
|
|
5820
5926
|
},
|
|
5821
5927
|
"gemini-3.8-flash": { input: 75e-8, cached: 75e-9, output: 375e-8 }
|
|
5822
5928
|
};
|
|
5823
|
-
var CANONICAL_GEMINI_BASE_URL =
|
|
5929
|
+
var CANONICAL_GEMINI_BASE_URL = GEMINI_DEFAULT_BASE_URL;
|
|
5824
5930
|
function isValidTokenCount2(value) {
|
|
5825
5931
|
return typeof value === "number" && Number.isSafeInteger(value) && value >= 0;
|
|
5826
5932
|
}
|
|
@@ -6177,10 +6283,7 @@ var GeminiProvider = class {
|
|
|
6177
6283
|
axlRateGovernors;
|
|
6178
6284
|
constructor(options = {}) {
|
|
6179
6285
|
this.apiKeySource = options.apiKey ?? process.env.GOOGLE_API_KEY ?? process.env.GEMINI_API_KEY ?? "";
|
|
6180
|
-
this.baseUrl = (options.baseUrl ??
|
|
6181
|
-
/\/$/,
|
|
6182
|
-
""
|
|
6183
|
-
);
|
|
6286
|
+
this.baseUrl = (options.baseUrl ?? GEMINI_DEFAULT_BASE_URL).replace(/\/$/, "");
|
|
6184
6287
|
assertSafeProviderBaseUrl(
|
|
6185
6288
|
this.baseUrl,
|
|
6186
6289
|
"Google provider",
|
|
@@ -11379,6 +11482,34 @@ function toAccountingUsage(usage) {
|
|
|
11379
11482
|
cacheWriteTokens: usage.cache_write_tokens ?? 0
|
|
11380
11483
|
};
|
|
11381
11484
|
}
|
|
11485
|
+
function safeTiming(response) {
|
|
11486
|
+
try {
|
|
11487
|
+
const timing = response.timing;
|
|
11488
|
+
if (!timing) return void 0;
|
|
11489
|
+
const queuedMs = timing.queuedMs;
|
|
11490
|
+
const retryMs = timing.retryMs;
|
|
11491
|
+
const wireMs = timing.wireMs;
|
|
11492
|
+
if (![queuedMs, retryMs, wireMs].every((value) => Number.isFinite(value) && value >= 0)) {
|
|
11493
|
+
return void 0;
|
|
11494
|
+
}
|
|
11495
|
+
const attempts = timing.attempts;
|
|
11496
|
+
const ttfbMs = timing.ttfbMs;
|
|
11497
|
+
const rateLimitRetries = timing.rateLimitRetries;
|
|
11498
|
+
const firstTokenMs = timing.firstTokenMs;
|
|
11499
|
+
const valid = (value) => typeof value === "number" && Number.isFinite(value) && value >= 0;
|
|
11500
|
+
return {
|
|
11501
|
+
queuedMs,
|
|
11502
|
+
retryMs,
|
|
11503
|
+
wireMs,
|
|
11504
|
+
...valid(attempts) ? { attempts } : {},
|
|
11505
|
+
...valid(ttfbMs) ? { ttfbMs } : {},
|
|
11506
|
+
...valid(rateLimitRetries) ? { rateLimitRetries } : {},
|
|
11507
|
+
...valid(firstTokenMs) ? { firstTokenMs } : {}
|
|
11508
|
+
};
|
|
11509
|
+
} catch {
|
|
11510
|
+
return void 0;
|
|
11511
|
+
}
|
|
11512
|
+
}
|
|
11382
11513
|
function composeLifecycle(caller, onDispatch) {
|
|
11383
11514
|
return {
|
|
11384
11515
|
onDispatch() {
|
|
@@ -11572,7 +11703,13 @@ var CaptureRecorder = class {
|
|
|
11572
11703
|
}
|
|
11573
11704
|
};
|
|
11574
11705
|
function openProviderOperation(raw, kind, options) {
|
|
11575
|
-
const handle = openOperation({
|
|
11706
|
+
const handle = openOperation({
|
|
11707
|
+
kind,
|
|
11708
|
+
model: options.model,
|
|
11709
|
+
diagnosticModelUri: options.accountingModelUri,
|
|
11710
|
+
provider: raw.name,
|
|
11711
|
+
agentCall: options.accountingModelUri !== void 0
|
|
11712
|
+
});
|
|
11576
11713
|
if (handle && raw.reportsRequestLifecycle === true) handle.markDispatchObservable();
|
|
11577
11714
|
return handle;
|
|
11578
11715
|
}
|
|
@@ -11589,7 +11726,8 @@ function createScopedProvider(raw) {
|
|
|
11589
11726
|
handle.settle({
|
|
11590
11727
|
cost: response.cost,
|
|
11591
11728
|
provenance: response.costProvenance,
|
|
11592
|
-
usage: toAccountingUsage(response.usage)
|
|
11729
|
+
usage: toAccountingUsage(response.usage),
|
|
11730
|
+
timing: safeTiming(response)
|
|
11593
11731
|
});
|
|
11594
11732
|
recorder?.end({ response });
|
|
11595
11733
|
return response;
|
|
@@ -11644,7 +11782,8 @@ function createScopedProvider(raw) {
|
|
|
11644
11782
|
handle?.settle({
|
|
11645
11783
|
cost: result.value.cost,
|
|
11646
11784
|
provenance: result.value.costProvenance,
|
|
11647
|
-
usage: toAccountingUsage(result.value.usage)
|
|
11785
|
+
usage: toAccountingUsage(result.value.usage),
|
|
11786
|
+
timing: safeTiming(result.value)
|
|
11648
11787
|
});
|
|
11649
11788
|
settled = true;
|
|
11650
11789
|
recorder?.end({
|
|
@@ -12077,13 +12216,6 @@ function eventError(error) {
|
|
|
12077
12216
|
return { name: "Error", message: "Unknown thrown value" };
|
|
12078
12217
|
}
|
|
12079
12218
|
}
|
|
12080
|
-
function isToolFailure(error) {
|
|
12081
|
-
try {
|
|
12082
|
-
return error instanceof ToolFailure;
|
|
12083
|
-
} catch {
|
|
12084
|
-
return false;
|
|
12085
|
-
}
|
|
12086
|
-
}
|
|
12087
12219
|
function cancellation(phase, error, result) {
|
|
12088
12220
|
let reason;
|
|
12089
12221
|
try {
|
|
@@ -12099,7 +12231,7 @@ function cancellation(phase, error, result) {
|
|
|
12099
12231
|
}
|
|
12100
12232
|
function failed(phase, error, options = {}) {
|
|
12101
12233
|
let modelMessage;
|
|
12102
|
-
if (
|
|
12234
|
+
if (isToolFailureError(error)) {
|
|
12103
12235
|
try {
|
|
12104
12236
|
modelMessage = typeof error.modelMessage === "string" ? error.modelMessage : void 0;
|
|
12105
12237
|
} catch {
|
|
@@ -13787,6 +13919,7 @@ ${appendedSchemaText}`;
|
|
|
13787
13919
|
const turnStart = Date.now();
|
|
13788
13920
|
const chatOptions = {
|
|
13789
13921
|
model,
|
|
13922
|
+
accountingModelUri: effectiveModelUri,
|
|
13790
13923
|
temperature: options?.temperature ?? agent2._config.temperature,
|
|
13791
13924
|
tools: toolDefs.length > 0 ? toolDefs : void 0,
|
|
13792
13925
|
maxTokens: options?.maxTokens ?? agent2._config.maxTokens ?? 4096,
|
|
@@ -20541,8 +20674,9 @@ var AxlRuntime = class extends EventEmitter2 {
|
|
|
20541
20674
|
* new paid operations once known spend reaches the limit. Already-dispatched
|
|
20542
20675
|
* work still settles and is still counted.
|
|
20543
20676
|
*
|
|
20544
|
-
*
|
|
20545
|
-
*
|
|
20677
|
+
* Model metadata and timing share the settlement scope with accounting, so
|
|
20678
|
+
* they cross runtimes and compatible ESM/CJS copies. Workflow names and
|
|
20679
|
+
* captured traces still come from this runtime's events.
|
|
20546
20680
|
*/
|
|
20547
20681
|
async trackOutcome(fn, options) {
|
|
20548
20682
|
const parentScope = costScopeStorage.getStore();
|
|
@@ -20551,49 +20685,11 @@ var AxlRuntime = class extends EventEmitter2 {
|
|
|
20551
20685
|
trackedIds: /* @__PURE__ */ new Set(),
|
|
20552
20686
|
parent: parentScope
|
|
20553
20687
|
};
|
|
20554
|
-
const modelCalls = /* @__PURE__ */ new Map();
|
|
20555
|
-
const modelTiming = /* @__PURE__ */ new Map();
|
|
20556
|
-
const captureTimingSamples = options?.captureTimingSamples === true;
|
|
20557
20688
|
const workflowCalls = /* @__PURE__ */ new Map();
|
|
20558
|
-
const tokens = { input: 0, output: 0, reasoning: 0 };
|
|
20559
|
-
let agentCalls = 0;
|
|
20560
20689
|
const capturedTraces = options?.captureTraces ? [] : void 0;
|
|
20561
20690
|
const listener = (event) => {
|
|
20562
20691
|
if (!scope.trackedIds.has(event.executionId)) return;
|
|
20563
20692
|
scope.totalCost += eventCostContribution(event);
|
|
20564
|
-
if (event.type === "agent_call_end") {
|
|
20565
|
-
if (event.model) modelCalls.set(event.model, (modelCalls.get(event.model) ?? 0) + 1);
|
|
20566
|
-
agentCalls++;
|
|
20567
|
-
if (event.tokens) {
|
|
20568
|
-
tokens.input += event.tokens.input ?? 0;
|
|
20569
|
-
tokens.output += event.tokens.output ?? 0;
|
|
20570
|
-
tokens.reasoning += event.tokens.reasoning ?? 0;
|
|
20571
|
-
}
|
|
20572
|
-
const failed2 = event.data?.error != null;
|
|
20573
|
-
if (event.model && event.timing && !failed2) {
|
|
20574
|
-
const t = event.timing;
|
|
20575
|
-
let bucket = modelTiming.get(event.model);
|
|
20576
|
-
if (!bucket) {
|
|
20577
|
-
bucket = {
|
|
20578
|
-
calls: 0,
|
|
20579
|
-
queuedMs: 0,
|
|
20580
|
-
retryMs: 0,
|
|
20581
|
-
wireMs: 0,
|
|
20582
|
-
...captureTimingSamples ? { samples: [] } : {}
|
|
20583
|
-
};
|
|
20584
|
-
modelTiming.set(event.model, bucket);
|
|
20585
|
-
}
|
|
20586
|
-
bucket.calls++;
|
|
20587
|
-
bucket.samples?.push(t);
|
|
20588
|
-
bucket.queuedMs += t.queuedMs;
|
|
20589
|
-
bucket.retryMs += t.retryMs;
|
|
20590
|
-
bucket.wireMs += t.wireMs;
|
|
20591
|
-
if (t.firstTokenMs != null) {
|
|
20592
|
-
bucket.firstTokenMs = (bucket.firstTokenMs ?? 0) + t.firstTokenMs;
|
|
20593
|
-
bucket.firstTokenCalls = (bucket.firstTokenCalls ?? 0) + 1;
|
|
20594
|
-
}
|
|
20595
|
-
}
|
|
20596
|
-
}
|
|
20597
20693
|
if (event.type === "workflow_start" && event.workflow) {
|
|
20598
20694
|
workflowCalls.set(event.workflow, (workflowCalls.get(event.workflow) ?? 0) + 1);
|
|
20599
20695
|
}
|
|
@@ -20619,9 +20715,14 @@ var AxlRuntime = class extends EventEmitter2 {
|
|
|
20619
20715
|
this.on("trace", listener);
|
|
20620
20716
|
let outcome;
|
|
20621
20717
|
let accounting;
|
|
20718
|
+
let diagnostics;
|
|
20622
20719
|
try {
|
|
20623
|
-
({ outcome, accounting } = await runInAccountingScope(
|
|
20624
|
-
{
|
|
20720
|
+
({ outcome, accounting, diagnostics } = await runInAccountingScope(
|
|
20721
|
+
{
|
|
20722
|
+
purpose: options?.purpose,
|
|
20723
|
+
admission: options?.admission,
|
|
20724
|
+
captureTimingSamples: options?.captureTimingSamples
|
|
20725
|
+
},
|
|
20625
20726
|
() => (
|
|
20626
20727
|
// Capture wraps the cost scope rather than the other way round so a
|
|
20627
20728
|
// record can never be written for an operation the accounting scope
|
|
@@ -20645,13 +20746,13 @@ var AxlRuntime = class extends EventEmitter2 {
|
|
|
20645
20746
|
return {
|
|
20646
20747
|
...outcome,
|
|
20647
20748
|
accounting,
|
|
20648
|
-
...modelTiming.
|
|
20749
|
+
...Object.keys(diagnostics.modelTiming).length > 0 ? { modelTiming: diagnostics.modelTiming } : {},
|
|
20649
20750
|
...capturedTraces ? { traces: capturedTraces } : {},
|
|
20650
20751
|
metadata: {
|
|
20651
|
-
models:
|
|
20652
|
-
modelCallCounts:
|
|
20653
|
-
tokens,
|
|
20654
|
-
agentCalls,
|
|
20752
|
+
models: Object.keys(diagnostics.modelCallCounts),
|
|
20753
|
+
modelCallCounts: Object.keys(diagnostics.modelCallCounts).length > 0 ? diagnostics.modelCallCounts : void 0,
|
|
20754
|
+
tokens: diagnostics.tokens,
|
|
20755
|
+
agentCalls: diagnostics.agentCalls,
|
|
20655
20756
|
workflows: [...workflowCalls.keys()],
|
|
20656
20757
|
workflowCallCounts: workflowCalls.size > 0 ? Object.fromEntries(workflowCalls) : void 0
|
|
20657
20758
|
}
|