@tangle-network/agent-eval 0.139.2 → 0.139.3

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.
@@ -1172,7 +1172,7 @@ const ANALYST_BENCHMARK_DEPENDENCY_LOCK_FILES = Object.freeze([
1172
1172
  "package.json",
1173
1173
  "pnpm-lock.yaml"
1174
1174
  ]);
1175
- const ANALYST_BENCHMARK_DEPENDENCY_LOCK_SHA256 = "1ca280998a9f3a416b40cadb9c14789ada490a727a4ec78491c92bb2022e6c95";
1175
+ const ANALYST_BENCHMARK_DEPENDENCY_LOCK_SHA256 = "11ea62baf2914dba71dd62e45ba4bb8e856b2cefdd5b1b73dc2f14b4b6e6d115";
1176
1176
  /** The published benchmark evidence was produced at this package version, by
1177
1177
  * the retired one-shot direct runner, before trace analysts moved to the
1178
1178
  * recursive DSPy RLM engine. Both evidence digests below are historical facts
@@ -1203,6 +1203,7 @@ const ANALYST_BENCHMARK_IMPLEMENTATION_FILES = Object.freeze([
1203
1203
  "src/analyst/benchmark-public-data.ts",
1204
1204
  "src/analyst/benchmark-public-errors.ts",
1205
1205
  "src/analyst/benchmark-public-model.ts",
1206
+ "src/analyst/benchmark-public-prompt.ts",
1206
1207
  "src/analyst/benchmark-public-rlm.ts",
1207
1208
  "src/analyst/benchmark-public-types.ts",
1208
1209
  "src/analyst/benchmark-real-model.ts",
@@ -1265,7 +1266,7 @@ const ANALYST_BENCHMARK_IMPLEMENTATION_FILES = Object.freeze([
1265
1266
  "src/trace/otlp-attributes.ts",
1266
1267
  "src/trace/raw-provider-sink.ts"
1267
1268
  ]);
1268
- const ANALYST_BENCHMARK_IMPLEMENTATION_SHA256 = "5e47fc9d9f49c468d3ef06c5d552925e6a026f9e22a75056a9c8c5a2879744c0";
1269
+ const ANALYST_BENCHMARK_IMPLEMENTATION_SHA256 = "26820de559ca069145eb9649283d2efba51a0a7b8d3662d4c378b9ecebfd4777";
1269
1270
  function analystBenchmarkImplementationDigest() {
1270
1271
  return ANALYST_BENCHMARK_IMPLEMENTATION_SHA256;
1271
1272
  }
@@ -1332,19 +1333,12 @@ async function validateCodeTraceFindingEvidence(options) {
1332
1333
  if (citations.length === 0) return;
1333
1334
  for (const citation of citations) if (!citation.location || citation.location.traceId !== options.trajectoryId) throw new Error(`model finding '${citation.findingId}' cites non-case evidence '${citation.evidence.uri}'`);
1334
1335
  const spanIds = [...new Set(citations.map((citation) => `step-${citation.location.step}`))];
1335
- const spans = /* @__PURE__ */ new Map();
1336
- for (let offset = 0; offset < spanIds.length; offset += TRACE_ANALYSIS_LIMITS.viewSpans) {
1337
- const requested = spanIds.slice(offset, offset + TRACE_ANALYSIS_LIMITS.viewSpans);
1338
- const result = await options.store.viewSpans({
1339
- trace_id: options.trajectoryId,
1340
- span_ids: requested
1341
- }, options.signal ? { signal: options.signal } : void 0);
1342
- if (result.missing_span_ids.length > 0 || result.omitted_span_ids.length > 0) {
1343
- const unavailable = [...result.missing_span_ids, ...result.omitted_span_ids];
1344
- throw new Error(`model finding evidence is unavailable in the case trace: ${unavailable.join(", ")}`);
1345
- }
1346
- for (const span of result.spans) spans.set(span.span_id, span);
1347
- }
1336
+ const { spans, missing } = await fetchTraceSpans(options.store, {
1337
+ trajectoryId: options.trajectoryId,
1338
+ spanIds,
1339
+ ...options.signal ? { signal: options.signal } : {}
1340
+ });
1341
+ if (missing.length > 0) throw new Error(`model finding evidence is unavailable in the case trace: ${missing.join(", ")}`);
1348
1342
  for (const citation of citations) {
1349
1343
  const spanId = `step-${citation.location.step}`;
1350
1344
  const span = spans.get(spanId);
@@ -1353,31 +1347,45 @@ async function validateCodeTraceFindingEvidence(options) {
1353
1347
  assertExactActionExcerpt(citation.findingId, citation.evidence, spanId, span.attributes.content);
1354
1348
  }
1355
1349
  }
