agent-inspect 6.31.32 → 6.31.33
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 +6 -0
- package/README.md +1 -1
- package/docs/TRACE-CONTRACTS.md +2 -0
- package/package.json +1 -1
- package/packages/cli/dist/{chunk-PEGM6T2X.mjs → chunk-AILSHDEF.mjs} +111 -24
- package/packages/cli/dist/chunk-AILSHDEF.mjs.map +1 -0
- package/packages/cli/dist/index.cjs +110 -23
- package/packages/cli/dist/index.cjs.map +1 -1
- package/packages/cli/dist/index.mjs +4 -4
- package/packages/cli/dist/index.mjs.map +1 -1
- package/packages/cli/dist/{src-CWUJTMRD.mjs → src-SP36M4VB.mjs} +3 -3
- package/packages/cli/dist/{src-CWUJTMRD.mjs.map → src-SP36M4VB.mjs.map} +1 -1
- package/packages/core/dist/advanced.cjs +76 -18
- package/packages/core/dist/advanced.cjs.map +1 -1
- package/packages/core/dist/advanced.mjs +2 -2
- package/packages/core/dist/checks.cjs +109 -22
- package/packages/core/dist/checks.cjs.map +1 -1
- package/packages/core/dist/checks.mjs +1 -1
- package/packages/core/dist/{chunk-6G67ZN72.mjs → chunk-EMDJLFRK.mjs} +111 -24
- package/packages/core/dist/chunk-EMDJLFRK.mjs.map +1 -0
- package/packages/cli/dist/chunk-PEGM6T2X.mjs.map +0 -1
- package/packages/core/dist/chunk-6G67ZN72.mjs.map +0 -1
|
@@ -1,5 +1,5 @@
|
|
|
1
|
-
import { extractSessionWorkflowMetadata, sessionKeyForRun, defineTraceContract, runTraceChecks, createRunStatusRule, createToolUsageRule, createRunDurationRule, createRunDepthRule, createToolFailureRule, createLlmUsageRule, createObservedOutcomeRule } from './chunk-
|
|
2
|
-
export { extractSessionWorkflowMetadata, sessionKeyForRun } from './chunk-
|
|
1
|
+
import { extractSessionWorkflowMetadata, sessionKeyForRun, defineTraceContract, runTraceChecks, createRunStatusRule, createToolUsageRule, createRunDurationRule, createRunDepthRule, createToolFailureRule, createLlmUsageRule, createObservedOutcomeRule } from './chunk-EMDJLFRK.mjs';
|
|
2
|
+
export { extractSessionWorkflowMetadata, sessionKeyForRun } from './chunk-EMDJLFRK.mjs';
|
|
3
3
|
export { MAX_TERMINAL_DEPTH, MAX_TERMINAL_NAME_LENGTH, TERMINAL_INDENT, TraceDirectory, createInspector, createInspectorRuntime, formatTerminalName, getCurrentContext, getCurrentCorrelationMetadata, getCurrentDepth, getCurrentRunId, getCurrentRunName, getCurrentStepId, getIndent, getParentStepId, getTraceDirFromContext, getTraceSafetyFromContext, hasActiveContext, isAgentInspectEnabled, isSilentContext, maybeInspectRun, printError, printFailedAt, printRunComplete, printRunStart, printStepComplete, printStepStart, renderErrorLine, renderRunSummary, renderStepLine, resolveTraceDir, runWithContext, runWithStepContext } from './chunk-VIEJJ5JB.mjs';
|
|
4
4
|
import { buildRunTimeline, filterTraces, extractMetadata, buildRunSummary } from './chunk-6S666BF4.mjs';
|
|
5
5
|
export { buildRunSummary, buildRunTimeline, buildRunWhatSummary, buildTraceStats, extractMetadata, filterTraces, formatStepLabel, renderRunWhat, renderTimeline, renderTraceStats } from './chunk-6S666BF4.mjs';
|
|
@@ -3010,10 +3010,17 @@ function contractToRules(contract) {
|
|
|
3010
3010
|
(event) => event.status === "running"
|
|
3011
3011
|
);
|
|
3012
3012
|
if (running.length > 0) {
|
|
3013
|
+
const labels = running.map((event) => {
|
|
3014
|
+
if (event.kind === "TOOL") {
|
|
3015
|
+
return `tool ${resolveCanonicalToolName(event)}`;
|
|
3016
|
+
}
|
|
3017
|
+
return `${event.kind} ${event.name}`;
|
|
3018
|
+
});
|
|
3019
|
+
const message = labels.length === 1 ? `Run contains incomplete running events: ${labels[0]} never completed.` : `Run contains incomplete running events: ${labels.join("; ")}.`;
|
|
3013
3020
|
findings.push(
|
|
3014
3021
|
contractFailFinding(
|
|
3015
3022
|
"contract.run.allowedStatuses",
|
|
3016
|
-
|
|
3023
|
+
message,
|
|
3017
3024
|
running.map((event) => ({
|
|
3018
3025
|
runId: event.runId,
|
|
3019
3026
|
eventId: event.eventId,
|
|
@@ -3022,7 +3029,10 @@ function contractToRules(contract) {
|
|
|
3022
3029
|
status: event.status
|
|
3023
3030
|
})),
|
|
3024
3031
|
"no running events",
|
|
3025
|
-
|
|
3032
|
+
{
|
|
3033
|
+
count: running.length,
|
|
3034
|
+
unfinished: labels
|
|
3035
|
+
}
|
|
3026
3036
|
)
|
|
3027
3037
|
);
|
|
3028
3038
|
}
|
|
@@ -4159,6 +4169,11 @@ function compareFindings(eventById) {
|
|
|
4159
4169
|
if (STATUS_RANK[a.status] !== STATUS_RANK[b.status]) {
|
|
4160
4170
|
return STATUS_RANK[a.status] - STATUS_RANK[b.status];
|
|
4161
4171
|
}
|
|
4172
|
+
if (a.ruleId === "tool.usage") {
|
|
4173
|
+
const aHasEvent = a.evidence[0]?.eventId !== void 0;
|
|
4174
|
+
const bHasEvent = b.evidence[0]?.eventId !== void 0;
|
|
4175
|
+
if (aHasEvent !== bHasEvent) return aHasEvent ? -1 : 1;
|
|
4176
|
+
}
|
|
4162
4177
|
const byRun = compareStrings(a.evidence[0]?.runId, b.evidence[0]?.runId);
|
|
4163
4178
|
if (byRun !== 0) return byRun;
|
|
4164
4179
|
const byTime = eventTimestamp(a, eventById).localeCompare(eventTimestamp(b, eventById));
|
|
@@ -4284,6 +4299,37 @@ function failFinding(ruleId, message, evidence, expected, actual, meta) {
|
|
|
4284
4299
|
function toolName(event) {
|
|
4285
4300
|
return resolveCanonicalToolName(event);
|
|
4286
4301
|
}
|
|
4302
|
+
function formatToolNameForMessage(name) {
|
|
4303
|
+
const details = [];
|
|
4304
|
+
for (let index = 0; index < name.length; ) {
|
|
4305
|
+
const codePoint = name.codePointAt(index);
|
|
4306
|
+
const width = codePoint > 65535 ? 2 : 1;
|
|
4307
|
+
if (codePoint > 127) {
|
|
4308
|
+
details.push(
|
|
4309
|
+
`U+${codePoint.toString(16).toUpperCase().padStart(4, "0")} at index ${index}`
|
|
4310
|
+
);
|
|
4311
|
+
}
|
|
4312
|
+
index += width;
|
|
4313
|
+
}
|
|
4314
|
+
if (details.length === 0) return name;
|
|
4315
|
+
return `"${name}" (contains ${details.join("; ")})`;
|
|
4316
|
+
}
|
|
4317
|
+
function describeRunningEvent(event) {
|
|
4318
|
+
if (event.kind === "TOOL") {
|
|
4319
|
+
return `tool ${formatToolNameForMessage(resolveCanonicalToolName(event))}`;
|
|
4320
|
+
}
|
|
4321
|
+
if (event.kind === "LLM") {
|
|
4322
|
+
return `llm ${stepEndpointName(event, "LLM")}`;
|
|
4323
|
+
}
|
|
4324
|
+
return `${event.kind} ${event.name}`;
|
|
4325
|
+
}
|
|
4326
|
+
function incompleteRunningMessage(prefix, running) {
|
|
4327
|
+
const labels = running.map(describeRunningEvent);
|
|
4328
|
+
if (labels.length === 1) {
|
|
4329
|
+
return `${prefix}: ${labels[0]} never completed.`;
|
|
4330
|
+
}
|
|
4331
|
+
return `${prefix}: ${labels.join("; ")}.`;
|
|
4332
|
+
}
|
|
4287
4333
|
function stepEndpointName(event, kind) {
|
|
4288
4334
|
if (kind === "TOOL") return resolveCanonicalToolName(event);
|
|
4289
4335
|
for (const prefix of ["llm:", "generation:", "transcription:", "speech:"]) {
|
|
@@ -4628,10 +4674,13 @@ function createRunStatusRule(options = {}) {
|
|
|
4628
4674
|
findings.push(
|
|
4629
4675
|
failFinding(
|
|
4630
4676
|
"run.status",
|
|
4631
|
-
"Run contains incomplete running events
|
|
4677
|
+
incompleteRunningMessage("Run contains incomplete running events", running),
|
|
4632
4678
|
running.map((event) => eventEvidence3(event)),
|
|
4633
4679
|
"no running events",
|
|
4634
|
-
|
|
4680
|
+
{
|
|
4681
|
+
count: running.length,
|
|
4682
|
+
unfinished: running.map(describeRunningEvent)
|
|
4683
|
+
}
|
|
4635
4684
|
)
|
|
4636
4685
|
);
|
|
4637
4686
|
}
|
|
@@ -4837,6 +4886,34 @@ function createToolUsageRule(options) {
|
|
|
4837
4886
|
const names = tools.map(toolName);
|
|
4838
4887
|
const nameSet = new Set(names);
|
|
4839
4888
|
const findings = [];
|
|
4889
|
+
const forbidden = new Set(options.forbidden ?? []);
|
|
4890
|
+
const allowed = options.allowed?.length ? new Set(options.allowed) : void 0;
|
|
4891
|
+
for (const event of tools) {
|
|
4892
|
+
const name = toolName(event);
|
|
4893
|
+
const display = formatToolNameForMessage(name);
|
|
4894
|
+
if (forbidden.has(name)) {
|
|
4895
|
+
findings.push(
|
|
4896
|
+
failFinding(
|
|
4897
|
+
"tool.usage",
|
|
4898
|
+
`Forbidden tool ${display} appeared.`,
|
|
4899
|
+
[eventEvidence3(event)],
|
|
4900
|
+
"tool absent",
|
|
4901
|
+
name
|
|
4902
|
+
)
|
|
4903
|
+
);
|
|
4904
|
+
}
|
|
4905
|
+
if (allowed && !allowed.has(name)) {
|
|
4906
|
+
findings.push(
|
|
4907
|
+
failFinding(
|
|
4908
|
+
"tool.usage",
|
|
4909
|
+
`Tool ${display} is not in the allowed tool set.`,
|
|
4910
|
+
[eventEvidence3(event)],
|
|
4911
|
+
[...allowed].sort(),
|
|
4912
|
+
name
|
|
4913
|
+
)
|
|
4914
|
+
);
|
|
4915
|
+
}
|
|
4916
|
+
}
|
|
4840
4917
|
for (const required of options.required ?? []) {
|
|
4841
4918
|
if (!nameSet.has(required)) {
|
|
4842
4919
|
const otherKinds = [
|
|
@@ -4854,7 +4931,7 @@ function createToolUsageRule(options) {
|
|
|
4854
4931
|
findings.push(
|
|
4855
4932
|
failFinding(
|
|
4856
4933
|
"tool.usage",
|
|
4857
|
-
`Required tool ${required} did not appear.${hint}`,
|
|
4934
|
+
`Required tool ${formatToolNameForMessage(required)} did not appear.${hint}`,
|
|
4858
4935
|
runEvidence(context.selectedRun),
|
|
4859
4936
|
required,
|
|
4860
4937
|
names
|
|
@@ -4862,21 +4939,6 @@ function createToolUsageRule(options) {
|
|
|
4862
4939
|
);
|
|
4863
4940
|
}
|
|
4864
4941
|
}
|
|
4865
|
-
const forbidden = new Set(options.forbidden ?? []);
|
|
4866
|
-
const allowed = options.allowed?.length ? new Set(options.allowed) : void 0;
|
|
4867
|
-
for (const event of tools) {
|
|
4868
|
-
const name = toolName(event);
|
|
4869
|
-
if (forbidden.has(name)) {
|
|
4870
|
-
findings.push(
|
|
4871
|
-
failFinding("tool.usage", `Forbidden tool ${name} appeared.`, [eventEvidence3(event)], "tool absent", name)
|
|
4872
|
-
);
|
|
4873
|
-
}
|
|
4874
|
-
if (allowed && !allowed.has(name)) {
|
|
4875
|
-
findings.push(
|
|
4876
|
-
failFinding("tool.usage", `Tool ${name} is not in the allowed tool set.`, [eventEvidence3(event)], [...allowed].sort(), name)
|
|
4877
|
-
);
|
|
4878
|
-
}
|
|
4879
|
-
}
|
|
4880
4942
|
if (options.minCount !== void 0 && tools.length < options.minCount) {
|
|
4881
4943
|
findings.push(
|
|
4882
4944
|
failFinding("tool.usage", `Tool count ${tools.length} was below minimum ${options.minCount}.`, runEvidence(context.selectedRun), { minCount: options.minCount }, tools.length)
|
|
@@ -4910,6 +4972,28 @@ function createStepOrderingRule(options) {
|
|
|
4910
4972
|
const afterEvents = finishedEvents(context, options.after.kind).filter(
|
|
4911
4973
|
(event) => stepEndpointName(event, options.after.kind) === options.after.name
|
|
4912
4974
|
);
|
|
4975
|
+
const beforeRunning = semanticEvents(context).filter(
|
|
4976
|
+
(event) => event.kind === options.before.kind && event.status === "running" && stepEndpointName(event, options.before.kind) === options.before.name
|
|
4977
|
+
);
|
|
4978
|
+
if (beforeEvents.length === 0 && afterEvents.length > 0 && beforeRunning.length > 0) {
|
|
4979
|
+
const endpointExpected2 = bothTools ? { before: options.before.name, after: options.after.name } : { before: options.before, after: options.after };
|
|
4980
|
+
return [
|
|
4981
|
+
failFinding(
|
|
4982
|
+
ruleId,
|
|
4983
|
+
`${subject} ${beforeLabel} started but never finished before ${afterLabel} ran.`,
|
|
4984
|
+
[
|
|
4985
|
+
...beforeRunning.map((event) => eventEvidence3(event)),
|
|
4986
|
+
eventEvidence3(afterEvents[0])
|
|
4987
|
+
],
|
|
4988
|
+
{ ...endpointExpected2, mode },
|
|
4989
|
+
{
|
|
4990
|
+
code: bothTools ? "tool.order.interval-unresolved" : "step.order.interval-unresolved",
|
|
4991
|
+
unfinishedBefore: true,
|
|
4992
|
+
beforeStatus: "running"
|
|
4993
|
+
}
|
|
4994
|
+
)
|
|
4995
|
+
];
|
|
4996
|
+
}
|
|
4913
4997
|
if (beforeEvents.length === 0 || afterEvents.length === 0) {
|
|
4914
4998
|
if (!requireEndpoints) return [];
|
|
4915
4999
|
const findings = [];
|
|
@@ -5286,10 +5370,13 @@ function createStructureIncompleteRule(options = {}) {
|
|
|
5286
5370
|
findings.push(
|
|
5287
5371
|
failFinding(
|
|
5288
5372
|
"structure.incomplete",
|
|
5289
|
-
"Trace contains incomplete running events
|
|
5373
|
+
incompleteRunningMessage("Trace contains incomplete running events", running),
|
|
5290
5374
|
running.map((event) => eventEvidence3(event, "status")),
|
|
5291
5375
|
"no running events",
|
|
5292
|
-
|
|
5376
|
+
{
|
|
5377
|
+
count: running.length,
|
|
5378
|
+
unfinished: running.map(describeRunningEvent)
|
|
5379
|
+
}
|
|
5293
5380
|
)
|
|
5294
5381
|
);
|
|
5295
5382
|
}
|