1350
+ /**
1351
+ * Resolve assistant-step evidence for a trajectory.
1352
+ *
1353
+ * `steps` are claims the model made explicitly: an unresolvable one is a model
1354
+ * error and throws. `optionalSteps` are derived by the runner (a block's
1355
+ * interior, a block's consequence step), so an unresolvable one is simply
1356
+ * absent from the returned map and the caller decides what that means.
1357
+ */
1356
1358
  async function resolveAssistantStepEvidence(options) {
1357
- const steps = [...new Set(options.steps)];
1358
- for (const step of steps) if (!Number.isSafeInteger(step) || step < 1) throw new TypeError(`assistant evidence step must be a positive safe integer: ${step}`);
1359
- const spanIds = steps.map((step) => `step-${step}`);
1360
- const spans = /* @__PURE__ */ new Map();
1361
- for (let offset = 0; offset < spanIds.length; offset += TRACE_ANALYSIS_LIMITS.viewSpans) {
1362
- const requested = spanIds.slice(offset, offset + TRACE_ANALYSIS_LIMITS.viewSpans);
1363
- const result = await options.store.viewSpans({
1364
- trace_id: options.trajectoryId,
1365
- span_ids: requested
1366
- }, options.signal ? { signal: options.signal } : void 0);
1367
- if (result.missing_span_ids.length > 0 || result.omitted_span_ids.length > 0) {
1368
- const unavailable = [...result.missing_span_ids, ...result.omitted_span_ids];
1369
- throw new Error(`model selected unavailable assistant steps: ${unavailable.join(", ")}`);
1370
- }
1371
- for (const span of result.spans) spans.set(span.span_id, span);
1372
- }
1359
+ const required = [...new Set(options.steps)];
1360
+ const optional = [...new Set(options.optionalSteps ?? [])].filter((step) => !required.includes(step));
1361
+ for (const step of [...required, ...optional]) if (!Number.isSafeInteger(step) || step < 1) throw new TypeError(`assistant evidence step must be a positive safe integer: ${step}`);
1362
+ const steps = [...required, ...optional];
1363
+ if (steps.length === 0) return /* @__PURE__ */ new Map();
1364
+ const { spans, missing } = await fetchTraceSpans(options.store, {
1365
+ trajectoryId: options.trajectoryId,
1366
+ spanIds: steps.map((step) => `step-${step}`),
1367
+ ...options.signal ? { signal: options.signal } : {}
1368
+ });
1369
+ const missingRequired = missing.filter((spanId) => required.some((step) => `step-${step}` === spanId));
1370
+ if (missingRequired.length > 0) throw new Error(`model selected unavailable assistant steps: ${missingRequired.join(", ")}`);
1373
1371
  const evidence = /* @__PURE__ */ new Map();
1374
1372
  for (const step of steps) {
1375
1373
  const spanId = `step-${step}`;
1374
+ const optionalStep = optional.includes(step);
1376
1375
  const span = spans.get(spanId);
1377
- if (!span) throw new Error(`model selected missing assistant step '${spanId}'`);
1378
- if (span.kind !== "LLM") throw new Error(`model selected '${spanId}', which is ${span.kind}, not an assistant LLM span`);
1376
+ if (!span) {
1377
+ if (optionalStep) continue;
1378
+ throw new Error(`model selected missing assistant step '${spanId}'`);
1379
+ }
1380
+ if (span.kind !== "LLM") {
1381
+ if (optionalStep) continue;
1382
+ throw new Error(`model selected '${spanId}', which is ${span.kind}, not an assistant LLM span`);
1383
+ }
1379
1384
  const content = span.attributes.content;
1380
- if (typeof content !== "string" || content.trim().length === 0) throw new Error(`model selected '${spanId}' without action content`);
1385
+ if (typeof content !== "string" || content.trim().length === 0) {
1386
+ if (optionalStep) continue;
1387
+ throw new Error(`model selected '${spanId}' without action content`);
1388
+ }
1381
1389
  evidence.set(step, {
1382
1390
  kind: "span",
1383
1391
  uri: codeTraceStepEvidenceUri(options.trajectoryId, step),
@@ -1386,6 +1394,38 @@ async function resolveAssistantStepEvidence(options) {
1386
1394
  }
1387
1395
  return evidence;
1388
1396
  }
1397
+ /**
1398
+ * Read spans by id, paging over the store's byte-budget omissions.
1399
+ *
1400
+ * `omitted_span_ids` names spans that exist but did not fit the response
1401
+ * ceiling; the store guarantees at least one span lands per call, so
1402
+ * re-requesting exactly the omitted ids terminates. Only `missing_span_ids`
1403
+ * describes a span the trace does not contain.
1404
+ */
1405
+ async function fetchTraceSpans(store, options) {
1406
+ const spans = /* @__PURE__ */ new Map();
1407
+ const missing = [];
1408
+ const unique = [...new Set(options.spanIds)];
1409
+ const context = options.signal ? { signal: options.signal } : void 0;
1410
+ for (let offset = 0; offset < unique.length; offset += TRACE_ANALYSIS_LIMITS.viewSpans) {
1411
+ let pending = unique.slice(offset, offset + TRACE_ANALYSIS_LIMITS.viewSpans);
1412
+ while (pending.length > 0) {
1413
+ const result = await store.viewSpans({
1414
+ trace_id: options.trajectoryId,
1415
+ span_ids: pending
1416
+ }, context);
1417
+ for (const span of result.spans) spans.set(span.span_id, span);
1418
+ missing.push(...result.missing_span_ids);
1419
+ const omitted = result.omitted_span_ids.filter((spanId) => !spans.has(spanId));
1420
+ if (omitted.length >= pending.length) throw new Error(`trace '${options.trajectoryId}' cannot project spans within the store response budget: ${omitted.join(", ")}`);
1421
+ pending = omitted;
1422
+ }
1423
+ }
1424
+ return {
1425
+ spans,
1426
+ missing
1427
+ };
1428
+ }
1389
1429
  function scanValue(value, traceId, path, depth, serializedDepth) {
1390
1430
  if (depth > MAX_LABEL_SCAN_DEPTH) throw new Error(`trace '${traceId}' exceeds benchmark label scan depth at ${path}`);
1391
1431
  if (Array.isArray(value)) return 1 + value.reduce((count, entry, index) => count + scanValue(entry, traceId, `${path}[${index}]`, depth + 1, serializedDepth), 0);
@@ -1445,119 +1485,6 @@ function assertExactActionExcerpt(findingId, evidence, spanId, content) {
1445
1485
  if (!content.includes(excerpt)) throw new Error(`model finding '${findingId}' excerpt is not present in '${spanId}' action content`);
1446
1486
  }
1447
1487
  //#endregion
1448
- //#region src/analyst/benchmark-public-adapters.ts
1449
- function emptyPublicBenchmarkRunner() {
1450
- return {
1451
- id: "empty",
1452
- analyze() {
1453
- return {
1454
- findings: [],
1455
- usage: {
1456
- calls: 0,
1457
- tokens: {
1458
- input: 0,
1459
- output: 0
1460
- },
1461
- cost: {
1462
- kind: "observed",
1463
- usd: 0
1464
- }
1465
- },
1466
- metadata: { baseline: "emit-no-findings" }
1467
- };
1468
- }
1469
- };
1470
- }
1471
- function adaptPublicBenchmarkFindings(dataset, trajectoryId, findings, analystId) {
1472
- return dataset === "agentrx" ? adaptAgentRxFindings(trajectoryId, findings, analystId) : adaptCodeTraceFindings(trajectoryId, findings, analystId);
1473
- }
1474
- function adaptAgentRxFindings(trajectoryId, findings, analystId) {
1475
- if (findings.length === 0) return [];
1476
- if (findings.length !== 1) throw new Error(`AgentRx model analyst must emit zero or one root cause, received ${findings.length}`);
1477
- const source = findings[0];
1478
- if (!source.subject) throw new Error("AgentRx model analyst finding is missing its failure-category subject");
1479
- const steps = exactFindingSteps(trajectoryId, source);
1480
- if (steps.length !== 1) throw new Error(`AgentRx model analyst must cite exactly one root-cause step, received ${steps.length}`);
1481
- const [adapted] = agentRxPredictionsToFindings(trajectoryId, [{
1482
- failure_case: source.subject,
1483
- step_number: steps[0],
1484
- description: source.rationale ?? source.claim
1485
- }], {
1486
- analystId,
1487
- producedAt: source.produced_at,
1488
- confidence: source.confidence
1489
- });
1490
- if (!adapted) throw new Error("AgentRx output adapter produced no root-cause finding");
1491
- return [{
1492
- ...adapted,
1493
- metadata: {
1494
- ...adapted.metadata,
1495
- sourceFindingId: source.finding_id
1496
- }
1497
- }];
1498
- }
1499
- function adaptCodeTraceFindings(trajectoryId, findings, analystId) {
1500
- const clean = findings.filter((finding) => finding.subject === "clean");
1501
- if (clean.length > 0) {
1502
- if (findings.length !== 1) throw new Error("CodeTraceBench model analyst mixed a clean verdict with incorrect steps");
1503
- exactFindingSteps(trajectoryId, clean[0]);
1504
- return [];
1505
- }
1506
- const byStep = /* @__PURE__ */ new Map();
1507
- for (const source of findings) {
1508
- const steps = exactFindingSteps(trajectoryId, source);
1509
- for (const step of steps) {
1510
- if (byStep.has(step)) continue;
1511
- byStep.set(step, makeFinding({
1512
- analyst_id: analystId,
1513
- area: "incorrect",
1514
- subject: `incorrect-step-${step}`,
1515
- claim: `Step ${step} is incorrect. ${source.claim}`,
1516
- rationale: source.rationale,
1517
- severity: source.severity,
1518
- confidence: source.confidence,
1519
- evidence_refs: [{
1520
- kind: "span",
1521
- uri: codeTraceStepEvidenceUri(trajectoryId, step),
1522
- excerpt: source.evidence_refs.find((evidence) => evidence.uri === codeTraceStepEvidenceUri(trajectoryId, step))?.excerpt
1523
- }],
1524
- recommended_action: source.recommended_action,
1525
- metadata: { sourceFindingId: source.finding_id },
1526
- produced_at: source.produced_at,
1527
- id_basis: `incorrect-step-${step}`
1528
- }));
1529
- }
1530
- }
1531
- return [...byStep].sort(([left], [right]) => left - right).map(([, finding]) => finding);
1532
- }
1533
- function exactFindingSteps(trajectoryId, finding) {
1534
- if (finding.evidence_refs.length === 0) throw new Error(`model finding '${finding.finding_id}' has no step evidence`);
1535
- const steps = finding.evidence_refs.map((evidence) => {
1536
- const parsed = codeTraceStepFromEvidence(evidence.uri);
1537
- if (!parsed || parsed.traceId !== trajectoryId) throw new Error(`model finding '${finding.finding_id}' cites non-case evidence '${evidence.uri}'`);
1538
- return parsed.step;
1539
- });
1540
- return [...new Set(steps)];
1541
- }
1542
- //#endregion
1543
- //#region src/analyst/benchmark-public-types.ts
1544
- function requiredString(value, field) {
1545
- const trimmed = value.trim();
1546
- if (!trimmed) throw new TypeError(`${field} must be a non-empty string`);
1547
- return trimmed;
1548
- }
1549
- function positiveSafeInteger(value, field) {
1550
- if (!Number.isSafeInteger(value) || value < 1) throw new RangeError(`${field} must be a positive safe integer`);
1551
- return value;
1552
- }
1553
- function safeInteger(value, field) {
1554
- if (!Number.isSafeInteger(value)) throw new RangeError(`${field} must be a safe integer`);
1555
- return value;
1556
- }
1557
- function isRecord(value) {
1558
- return typeof value === "object" && value !== null && !Array.isArray(value);
1559
- }
1560
- //#endregion
1561
1488
  //#region src/analyst/benchmark-verification-outcome.ts
1562
1489
  const MAX_REPORTED_CHECKS = 20;
1563
1490
  const SWE_MULTI_NO_TEST_RESULTS = "After applying the fix patch, no test results were captured when executing the test command.";
@@ -2157,6 +2084,376 @@ function isNodeError$1(error, code) {
2157
2084
  return error instanceof Error && "code" in error && error.code === code;
2158
2085
  }
2159
2086
  //#endregion
2087
+ //#region src/analyst/benchmark-public-prompt.ts
2088
+ /** Widest contiguous failure block a model may report. The published corpus's
2089
+ * widest labeled block is 8 steps and its widest stage span is 9, so this bound
2090
+ * never binds honest enumeration; it caps how far one over-wide block can push
2091
+ * unlabeled steps into the precision denominator. */
2092
+ const MAX_INCORRECT_BLOCK_STEPS = 12;
2093
+ /** Most blocks a model may report for one trajectory. The published corpus's
2094
+ * densest case carries 4 disjoint labeled blocks. Together with the per-block
2095
+ * cap this bounds one case at 192 predicted steps without a second ceiling. */
2096
+ const MAX_INCORRECT_BLOCKS = 16;
2097
+ const TRACE_PROJECTION_ATTRIBUTE_BYTE_CAPS = [
2098
+ 4096,
2099
+ 2048,
2100
+ 1024,
2101
+ 512,
2102
+ 256,
2103
+ 128,
2104
+ 64
2105
+ ];
2106
+ const CODE_TRACE_BENCH_ANALYST_PROMPT = `Analyze exactly one coding-agent trajectory and its attached final verification.
2107
+ Your task is the CodeTraceBench incorrect-step task: identify every wrong state-changing action, bad hypothesis that drives an action, and regression.
2108
+ An incorrect step remains incorrect when the agent later recovers or the final verification passes; a trajectory that ends in success still contains every mistake the agent made along the way.
2109
+ Incorrect steps occur in contiguous failure blocks: one mistake plus every consecutive following step that commits to, compounds, or acts on it.
2110
+ Report each failure block as exactly one finding whose first_step is the block's first incorrect step and whose last_step is its last, covering every consecutive step between them.
2111
+ Set first_step to the first step that commits the mistake, not the step that planned it and not a later step that repeats it.
2112
+ Extend last_step one step at a time, and only while the next step independently satisfies the incorrect-step definition on its own action and its own following observation.
2113
+ Stop at the first step where the agent detects the problem, inspects it, or begins repairing it: a diagnostic probe, a test run that exposes the defect, or a repair action ends the block and is never inside it.
2114
+ A one-step block is a complete and correct answer.
2115
+ Every step inside a block is scored on its own: naming a correct step costs exactly as much as missing an incorrect one, and naming only the first step of a longer block forfeits every unnamed step.
2116
+ Report blocks separated by at least one correct step as separate findings, and never let two blocks overlap.
2117
+ Inspect the complete supplied trace data.
2118
+ Use the final-verification outcome as evidence about the final state, not as a rule for whether earlier steps were incorrect.
2119
+ For each candidate block, inspect every assistant action in it and its following observation.
2120
+ Admit a block only when you can point at the specific evidence it produced: name as consequence_step the step number whose action or observation shows the damage — a failing command, a wrong file state, a repeated failure, or rework the agent had to do because of this block. That step is the block's own last step when its observation already shows the damage, and a later step otherwise.
2121
+ When you cannot name that later step number from the trace you were given, drop the block; a plausible story about why a step looks wrong is not evidence that it was.
2122
+ Judge that consequence from the trajectory itself: a passing final verification is not evidence that a block caused nothing, and a failing final verification is not evidence that any particular block caused it.
2123
+ For every block, decide whether the agent escaped the failure.
2124
+ Mark escape_status "escaped" only when you can name the single later step that fully reversed the block, the agent needed no other step to recover, and nothing after that step revisits the same file, command, or hypothesis; write that step number in the rationale.
2125
+ Mark escape_status "unescaped" in every other case, including whenever you are unsure.
2126
+ A passing final verification never makes a block escaped: the agent may have made the mistake and repaired it over several steps, and those steps are still incorrect.
2127
+ Label a failed command when the assistant caused it through a wrong action or unsupported hypothesis.
2128
+ Label the later corrective action only when that action is itself wrong.
2129
+ Do not label a diagnostic probe merely because it exposes an earlier defect.
2130
+ Do not label a redundant but correct read or search; CodeTraceBench scores unuseful steps separately, and this run scores incorrect steps only.
2131
+ Do not label a step solely because final verification failed.
2132
+ When final verification is unavailable, use only directly observed trajectory evidence.
2133
+ Every step in a reported block MUST be the positive integer n from an existing assistant LLM span named step-<n>.
2134
+ Never select an EVALUATOR, TOOL, CHAIN, final-verification, benchmark-verification, or message-<n> span.
2135
+ Before emitting a finding, inspect every covered span's attributes.content and describe only the actions shown there.
2136
+ Report at most 16 blocks and at most 12 steps in one block; when more candidates than that exist, report the ones you can support with the clearest downstream evidence.
2137
+ When the trajectory has no incorrect steps, return an empty findings array.`;
2138
+ const AGENT_RX_PROMPT = `Analyze exactly one failed agent trajectory.
2139
+ Find the first unrecoverable critical failure, not every later symptom.
2140
+ Inspect the complete supplied trace data.
2141
+ Emit zero findings only when the trace does not contain enough evidence.
2142
+ Otherwise emit exactly one finding.
2143
+ Its category MUST be exactly one of:
2144
+ instruction-plan-adherence-failure
2145
+ invention-of-new-information
2146
+ invalid-invocation
2147
+ misinterpretation-of-tool-output-handoff-failure
2148
+ intent-plan-misalignment
2149
+ underspecified-user-intent
2150
+ intent-not-supported
2151
+ guardrails-triggered
2152
+ system-failure
2153
+ inconclusive
2154
+ Its step is the positive integer n from the first unrecoverable assistant span named step-<n>.`;
2155
+ const AGENT_RX_JSON_CONTRACT = `Each finding must contain only:
2156
+ - "step": a positive integer matching an existing assistant LLM span named step-<n>
2157
+ - "severity": "critical", "high", "medium", "low", or "info"
2158
+ - "claim": one sentence
2159
+ - "confidence": a number from 0 through 1
2160
+ - optional "rationale" and "recommended_action" strings
2161
+ - "category": one allowed failure category listed above`;
2162
+ const CODE_TRACE_JSON_CONTRACT = `Each finding is one contiguous failure block and must contain only:
2163
+ - "first_step": a positive integer, the block's first incorrect step, matching an existing assistant LLM span named step-<n>
2164
+ - "last_step": a positive integer >= first_step, the block's last incorrect step; every step from first_step through last_step must be an existing assistant LLM span, and a block spans at most 12 steps
2165
+ - "consequence_step": a positive integer >= first_step, the step whose action or following observation shows the damage this block caused; it may sit inside the block when the damage is already visible there
2166
+ - "escape_status": "escaped" only when one single later step fully reversed the block and nothing afterwards revisits it, "unescaped" otherwise and whenever you are unsure
2167
+ - "severity": "critical", "high", "medium", "low", or "info"
2168
+ - "claim": one sentence describing the block's failure
2169
+ - "confidence": a number from 0 through 1
2170
+ - optional "rationale" and "recommended_action" strings`;
2171
+ const AGENT_RX_RLM_CONTRACT = `Use the trace tools to inspect the action and its following observation.
2172
+ Emit exactly one finding whose subject is exactly one of the allowed failure categories.
2173
+ Cite exactly one assistant span named step-<n> as trace://<URL-encoded-trace-id>/span/step-<n>.
2174
+ The excerpt must quote the assistant action exactly.`;
2175
+ const CODE_TRACE_RLM_CONTRACT = `Use the trace tools rather than asking for the whole trajectory in the prompt.
2176
+ Keep retrieved trace objects in Python variables.
2177
+ Never print an entire trace, full source file, or more than 12000 characters in one iteration.
2178
+ Build a compact table of assistant step ids, actions, following observations, and final verification.
2179
+ Inspect suspicious steps with viewSpans or searchSpan instead of repeatedly printing the table.
2180
+ This runner emits no JSON fields, so the block is encoded in the finding's subject.
2181
+ Emit exactly one finding per contiguous failure block.
2182
+ Set the finding's subject to incorrect-steps-<first_step>-<last_step>-<escape_status>-consequence-<consequence_step>, using the same four values the task defines; for a block covering only step 7 that the agent never escaped and whose damage shows at step 9, the subject is incorrect-steps-7-7-unescaped-consequence-9.
2183
+ The runner expands the block to one scored step per member and builds every scored citation itself.
2184
+ Cite the block's first step and its last step as trace://<URL-encoded-trace-id>/span/step-<n>, each excerpt an exact quote from that step's own action content.
2185
+ Give the rationale as the concrete downstream evidence visible at the consequence step.
2186
+ Submit as soon as every candidate failure block has a supported verdict.
2187
+ Return no finding for a clean trajectory.`;
2188
+ /** One-shot JSON transport prompt for the direct runner. */
2189
+ function publicBenchmarkSystemPrompt(dataset) {
2190
+ const fieldContract = dataset === "agentrx" ? AGENT_RX_JSON_CONTRACT : CODE_TRACE_JSON_CONTRACT;
2191
+ return `${publicBenchmarkTaskPrompt(dataset)}
2192
+
2193
+ ${fieldContract}
2194
+
2195
+ Return exactly one JSON object with:
2196
+ - "report": a concise evidence-based explanation, at most 4000 characters
2197
+ - "findings": the strict finding array
2198
+ Use an empty findings array when the trace does not support a finding.
2199
+ Do not return a bare array, markdown, trace URIs, copied excerpts, or fields not listed above.
2200
+ The runner constructs exact trace URIs and action previews from each selected step.`;
2201
+ }
2202
+ /** Tool-loop prompt for the recursive runner. Same task, subject-encoded block. */
2203
+ function publicBenchmarkRlmInstructions(dataset) {
2204
+ const outputContract = dataset === "agentrx" ? AGENT_RX_RLM_CONTRACT : CODE_TRACE_RLM_CONTRACT;
2205
+ return `${publicBenchmarkTaskPrompt(dataset)}
2206
+ ${outputContract}`;
2207
+ }
2208
+ function publicBenchmarkTaskPrompt(dataset) {
2209
+ return dataset === "agentrx" ? AGENT_RX_PROMPT : CODE_TRACE_BENCH_ANALYST_PROMPT;
2210
+ }
2211
+ /** Digest of every prompt a runner can send plus the shared transport limits.
2212
+ * Both runner contracts are hashed so an edit to either one changes the digest
2213
+ * a run records, whichever runner executed. */
2214
+ function publicBenchmarkProtocolSha256(dataset) {
2215
+ return sha256Digest(JSON.stringify({
2216
+ dataset,
2217
+ systemPrompt: publicBenchmarkSystemPrompt(dataset),
2218
+ rlmInstructions: publicBenchmarkRlmInstructions(dataset),
2219
+ transport: {
2220
+ attempts: 1,
2221
+ jsonMode: true,
2222
+ thinking: "disabled"
2223
+ },
2224
+ blockLimits: dataset === "agentrx" ? null : {
2225
+ maxBlocks: 16,
2226
+ maxBlockSteps: 12
2227
+ },
2228
+ traceProjectionAttributeByteCaps: TRACE_PROJECTION_ATTRIBUTE_BYTE_CAPS,
2229
+ evidence: {
2230
+ location: "model-selected-positive-integer-assistant-step",
2231
+ uri: "deterministic-trace-uri",
2232
+ excerpt: `exact-action-prefix-512`
2233
+ }
2234
+ }));
2235
+ }
2236
+ //#endregion
2237
+ //#region src/analyst/benchmark-public-adapters.ts
2238
+ function emptyPublicBenchmarkRunner() {
2239
+ return {
2240
+ id: "empty",
2241
+ analyze() {
2242
+ return {
2243
+ findings: [],
2244
+ usage: {
2245
+ calls: 0,
2246
+ tokens: {
2247
+ input: 0,
2248
+ output: 0
2249
+ },
2250
+ cost: {
2251
+ kind: "observed",
2252
+ usd: 0
2253
+ }
2254
+ },
2255
+ metadata: { baseline: "emit-no-findings" }
2256
+ };
2257
+ }
2258
+ };
2259
+ }
2260
+ async function adaptPublicBenchmarkFindings(options) {
2261
+ if (options.dataset === "agentrx") return {
2262
+ findings: adaptAgentRxFindings(options.trajectoryId, options.findings, options.analystId),
2263
+ diagnostics: void 0
2264
+ };
2265
+ return adaptCodeTraceFindings(options.trajectoryId, options.findings, options.analystId, options.store, options.signal);
2266
+ }
2267
+ function adaptAgentRxFindings(trajectoryId, findings, analystId) {
2268
+ if (findings.length === 0) return [];
2269
+ if (findings.length !== 1) throw new Error(`AgentRx model analyst must emit zero or one root cause, received ${findings.length}`);
2270
+ const source = findings[0];
2271
+ if (!source.subject) throw new Error("AgentRx model analyst finding is missing its failure-category subject");
2272
+ const steps = exactFindingSteps(trajectoryId, source);
2273
+ if (steps.length !== 1) throw new Error(`AgentRx model analyst must cite exactly one root-cause step, received ${steps.length}`);
2274
+ const [adapted] = agentRxPredictionsToFindings(trajectoryId, [{
2275
+ failure_case: source.subject,
2276
+ step_number: steps[0],
2277
+ description: source.rationale ?? source.claim
2278
+ }], {
2279
+ analystId,
2280
+ producedAt: source.produced_at,
2281
+ confidence: source.confidence
2282
+ });
2283
+ if (!adapted) throw new Error("AgentRx output adapter produced no root-cause finding");
2284
+ return [{
2285
+ ...adapted,
2286
+ metadata: {
2287
+ ...adapted.metadata,
2288
+ sourceFindingId: source.finding_id
2289
+ }
2290
+ }];
2291
+ }
2292
+ const CODE_TRACE_BLOCK_SUBJECT = /^incorrect-steps-(\d+)-(\d+)-(escaped|unescaped)-consequence-(\d+)$/;
2293
+ async function adaptCodeTraceFindings(trajectoryId, findings, analystId, store, signal) {
2294
+ const clean = findings.filter((finding) => finding.subject === "clean");
2295
+ if (clean.length > 0) {
2296
+ if (findings.length !== 1) throw new Error("CodeTraceBench model analyst mixed a clean verdict with incorrect steps");
2297
+ exactFindingSteps(trajectoryId, clean[0]);
2298
+ return {
2299
+ findings: [],
2300
+ diagnostics: emptyCodeTraceBlockDiagnostics()
2301
+ };
2302
+ }
2303
+ await validateCodeTraceFindingEvidence({
2304
+ trajectoryId,
2305
+ findings,
2306
+ store,
2307
+ ...signal ? { signal } : {}
2308
+ });
2309
+ return expandCodeTraceFailureBlocks({
2310
+ trajectoryId,
2311
+ blocks: findings.map((source) => codeTraceBlockFromFinding(trajectoryId, source)),
2312
+ store,
2313
+ analystId,
2314
+ ...findings[0] ? { producedAt: findings[0].produced_at } : {},
2315
+ ...signal ? { signal } : {}
2316
+ });
2317
+ }
2318
+ function codeTraceBlockFromFinding(trajectoryId, source) {
2319
+ const parsed = CODE_TRACE_BLOCK_SUBJECT.exec(source.subject ?? "");
2320
+ if (!parsed) throw new Error(`CodeTraceBench model finding '${source.finding_id}' must set subject to incorrect-steps-<first>-<last>-<escaped|unescaped>-consequence-<step>, received '${source.subject ?? ""}'`);
2321
+ const firstStep = Number(parsed[1]);
2322
+ const lastStep = Number(parsed[2]);
2323
+ const consequenceStep = Number(parsed[4]);
2324
+ const cited = exactFindingSteps(trajectoryId, source);
2325
+ for (const step of cited) if (step < firstStep || step > lastStep) throw new Error(`CodeTraceBench model finding '${source.finding_id}' cites step ${step} outside its block ${firstStep}-${lastStep}`);
2326
+ return {
2327
+ firstStep,
2328
+ lastStep,
2329
+ consequenceStep,
2330
+ escapeStatus: parsed[3],
2331
+ severity: source.severity,
2332
+ claim: source.claim,
2333
+ confidence: source.confidence,
2334
+ ...source.rationale === void 0 ? {} : { rationale: source.rationale },
2335
+ ...source.recommended_action === void 0 ? {} : { recommendedAction: source.recommended_action },
2336
+ metadata: { sourceFindingId: source.finding_id }
2337
+ };
2338
+ }
2339
+ /**
2340
+ * Expand contiguous failure blocks into one scored finding per member step.
2341
+ *
2342
+ * The official scorer matches on area plus the exact step evidence URI, so
2343
+ * blocks never reach it: every runner reports blocks, and this function turns
2344
+ * them into the per-step findings the benchmark defines.
2345
+ */
2346
+ async function expandCodeTraceFailureBlocks(options) {
2347
+ const diagnostics = emptyCodeTraceBlockDiagnostics();
2348
+ diagnostics.reportedBlocks = options.blocks.length;
2349
+ if (options.blocks.length === 0) return {
2350
+ findings: [],
2351
+ diagnostics
2352
+ };
2353
+ assertCodeTraceBlockShape(options.blocks);
2354
+ const boundarySteps = options.blocks.flatMap((block) => [block.firstStep, block.lastStep]);
2355
+ const derivedSteps = options.blocks.flatMap((block) => [block.consequenceStep, ...interiorSteps(block)]);
2356
+ const evidenceByStep = await resolveAssistantStepEvidence({
2357
+ trajectoryId: options.trajectoryId,
2358
+ steps: boundarySteps,
2359
+ optionalSteps: derivedSteps,
2360
+ store: options.store,
2361
+ ...options.signal ? { signal: options.signal } : {}
2362
+ });
2363
+ const byStep = /* @__PURE__ */ new Map();
2364
+ for (const block of options.blocks) {
2365
+ if (!evidenceByStep.has(block.consequenceStep)) {
2366
+ diagnostics.blocksWithoutConsequenceEvidence.push(block);
2367
+ continue;
2368
+ }
2369
+ if (block.escapeStatus === "escaped") diagnostics.escapedBlocks += 1;
2370
+ for (let step = block.firstStep; step <= block.lastStep; step += 1) {
2371
+ if (!evidenceByStep.has(step)) {
2372
+ diagnostics.unresolvedBlockInteriorSteps.push(step);
2373
+ continue;
2374
+ }
2375
+ if (byStep.has(step)) {
2376
+ diagnostics.overlappingBlockSteps.push(step);
2377
+ continue;
2378
+ }
2379
+ byStep.set(step, block);
2380
+ }
2381
+ }
2382
+ return {
2383
+ findings: [...byStep].sort(([left], [right]) => left - right).map(([step, block]) => makeFinding({
2384
+ analyst_id: options.analystId,
2385
+ area: "incorrect",
2386
+ subject: `incorrect-step-${step}`,
2387
+ claim: `Step ${step} is incorrect. ${block.claim}`,
2388
+ rationale: block.rationale,
2389
+ severity: block.severity,
2390
+ confidence: block.confidence,
2391
+ evidence_refs: [evidenceByStep.get(step)],
2392
+ recommended_action: block.recommendedAction,
2393
+ metadata: {
2394
+ ...block.metadata,
2395
+ block_first_step: block.firstStep,
2396
+ block_last_step: block.lastStep,
2397
+ block_consequence_step: block.consequenceStep,
2398
+ escape_status: block.escapeStatus
2399
+ },
2400
+ ...options.producedAt === void 0 ? {} : { produced_at: options.producedAt },
2401
+ id_basis: `incorrect-step-${step}`
2402
+ })),
2403
+ diagnostics
2404
+ };
2405
+ }
2406
+ function assertCodeTraceBlockShape(blocks) {
2407
+ if (blocks.length > 16) throw new Error(`model reported ${blocks.length} failure blocks; the maximum is 16`);
2408
+ for (const block of blocks) {
2409
+ if (block.lastStep < block.firstStep) throw new Error(`failure block last_step ${block.lastStep} precedes first_step ${block.firstStep}`);
2410
+ const length = block.lastStep - block.firstStep + 1;
2411
+ if (length > 12) throw new Error(`failure block spans ${length} steps; the maximum is 12`);
2412
+ if (block.consequenceStep < block.firstStep) throw new Error(`failure block consequence_step ${block.consequenceStep} precedes first_step ${block.firstStep}`);
2413
+ }
2414
+ }
2415
+ function interiorSteps(block) {
2416
+ const steps = [];
2417
+ for (let step = block.firstStep + 1; step < block.lastStep; step += 1) steps.push(step);
2418
+ return steps;
2419
+ }
2420
+ function emptyCodeTraceBlockDiagnostics() {
2421
+ return {
2422
+ reportedBlocks: 0,
2423
+ escapedBlocks: 0,
2424
+ blocksWithoutConsequenceEvidence: [],
2425
+ unresolvedBlockInteriorSteps: [],
2426
+ overlappingBlockSteps: []
2427
+ };
2428
+ }
2429
+ function exactFindingSteps(trajectoryId, finding) {
2430
+ if (finding.evidence_refs.length === 0) throw new Error(`model finding '${finding.finding_id}' has no step evidence`);
2431
+ const steps = finding.evidence_refs.map((evidence) => {
2432
+ const parsed = codeTraceStepFromEvidence(evidence.uri);
2433
+ if (!parsed || parsed.traceId !== trajectoryId) throw new Error(`model finding '${finding.finding_id}' cites non-case evidence '${evidence.uri}'`);
2434
+ return parsed.step;
2435
+ });
2436
+ return [...new Set(steps)];
2437
+ }
2438
+ //#endregion
2439
+ //#region src/analyst/benchmark-public-types.ts
2440
+ function requiredString(value, field) {
2441
+ const trimmed = value.trim();
2442
+ if (!trimmed) throw new TypeError(`${field} must be a non-empty string`);
2443
+ return trimmed;
2444
+ }
2445
+ function positiveSafeInteger(value, field) {
2446
+ if (!Number.isSafeInteger(value) || value < 1) throw new RangeError(`${field} must be a positive safe integer`);
2447
+ return value;
2448
+ }
2449
+ function safeInteger(value, field) {
2450
+ if (!Number.isSafeInteger(value)) throw new RangeError(`${field} must be a safe integer`);
2451
+ return value;
2452
+ }
2453
+ function isRecord(value) {
2454
+ return typeof value === "object" && value !== null && !Array.isArray(value);
2455
+ }
2456
+ //#endregion
2160
2457
  //#region src/analyst/benchmark-public-data.ts
2161
2458
  const DEFAULT_MAX_PUBLIC_BENCHMARK_LABEL_BYTES = 256 * 1024 * 1024;
2162
2459
  const INPUT_OPEN_FLAGS = constants.O_RDONLY | (constants.O_NOFOLLOW ?? 0);
@@ -2655,15 +2952,6 @@ function fileContext() {
2655
2952
  }
2656
2953
  //#endregion
2657
2954
  //#region src/analyst/benchmark-public-model.ts
2658
- const TRACE_PROJECTION_ATTRIBUTE_BYTE_CAPS = [
2659
- 4096,
2660
- 2048,
2661
- 1024,
2662
- 512,
2663
- 256,
2664
- 128,
2665
- 64
2666
- ];
2667
2955
  /** One-shot JSON baseline. This is not a recursive trace analyst. */
2668
2956
  function createPublicBenchmarkDirectRunner(dataset, config) {
2669
2957
  const model = requiredString(config.model, "model");
@@ -2677,7 +2965,7 @@ function createPublicBenchmarkDirectRunner(dataset, config) {
2677
2965
  responseCacheDir: requiredString(config.durability.responseCacheDir, "durability.responseCacheDir")
2678
2966
  } : void 0;
2679
2967
  const actor = dataset === "agentrx" ? "agentrx-root-cause-localizer" : "codetracebench-step-localizer";
2680
- const outputAdapter = dataset === "agentrx" ? "agentrx-taxonomy-and-root-step" : "codetracebench-incorrect-step";
2968
+ const outputAdapter = dataset === "agentrx" ? "agentrx-taxonomy-and-root-step" : "codetracebench-incorrect-block";
2681
2969
  const llmOptions = {
2682
2970
  baseUrl,
2683
2971
  apiKey,
@@ -2697,6 +2985,7 @@ function createPublicBenchmarkDirectRunner(dataset, config) {
2697
2985
  benchmarkRepetition: String(context.repetition)
2698
2986
  };
2699
2987
  let rawPredictions = [];
2988
+ let rejectedBlocks = [];
2700
2989
  let modelFindings = [];
2701
2990
  let providerModel = model;
2702
2991
  let producedAt;
@@ -2748,6 +3037,7 @@ function createPublicBenchmarkDirectRunner(dataset, config) {
2748
3037
  };
2749
3038
  const response = parsePublicBenchmarkModelResponse(dataset, cached.response);
2750
3039
  rawPredictions = response.findings;
3040
+ rejectedBlocks = response.rejectedBlocks;
2751
3041
  providerModel = cached.metadata.providerModel;
2752
3042
  producedAt = cached.metadata.producedAt;
2753
3043
  modelMetadata = {
@@ -2784,7 +3074,7 @@ function createPublicBenchmarkDirectRunner(dataset, config) {
2784
3074
  ...cacheIdentity,
2785
3075
  callId: providerCallId,
2786
3076
  status: "succeeded",
2787
- response,
3077
+ response: completed.value,
2788
3078
  metadata: {
2789
3079
  providerModel: completed.result.model,
2790
3080
  providerDurationMs: completed.result.durationMs,
@@ -2816,6 +3106,7 @@ function createPublicBenchmarkDirectRunner(dataset, config) {
2816
3106
  if (!paid.succeeded) throw paid.error;
2817
3107
  const response = paid.value.response;
2818
3108
  rawPredictions = response.findings;
3109
+ rejectedBlocks = response.rejectedBlocks;
2819
3110
  providerModel = paid.value.result.model;
2820
3111
  producedAt = paid.value.producedAt;
2821
3112
  modelMetadata = {
@@ -2828,7 +3119,7 @@ function createPublicBenchmarkDirectRunner(dataset, config) {
2828
3119
  cost: costReceiptMetadata(paid.receipt)
2829
3120
  };
2830
3121
  }
2831
- modelFindings = await publicBenchmarkPredictionsToFindings({
3122
+ const converted = await publicBenchmarkPredictionsToFindings({
2832
3123
  dataset,
2833
3124
  trajectoryId,
2834
3125
  predictions: rawPredictions,
@@ -2838,6 +3129,14 @@ function createPublicBenchmarkDirectRunner(dataset, config) {
2838
3129
  producedAt: requiredString(producedAt ?? "", "finding producedAt"),
2839
3130
  ...context.signal ? { signal: context.signal } : {}
2840
3131
  });
3132
+ modelFindings = converted.findings;
3133
+ if (converted.diagnostics) modelMetadata = {
3134
+ ...modelMetadata,
3135
+ blockDiagnostics: {
3136
+ ...converted.diagnostics,
3137
+ rejectedBlocks
3138
+ }
3139
+ };
2841
3140
  if (dataset === "codetracebench") await validateCodeTraceFindingEvidence({
2842
3141
  trajectoryId,
2843
3142
  findings: modelFindings,
@@ -2935,7 +3234,7 @@ const ModelSeveritySchema = z.enum([
2935
3234
  "low",
2936
3235
  "info"
2937
3236
  ]);
2938
- const PublicBenchmarkPredictionSchema = z.object({
3237
+ const AgentRxPredictionSchema = z.object({
2939
3238
  step: z.number().int().positive(),
2940
3239
  severity: ModelSeveritySchema,
2941
3240
  claim: z.string().min(1),
@@ -2943,6 +3242,34 @@ const PublicBenchmarkPredictionSchema = z.object({
2943
3242
  rationale: z.string().min(1).optional(),
2944
3243
  recommended_action: z.string().min(1).optional()
2945
3244
  }).strict();
3245
+ const CodeTraceBlockPredictionSchema = z.object({
3246
+ first_step: z.number().int().positive(),
3247
+ last_step: z.number().int().positive(),
3248
+ consequence_step: z.number().int().positive(),
3249
+ escape_status: z.enum(["escaped", "unescaped"]),
3250
+ severity: ModelSeveritySchema,
3251
+ claim: z.string().min(1),
3252
+ confidence: z.number().min(0).max(1),
3253
+ rationale: z.string().min(1).optional(),
3254
+ recommended_action: z.string().min(1).optional()
3255
+ }).strict().superRefine((block, ctx) => {
3256
+ if (block.last_step < block.first_step) {
3257
+ ctx.addIssue({
3258
+ code: z.ZodIssueCode.custom,
3259
+ message: `failure block last_step ${block.last_step} precedes first_step ${block.first_step}`
3260
+ });
3261
+ return;
3262
+ }
3263
+ const length = block.last_step - block.first_step + 1;
3264
+ if (length > 12) ctx.addIssue({
3265
+ code: z.ZodIssueCode.custom,
3266
+ message: `failure block spans ${length} steps; the maximum is 12`
3267
+ });
3268
+ if (block.consequence_step < block.first_step) ctx.addIssue({
3269
+ code: z.ZodIssueCode.custom,
3270
+ message: `failure block consequence_step ${block.consequence_step} precedes first_step ${block.first_step}`
3271
+ });
3272
+ });
2946
3273
  const AgentRxCategorySchema = z.enum([
2947
3274
  "instruction-plan-adherence-failure",
2948
3275
  "invention-of-new-information",
@@ -2955,28 +3282,52 @@ const AgentRxCategorySchema = z.enum([
2955
3282
  "system-failure",
2956
3283
  "inconclusive"
2957
3284
  ]);
2958
- const CodeTraceModelResponseSchema = z.object({
3285
+ const CodeTraceModelResponseEnvelopeSchema = z.object({
2959
3286
  report: z.string().min(1).max(4e3),
2960
- findings: z.array(PublicBenchmarkPredictionSchema).max(200)
3287
+ findings: z.array(z.unknown()).max(16)
2961
3288
  }).strict();
2962
3289
  const AgentRxModelResponseSchema = z.object({
2963
3290
  report: z.string().min(1).max(4e3),
2964
- findings: z.array(PublicBenchmarkPredictionSchema.extend({ category: AgentRxCategorySchema }).strict()).max(1)
3291
+ findings: z.array(AgentRxPredictionSchema.extend({ category: AgentRxCategorySchema }).strict()).max(1)
2965
3292
  }).strict();
2966
3293
  function parsePublicBenchmarkModelResponse(dataset, value) {
2967
- return dataset === "agentrx" ? AgentRxModelResponseSchema.parse(value) : CodeTraceModelResponseSchema.parse(value);
3294
+ if (dataset === "agentrx") return {
3295
+ ...AgentRxModelResponseSchema.parse(value),
3296
+ rejectedBlocks: []
3297
+ };
3298
+ const envelope = CodeTraceModelResponseEnvelopeSchema.parse(value);
3299
+ const findings = [];
3300
+ const rejectedBlocks = [];
3301
+ for (const [index, block] of envelope.findings.entries()) {
3302
+ const parsed = CodeTraceBlockPredictionSchema.safeParse(block);
3303
+ if (parsed.success) {
3304
+ findings.push(parsed.data);
3305
+ continue;
3306
+ }
3307
+ rejectedBlocks.push(`block ${index}: ${parsed.error.issues.map((issue) => `${issue.path.join(".") || "<root>"} ${issue.message}`).join("; ")}`);
3308
+ }
3309
+ if (findings.length === 0 && envelope.findings.length > 0) throw new ValidationError(`every reported failure block was malformed: ${rejectedBlocks.join(" | ")}`);
3310
+ return {
3311
+ report: envelope.report,
3312
+ findings,
3313
+ rejectedBlocks
3314
+ };
2968
3315
  }
2969
3316
  async function publicBenchmarkPredictionsToFindings(options) {
2970
- if (options.predictions.length === 0) return [];
2971
- const evidenceByStep = await resolveAssistantStepEvidence({
2972
- trajectoryId: options.trajectoryId,
2973
- steps: options.predictions.map((prediction) => prediction.step),
2974
- store: options.store,
2975
- ...options.signal ? { signal: options.signal } : {}
2976
- });
3317
+ if (options.predictions.length === 0 && options.dataset === "agentrx") return {
3318
+ findings: [],
3319
+ diagnostics: void 0
3320
+ };
2977
3321
  if (options.dataset === "agentrx") {
2978
3322
  const prediction = options.predictions[0];
3323
+ if (!("step" in prediction)) throw new Error("AgentRx model output must name a single root-cause step");
2979
3324
  if (!prediction.category) throw new Error("AgentRx model output is missing its failure category");
3325
+ const evidenceByStep = await resolveAssistantStepEvidence({
3326
+ trajectoryId: options.trajectoryId,
3327
+ steps: [prediction.step],
3328
+ store: options.store,
3329
+ ...options.signal ? { signal: options.signal } : {}
3330
+ });
2980
3331
  const [finding] = agentRxPredictionsToFindings(options.trajectoryId, [{
2981
3332
  failure_case: prediction.category,
2982
3333
  step_number: prediction.step,
@@ -2987,69 +3338,44 @@ async function publicBenchmarkPredictionsToFindings(options) {
2987
3338
  confidence: prediction.confidence
2988
3339
  });
2989
3340
  if (!finding) throw new Error("AgentRx output adapter produced no root-cause finding");
2990
- return [{
2991
- ...finding,
2992
- evidence_refs: [evidenceByStep.get(prediction.step)],
3341
+ return {
3342
+ findings: [{
3343
+ ...finding,
3344
+ evidence_refs: [evidenceByStep.get(prediction.step)],
3345
+ metadata: {
3346
+ ...finding.metadata,
3347
+ model: options.providerModel
3348
+ }
3349
+ }],
3350
+ diagnostics: void 0
3351
+ };
3352
+ }
3353
+ const blocks = options.predictions.map((prediction) => {
3354
+ if (!("first_step" in prediction)) throw new Error("CodeTraceBench model output must report first_step/last_step failure blocks");
3355
+ return {
3356
+ firstStep: prediction.first_step,
3357
+ lastStep: prediction.last_step,
3358
+ consequenceStep: prediction.consequence_step,
3359
+ escapeStatus: prediction.escape_status,
3360
+ severity: prediction.severity,
3361
+ claim: prediction.claim,
3362
+ confidence: prediction.confidence,
3363
+ ...prediction.rationale === void 0 ? {} : { rationale: prediction.rationale },
3364
+ ...prediction.recommended_action === void 0 ? {} : { recommendedAction: prediction.recommended_action },
2993
3365
  metadata: {
2994
- ...finding.metadata,
3366
+ analysis_mode: "direct-baseline",
2995
3367
  model: options.providerModel
2996
3368
  }
2997
- }];
2998
- }
2999
- const byStep = /* @__PURE__ */ new Map();
3000
- for (const prediction of options.predictions) if (!byStep.has(prediction.step)) byStep.set(prediction.step, prediction);
3001
- return [...byStep].sort(([left], [right]) => left - right).map(([step, prediction]) => makeFinding({
3002
- analyst_id: options.analystId,
3003
- area: "incorrect",
3004
- subject: `incorrect-step-${step}`,
3005
- claim: `Step ${step} is incorrect. ${prediction.claim}`,
3006
- rationale: prediction.rationale,
3007
- severity: prediction.severity,
3008
- confidence: prediction.confidence,
3009
- evidence_refs: [evidenceByStep.get(step)],
3010
- recommended_action: prediction.recommended_action,
3011
- metadata: {
3012
- analysis_mode: "direct-baseline",
3013
- model: options.providerModel
3014
- },
3015
- produced_at: options.producedAt,
3016
- id_basis: `incorrect-step-${step}`
3017
- }));
3018
- }
3019
- function publicBenchmarkSystemPrompt(dataset) {
3020
- return `${dataset === "agentrx" ? AGENT_RX_PROMPT : CODE_TRACE_BENCH_ANALYST_PROMPT}
3021
-
3022
- Each finding must contain only:
3023
- - "step": a positive integer matching an existing assistant LLM span named step-<n>
3024
- - "severity": "critical", "high", "medium", "low", or "info"
3025
- - "claim": one sentence
3026
- - "confidence": a number from 0 through 1
3027
- - optional "rationale" and "recommended_action" strings
3028
- ${dataset === "agentrx" ? `- "category": one allowed failure category listed above` : ""}
3029
-
3030
- Return exactly one JSON object with:
3031
- - "report": a concise evidence-based explanation, at most 4000 characters
3032
- - "findings": the strict finding array
3033
- Use an empty findings array when the trace does not support a finding.
3034
- Do not return a bare array, markdown, trace URIs, copied excerpts, or fields not listed above.
3035
- The runner constructs exact trace URIs and action previews from each selected step.`;
3036
- }
3037
- function publicBenchmarkProtocolSha256(dataset) {
3038
- return sha256Digest(JSON.stringify({
3039
- dataset,
3040
- systemPrompt: publicBenchmarkSystemPrompt(dataset),
3041
- transport: {
3042
- attempts: 1,
3043
- jsonMode: true,
3044
- thinking: "disabled"
3045
- },
3046
- traceProjectionAttributeByteCaps: TRACE_PROJECTION_ATTRIBUTE_BYTE_CAPS,
3047
- evidence: {
3048
- location: "model-selected-positive-integer-assistant-step",
3049
- uri: "deterministic-trace-uri",
3050
- excerpt: `exact-action-prefix-512`
3051
- }
3052
- }));
3369
+ };
3370
+ });
3371
+ return expandCodeTraceFailureBlocks({
3372
+ trajectoryId: options.trajectoryId,
3373
+ blocks,
3374
+ store: options.store,
3375
+ analystId: options.analystId,
3376
+ producedAt: options.producedAt,
3377
+ ...options.signal ? { signal: options.signal } : {}
3378
+ });
3053
3379
  }
3054
3380
  async function prepareSingleTraceContext(store, context) {
3055
3381
  const storeContext = context.signal ? { signal: context.signal } : void 0;
@@ -3069,40 +3395,6 @@ async function prepareSingleTraceContext(store, context) {
3069
3395
  });
3070
3396
  }
3071
3397
  }
3072
- const AGENT_RX_PROMPT = `Analyze exactly one failed agent trajectory.
3073
- Find the first unrecoverable critical failure, not every later symptom.
3074
- Inspect the complete supplied trace data.
3075
- Emit zero findings only when the trace does not contain enough evidence.
3076
- Otherwise emit exactly one finding.
3077
- Its category MUST be exactly one of:
3078
- instruction-plan-adherence-failure
3079
- invention-of-new-information
3080
- invalid-invocation
3081
- misinterpretation-of-tool-output-handoff-failure
3082
- intent-plan-misalignment
3083
- underspecified-user-intent
3084
- intent-not-supported
3085
- guardrails-triggered
3086
- system-failure
3087
- inconclusive
3088
- Its step is the positive integer n from the first unrecoverable assistant span named step-<n>.`;
3089
- const CODE_TRACE_BENCH_ANALYST_PROMPT = `Analyze exactly one coding-agent trajectory and its attached final verification.
3090
- Your task is the CodeTraceBench incorrect-step task: identify every wrong state-changing action, bad hypothesis that drives an action, and regression.
3091
- An incorrect step remains incorrect when the agent later recovers or the final verification passes.
3092
- Inspect the complete supplied trace data.
3093
- Use the final-verification outcome as evidence about the final state, not as a rule for whether earlier steps were incorrect.
3094
- For each candidate, inspect the assistant action and its following observation.
3095
- Label a failed command when the assistant caused it through a wrong action or unsupported hypothesis.
3096
- Label the later corrective action only when that action is itself wrong.
3097
- Do not label a diagnostic probe merely because it exposes an earlier defect.
3098
- Do not label a redundant but correct read or search; CodeTraceBench scores unuseful steps separately, and this run scores incorrect steps only.
3099
- Do not label a step solely because final verification failed.
3100
- When final verification is unavailable, use only directly observed trajectory evidence.
3101
- Emit one finding per incorrect assistant step.
3102
- Each finding's step MUST be the positive integer n from an existing assistant LLM span named step-<n>.
3103
- Never select an EVALUATOR, TOOL, CHAIN, final-verification, benchmark-verification, or message-<n> span.
3104
- Before emitting a finding, inspect its candidate span's attributes.content and describe only the action shown there.
3105
- When the trajectory has no incorrect steps, return an empty findings array.`;
3106
3398
  function trajectoryIdFromCaseId$1(dataset, caseId) {
3107
3399
  const prefix = dataset === "agentrx" ? "agentrx:" : "codetrace:";
3108
3400
  if (!caseId.startsWith(prefix) || caseId.length === prefix.length) throw new Error(`unexpected ${dataset} benchmark case id '${caseId}'`);
@@ -3110,34 +3402,6 @@ function trajectoryIdFromCaseId$1(dataset, caseId) {
3110
3402
  }
3111
3403
  //#endregion
3112
3404
  //#region src/analyst/benchmark-public-rlm.ts
3113
- const AGENT_RX_RLM_INSTRUCTIONS = `Analyze exactly one failed agent trajectory.
3114
- Find the first unrecoverable critical failure, not every later symptom.
3115
- Use the trace tools to inspect the action and its following observation.
3116
- Emit zero findings only when evidence does not support a root cause.
3117
- Otherwise emit exactly one finding whose subject is exactly one of:
3118
- instruction-plan-adherence-failure
3119
- invention-of-new-information
3120
- invalid-invocation
3121
- misinterpretation-of-tool-output-handoff-failure
3122
- intent-plan-misalignment
3123
- underspecified-user-intent
3124
- intent-not-supported
3125
- guardrails-triggered
3126
- system-failure
3127
- inconclusive
3128
- Cite exactly one assistant span named step-<n> as trace://<trace-id>/span/step-<n>.
3129
- The excerpt must quote the assistant action exactly.`;
3130
- const CODE_TRACE_RLM_INSTRUCTIONS = `${CODE_TRACE_BENCH_ANALYST_PROMPT}
3131
- Use the trace tools rather than asking for the whole trajectory in the prompt.
3132
- Keep retrieved trace objects in Python variables.
3133
- Never print an entire trace, full source file, or more than 12000 characters in one iteration.
3134
- Build a compact table of assistant step ids, actions, following observations, and final verification.
3135
- Inspect suspicious steps with viewSpans or searchSpan instead of repeatedly printing the table.
3136
- Submit as soon as every state-changing assistant step has a supported verdict.
3137
- For each incorrect step, set subject to incorrect-step-<n>.
3138
- Cite the assistant span as trace://<URL-encoded-trace-id>/span/step-<n>.
3139
- The evidence excerpt must be an exact quote from that span's action content.
3140
- Return no finding for a clean trajectory.`;
3141
3405
  /** Public benchmark candidate that runs the actual recursive trace analyst. */
3142
3406
  function createPublicBenchmarkRlmRunner(dataset, config) {
3143
3407
  const costLedger = config.costLedger ?? new CostLedger();
@@ -3205,20 +3469,22 @@ function createPublicBenchmarkRlmRunner(dataset, config) {
3205
3469
  },
3206
3470
  produced_at: producedAt
3207
3471
  }));
3208
- const findings = adaptPublicBenchmarkFindings(dataset, trajectoryId, rawFindings, "dspy-rlm");
3209
- if (dataset === "codetracebench") await validateCodeTraceFindingEvidence({
3472
+ const adapted = await adaptPublicBenchmarkFindings({
3473
+ dataset,
3210
3474
  trajectoryId,
3211
- findings,
3475
+ findings: rawFindings,
3476
+ analystId: "dspy-rlm",
3212
3477
  store: input.traceStore,
3213
3478
  ...context.signal ? { signal: context.signal } : {}
3214
3479
  });
3215
3480
  return {
3216
- findings,
3481
+ findings: adapted.findings,
3217
3482
  usage,
3218
3483
  metadata: {
3219
3484
  analysisMode: "recursive",
3220
3485
  engine: "dspy-rlm",
3221
3486
  protocolSha256: publicBenchmarkProtocolSha256(dataset),
3487
+ ...adapted.diagnostics ? { blockDiagnostics: adapted.diagnostics } : {},
3222
3488
  answer: completed.answer,
3223
3489
  trajectory: completed.trajectory,
3224
3490
  modelCalls: completed.modelCalls,
@@ -3250,7 +3516,7 @@ function publicBenchmarkDefinition(dataset, limits) {
3250
3516
  area: dataset === "agentrx" ? "root-cause" : "incorrect",
3251
3517
  version: "1.0.0",
3252
3518
  question: dataset === "agentrx" ? "What is the first unrecoverable root cause in this failed trajectory?" : "Which assistant steps are incorrect under the CodeTraceBench definition?",
3253
- instructions: dataset === "agentrx" ? AGENT_RX_RLM_INSTRUCTIONS : CODE_TRACE_RLM_INSTRUCTIONS,
3519
+ instructions: publicBenchmarkRlmInstructions(dataset),
3254
3520
  toolGroup: "singleTrace",
3255
3521
  limits
3256
3522
  };
@@ -3341,7 +3607,7 @@ function createRunIdentity(config, prepared) {
3341
3607
  analystProtocolSha256: publicBenchmarkProtocolSha256(config.dataset),
3342
3608
  implementationSha256: ANALYST_BENCHMARK_IMPLEMENTATION_SHA256,
3343
3609
  dependencyLockSha256: ANALYST_BENCHMARK_DEPENDENCY_LOCK_SHA256,
3344
- runnerIds: ["empty", "dspy-rlm"]
3610
+ runnerIds: ["empty", config.analyst]
3345
3611
  },
3346
3612
  inputs: {
3347
3613
  labelsSha256: prepared.labelsSha256,
@@ -3512,7 +3778,7 @@ function createObservationAppender(path, runIdentitySha256, progress) {
3512
3778
  return write;
3513
3779
  };
3514
3780
  }
3515
- async function readProgress(path, runIdentitySha256, caseIds, repetitions) {
3781
+ async function readProgress(path, runIdentitySha256, caseIds, repetitions, analystRunnerId) {
3516
3782
  const rawLines = (await readRegularFile(path, "benchmark observation log")).split("\n");
3517
3783
  if (rawLines.at(-1) === "") rawLines.pop();
3518
3784
  const observations = [];
@@ -3546,7 +3812,7 @@ async function readProgress(path, runIdentitySha256, caseIds, repetitions) {
3546
3812
  previousRowSha256: parsed.previousRowSha256,
3547
3813
  observation
3548
3814
  }) !== parsed.rowSha256) throw new Error(`benchmark observation row ${index + 1} digest does not match its contents`);
3549
- if (!allowedCases.has(observation.caseId) || observation.runnerId !== "empty" && observation.runnerId !== "dspy-rlm" || observation.repetition >= repetitions || observation.executionIndex >= plannedObservationCount) throw new Error(`benchmark observation row ${index + 1} does not match a planned case, runner, and repetition`);
3815
+ if (!allowedCases.has(observation.caseId) || observation.runnerId !== "empty" && observation.runnerId !== analystRunnerId || observation.repetition >= repetitions || observation.executionIndex >= plannedObservationCount) throw new Error(`benchmark observation row ${index + 1} does not match a planned case, runner, and repetition`);
3550
3816
  if (executionIndexes.has(observation.executionIndex)) throw new Error(`duplicate benchmark executionIndex ${observation.executionIndex} at line ${index + 1}`);
3551
3817
  observations.push(observation);
3552
3818
  seen.add(key);
@@ -3991,7 +4257,7 @@ function assertCompletedArtifactMatchesRun(artifact, manifest, observations, pre
3991
4257
  if (canonicalJson(artifact.inputs) !== canonicalJson(expectedInputs)) throw new Error("completed benchmark result inputs do not match the run manifest");
3992
4258
  const provenance = artifact.result.provenance;
3993
4259
  const expectedDatasetId = config.dataset === "agentrx" ? "microsoft/AgentRx" : "NJU-LINK/CodeTraceBench";
3994
- const expectedOutputAdapter = config.dataset === "agentrx" ? "agentrx-taxonomy-and-root-step" : "codetracebench-incorrect-step";
4260
+ const expectedOutputAdapter = config.dataset === "agentrx" ? "agentrx-taxonomy-and-root-step" : "codetracebench-incorrect-block";
3995
4261
  if (provenance.id !== `${config.dataset}-real-model-analyst` || provenance.startedAt !== manifest.createdAt || !Number.isFinite(Date.parse(provenance.endedAt)) || Date.parse(provenance.endedAt) < Date.parse(provenance.startedAt) || canonicalJson(provenance.dataset) !== canonicalJson({
3996
4262
  id: expectedDatasetId,
3997
4263
  revision: config.datasetRevision,
@@ -4001,7 +4267,7 @@ function assertCompletedArtifactMatchesRun(artifact, manifest, observations, pre
4001
4267
  if (canonicalJson(artifact.result.summaries) !== canonicalJson(expectedSummaries)) throw new Error("completed benchmark summaries do not match durable observations");
4002
4268
  const expectedComparisons = [compareAnalystRunners(artifact.result, {
4003
4269
  baselineRunnerId: "empty",
4004
- candidateRunnerId: "dspy-rlm",
4270
+ candidateRunnerId: config.runnerIds[1],
4005
4271
  seed: config.seed
4006
4272
  })];
4007
4273
  if (canonicalJson(artifact.comparisons) !== canonicalJson(expectedComparisons)) throw new Error("completed benchmark comparisons do not match durable observations");
@@ -4134,7 +4400,7 @@ async function executeAnalystBenchmarkCommand(config, dependencies) {
4134
4400
  const localIdentitySha256 = digestCanonical(localReceipt.local);
4135
4401
  const identitySha256 = digestCanonical(identity);
4136
4402
  const manifest = config.resume ? await readAndValidateResumeFiles(paths, identity, identitySha256, localIdentitySha256, localReceipt) : await initializeRunFiles(paths, identity, identitySha256, localIdentitySha256, localReceipt);
4137
- const progress = await readProgress(paths.observations, manifest.identitySha256, prepared.selectedCaseIds, config.repetitions);
4403
+ const progress = await readProgress(paths.observations, manifest.identitySha256, prepared.selectedCaseIds, config.repetitions, config.analyst);
4138
4404
  const costLedger = createRunCostLedger({
4139
4405
  storage: fsCampaignStorage(),
4140
4406
  runDir: paths.directory,
@@ -4147,10 +4413,10 @@ async function executeAnalystBenchmarkCommand(config, dependencies) {
4147
4413
  const markdown = renderArtifactMarkdown(artifact);
4148
4414
  await writeExclusiveOrVerify(paths.report, markdown);
4149
4415
  printSuccessSummary(artifact, paths);
4150
- return benchmarkExitCode(artifact.result);
4416
+ return benchmarkExitCode(artifact.result, config.analyst);
4151
4417
  }
4152
4418
  if (await regularFileExists(paths.report)) throw new Error(`benchmark report exists without a completed result; refusing ambiguous resume: ${paths.report}`);
4153
- const createAnalystRunner = dependencies.createAnalystRunner ?? ((dataset, model) => createPublicBenchmarkRlmRunner(dataset, model));
4419
+ const createAnalystRunner = dependencies.createAnalystRunner ?? ((dataset, model) => config.analyst === "direct" ? createPublicBenchmarkDirectRunner(dataset, model) : createPublicBenchmarkRlmRunner(dataset, model));
4154
4420
  const runners = [emptyPublicBenchmarkRunner(), createAnalystRunner(config.dataset, {
4155
4421
  ...config.model,
4156
4422
  costLedger,
@@ -4172,7 +4438,7 @@ async function executeAnalystBenchmarkCommand(config, dependencies) {
4172
4438
  initialObservations: progress.observations,
4173
4439
  signal: runAbort.signal,
4174
4440
  onObservation: async (observation) => {
4175
- assertObservationAccountingComplete(observation, costLedger);
4441
+ assertObservationAccountingComplete(observation, costLedger, config.analyst);
4176
4442
  await appendObservation(observation);
4177
4443
  },
4178
4444
  resolveEvidence: traceStoreEvidenceResolver((input) => {
@@ -4193,7 +4459,7 @@ async function executeAnalystBenchmarkCommand(config, dependencies) {
4193
4459
  },
4194
4460
  metadata: {
4195
4461
  model: config.model.model,
4196
- outputAdapter: config.dataset === "agentrx" ? "agentrx-taxonomy-and-root-step" : "codetracebench-incorrect-step",
4462
+ outputAdapter: config.dataset === "agentrx" ? "agentrx-taxonomy-and-root-step" : "codetracebench-incorrect-block",
4197
4463
  caseSelection: prepared.selection.method,
4198
4464
  caseSelectionSeed: config.seed,
4199
4465
  selectionStratified: prepared.selection.stratified,
@@ -4211,11 +4477,11 @@ async function executeAnalystBenchmarkCommand(config, dependencies) {
4211
4477
  }
4212
4478
  assertCostLedgerFinalizable(costLedger);
4213
4479
  result.provenance.startedAt = manifest.createdAt;
4214
- const persisted = await readProgress(paths.observations, manifest.identitySha256, prepared.selectedCaseIds, config.repetitions);
4480
+ const persisted = await readProgress(paths.observations, manifest.identitySha256, prepared.selectedCaseIds, config.repetitions, config.analyst);
4215
4481
  assertSameObservations(result.observations, persisted.observations);
4216
4482
  const comparisons = [compareAnalystRunners(result, {
4217
4483
  baselineRunnerId: "empty",
4218
- candidateRunnerId: "dspy-rlm",
4484
+ candidateRunnerId: config.analyst,
4219
4485
  seed: config.seed
4220
4486
  })];
4221
4487
  const codeTraceCalibration = config.dataset === "codetracebench" ? summarizeCodeTraceCalibration(result) : void 0;
@@ -4260,7 +4526,7 @@ async function executeAnalystBenchmarkCommand(config, dependencies) {
4260
4526
  await writeExclusiveOrVerify(paths.result, `${JSON.stringify(artifact, null, 2)}\n`);
4261
4527
  await writeExclusiveOrVerify(paths.report, markdown);
4262
4528
  printSuccessSummary(artifact, paths);
4263
- return benchmarkExitCode(result);
4529
+ return benchmarkExitCode(result, config.analyst);
4264
4530
  }
4265
4531
  const NON_SCORABLE_COST_ERRORS = /* @__PURE__ */ new Set([
4266
4532
  "CostAccountingIncompleteError",
@@ -4270,9 +4536,9 @@ const NON_SCORABLE_COST_ERRORS = /* @__PURE__ */ new Set([
4270
4536
  "CostReceiptCaptureError",
4271
4537
  "CostReservationExceededError"
4272
4538
  ]);
4273
- function assertObservationAccountingComplete(observation, costLedger) {
4539
+ function assertObservationAccountingComplete(observation, costLedger, analystRunnerId) {
4274
4540
  if (observation.error && NON_SCORABLE_COST_ERRORS.has(observation.error.class)) throw new CostAccountingIncompleteError(`Analyst benchmark stopped before scoring: ${observation.error.message}`);
4275
- if (observation.runnerId !== "dspy-rlm") return;
4541
+ if (observation.runnerId !== analystRunnerId) return;
4276
4542
  const summary = costLedger.summary({
4277
4543
  channel: "analyst",
4278
4544
  tags: {
@@ -4302,6 +4568,9 @@ Run the recursive DSPy trace analyst against public AgentRx or CodeTraceBench la
4302
4568
 
4303
4569
  Required:
4304
4570
  --dataset agentrx|codetracebench
4571
+ --analyst dspy-rlm|direct Scored analyst. Default: dspy-rlm.
4572
+ 'direct' is the retired one-shot runner that
4573
+ produced the published evidence.
4305
4574
  --labels <dataset.json|dataset.jsonl>
4306
4575
  --trace-dir <one-trace-per-file OTLP JSONL directory>
4307
4576
  --artifact-dir <extracted artifact root> Required for CodeTraceBench
@@ -4344,8 +4613,11 @@ function parseCommandConfig(argv, env) {
4344
4613
  if (!apiKey) throw new Error(`--api-key-env points to an empty or missing variable: ${apiKeyEnv}`);
4345
4614
  const maxCostUsd = positiveFiniteFlag(flags, "max-cost-usd", 5);
4346
4615
  const python = flags.get("python")?.trim();
4616
+ const analyst = flags.get("analyst")?.trim() ?? "dspy-rlm";
4617
+ if (analyst !== "dspy-rlm" && analyst !== "direct") throw new Error("--analyst must be 'dspy-rlm' or 'direct'");
4347
4618
  return {
4348
4619
  dataset,
4620
+ analyst,
4349
4621
  labelsPath: requiredFlag(flags, "labels"),
4350
4622
  traceDir: requiredFlag(flags, "trace-dir"),
4351
4623
  ...artifactDir ? { artifactDir } : {},
@@ -4396,6 +4668,7 @@ function parseFlags(argv) {
4396
4668
  const KNOWN_FLAGS = /* @__PURE__ */ new Set([
4397
4669
  "resume",
4398
4670
  "dataset",
4671
+ "analyst",
4399
4672
  "labels",
4400
4673
  "trace-dir",
4401
4674
  "artifact-dir",
@@ -4519,8 +4792,8 @@ function renderArtifactMarkdown(artifact) {
4519
4792
  const verificationMarkdown = artifact.inputs.dataset === "codetracebench" ? `\n\n${renderVerificationAvailability(artifact.inputs.verificationAvailability)}` : "";
4520
4793
  return `${renderAnalystBenchmarkMarkdown(artifact.result, artifact.comparisons).trimEnd()}${calibrationMarkdown}${verificationMarkdown}\n\n${renderSelectionMarkdown(artifact.inputs.selection.report)}\n`;
4521
4794
  }
4522
- function benchmarkExitCode(result) {
4523
- return result.summaries.find((summary) => summary.runnerId === "dspy-rlm")?.failedRuns ? 2 : 0;
4795
+ function benchmarkExitCode(result, analystRunnerId) {
4796
+ return result.summaries.find((summary) => summary.runnerId === analystRunnerId)?.failedRuns ? 2 : 0;
4524
4797
  }
4525
4798
  function printSuccessSummary(artifact, paths) {
4526
4799
  const failures = artifact.result.summaries.reduce((total, summary) => total + summary.failedRuns, 0);
@@ -4532,6 +4805,6 @@ function shellQuote(value) {
4532
4805
  return /^[a-zA-Z0-9_./:@%+=,-]+$/.test(value) ? value : `'${value.replaceAll("'", "'\\''")}'`;
4533
4806
  }
4534
4807
  //#endregion
4535
- export { ANALYST_BENCHMARK_IMPLEMENTATION_FILES as A, summarizeAgentRxCalibration as B, ANALYST_BENCHMARK_DEPENDENCY_LOCK_DIGEST_ALGORITHM as C, ANALYST_BENCHMARK_EVIDENCE_IMPLEMENTATION_SHA256 as D, ANALYST_BENCHMARK_EVIDENCE_DEPENDENCY_LOCK_SHA256 as E, ANALYST_BENCHMARK_LOCAL_RECEIPT_FILE as F, normalizeAgentRxCategory as G, codeTracerPredictionsToFindings as H, ANALYST_BENCHMARK_MANIFEST_FILE as I, roundAgentRxStep as K, ANALYST_BENCHMARK_OBSERVATIONS_FILE as L, analystBenchmarkDependencyLockDigest as M, analystBenchmarkImplementationDigest as N, ANALYST_BENCHMARK_EVIDENCE_PACKAGE_VERSION as O, ANALYST_BENCHMARK_COST_LEDGER_FILE as P, AGENT_RX_UPSTREAM_REVISION as R, emptyPublicBenchmarkRunner as S, ANALYST_BENCHMARK_DEPENDENCY_LOCK_SHA256 as T, agentRxBenchmarkCase as U, codeTraceBenchCase as V, agentRxPredictionsToFindings as W, DEFAULT_MAX_VERIFICATION_ARTIFACT_BYTES as _, renderCodeTraceCalibrationMarkdown as a, parseVerificationOutcome as b, createPublicBenchmarkRlmRunner as c, publicBenchmarkProtocolSha256 as d, loadPublicBenchmarkRows as f, selectPublicBenchmarkRows as g, publicBenchmarkSelectionReport as h, readAnalystBenchmarkArtifact as i, ANALYST_BENCHMARK_IMPLEMENTATION_SHA256 as j, ANALYST_BENCHMARK_IMPLEMENTATION_DIGEST_ALGORITHM as k, CODE_TRACE_BENCH_ANALYST_PROMPT as l, publicBenchmarkDistributions as m, runAnalystBenchmarkCommand as n, summarizeCodeTraceCalibration as o, preparePublicAnalystBenchmark as p, normalizeBenchmarkLabel as q, renderAnalystBenchmarkMarkdown as r, compareAnalystRunners as s, ANALYST_BENCHMARK_HELP as t, createPublicBenchmarkDirectRunner as u, appendVerificationArtifactsToOtlp as v, ANALYST_BENCHMARK_DEPENDENCY_LOCK_FILES as w, adaptPublicBenchmarkFindings as x, loadCodeTraceVerificationArtifacts as y, renderAgentRxCalibrationMarkdown as z };
4808
+ export { ANALYST_BENCHMARK_DEPENDENCY_LOCK_SHA256 as A, ANALYST_BENCHMARK_LOCAL_RECEIPT_FILE as B, publicBenchmarkSystemPrompt as C, parseVerificationOutcome as D, loadCodeTraceVerificationArtifacts as E, ANALYST_BENCHMARK_IMPLEMENTATION_FILES as F, summarizeAgentRxCalibration as G, ANALYST_BENCHMARK_OBSERVATIONS_FILE as H, ANALYST_BENCHMARK_IMPLEMENTATION_SHA256 as I, agentRxBenchmarkCase as J, codeTraceBenchCase as K, analystBenchmarkDependencyLockDigest as L, ANALYST_BENCHMARK_EVIDENCE_IMPLEMENTATION_SHA256 as M, ANALYST_BENCHMARK_EVIDENCE_PACKAGE_VERSION as N, ANALYST_BENCHMARK_DEPENDENCY_LOCK_DIGEST_ALGORITHM as O, ANALYST_BENCHMARK_IMPLEMENTATION_DIGEST_ALGORITHM as P, normalizeBenchmarkLabel as Q, analystBenchmarkImplementationDigest as R, publicBenchmarkRlmInstructions as S, appendVerificationArtifactsToOtlp as T, AGENT_RX_UPSTREAM_REVISION as U, ANALYST_BENCHMARK_MANIFEST_FILE as V, renderAgentRxCalibrationMarkdown as W, normalizeAgentRxCategory as X, agentRxPredictionsToFindings as Y, roundAgentRxStep as Z, expandCodeTraceFailureBlocks as _, renderCodeTraceCalibrationMarkdown as a, MAX_INCORRECT_BLOCK_STEPS as b, createPublicBenchmarkRlmRunner as c, preparePublicAnalystBenchmark as d, publicBenchmarkDistributions as f, emptyPublicBenchmarkRunner as g, adaptPublicBenchmarkFindings as h, readAnalystBenchmarkArtifact as i, ANALYST_BENCHMARK_EVIDENCE_DEPENDENCY_LOCK_SHA256 as j, ANALYST_BENCHMARK_DEPENDENCY_LOCK_FILES as k, createPublicBenchmarkDirectRunner as l, selectPublicBenchmarkRows as m, runAnalystBenchmarkCommand as n, summarizeCodeTraceCalibration as o, publicBenchmarkSelectionReport as p, codeTracerPredictionsToFindings as q, renderAnalystBenchmarkMarkdown as r, compareAnalystRunners as s, ANALYST_BENCHMARK_HELP as t, loadPublicBenchmarkRows as u, CODE_TRACE_BENCH_ANALYST_PROMPT as v, DEFAULT_MAX_VERIFICATION_ARTIFACT_BYTES as w, publicBenchmarkProtocolSha256 as x, MAX_INCORRECT_BLOCKS as y, ANALYST_BENCHMARK_COST_LEDGER_FILE as z };
4536
4809
 
4537
- //# sourceMappingURL=benchmark-command-DzUZJl8M.js.map
4810
+ //# sourceMappingURL=benchmark-command-xvi2liH7.js.map