@tangle-network/agent-eval 0.193.2 → 0.195.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (73) hide show
  1. package/CHANGELOG.md +33 -0
  2. package/dist/adapters/http.d.ts +2 -2
  3. package/dist/analyst/index.d.ts +5 -5
  4. package/dist/analyst/index.js +1 -1
  5. package/dist/{benchmark-command-N5r3GXMP.js → benchmark-command-D2kaOHat.js} +2 -2
  6. package/dist/{benchmark-command-N5r3GXMP.js.map → benchmark-command-D2kaOHat.js.map} +1 -1
  7. package/dist/benchmarks/index.d.ts +3 -3
  8. package/dist/benchmarks/index.js +2 -2
  9. package/dist/campaign/index.d.ts +4 -4
  10. package/dist/campaign/index.js +6 -6
  11. package/dist/{campaign-DnL0S4XL.js → campaign-DkMRR1Co.js} +6 -6
  12. package/dist/{campaign-DnL0S4XL.js.map → campaign-DkMRR1Co.js.map} +1 -1
  13. package/dist/cli.js +4 -4
  14. package/dist/contract/index.d.ts +6 -6
  15. package/dist/contract/index.js +3 -3
  16. package/dist/{default-registry-C3HTE08O.d.ts → default-registry-D44M_E4Q.d.ts} +3 -3
  17. package/dist/{default-registry-C3HTE08O.d.ts.map → default-registry-D44M_E4Q.d.ts.map} +1 -1
  18. package/dist/{define-agent-eval-qxAPjMSL.js → define-agent-eval-Ddut4mkS.js} +3 -3
  19. package/dist/{define-agent-eval-qxAPjMSL.js.map → define-agent-eval-Ddut4mkS.js.map} +1 -1
  20. package/dist/{define-agent-eval-DQJvVa1P.d.ts → define-agent-eval-Dl0tmtJU.d.ts} +4 -4
  21. package/dist/{define-agent-eval-DQJvVa1P.d.ts.map → define-agent-eval-Dl0tmtJU.d.ts.map} +1 -1
  22. package/dist/{engine-DjRV55F9.d.ts → engine-LkP-rfp1.d.ts} +2 -2
  23. package/dist/{engine-DjRV55F9.d.ts.map → engine-LkP-rfp1.d.ts.map} +1 -1
  24. package/dist/evaluation.d.ts +1 -1
  25. package/dist/experiment/index.d.ts +1 -1
  26. package/dist/hosted/index.js +1 -1
  27. package/dist/{index-DWQNDqPd.d.ts → index-CZYB36IQ.d.ts} +6 -6
  28. package/dist/{index-DWQNDqPd.d.ts.map → index-CZYB36IQ.d.ts.map} +1 -1
  29. package/dist/{index-DMPLG226.d.ts → index-CdHX0_c3.d.ts} +120 -15
  30. package/dist/index-CdHX0_c3.d.ts.map +1 -0
  31. package/dist/{index-0jEtpSM7.d.ts → index-cWnRlQLW.d.ts} +3 -3
  32. package/dist/{index-0jEtpSM7.d.ts.map → index-cWnRlQLW.d.ts.map} +1 -1
  33. package/dist/index.d.ts +9 -9
  34. package/dist/index.js +3 -3
  35. package/dist/jev.d.ts +1 -1
  36. package/dist/{llm-judge-Cififl_V.js → llm-judge-CvKpaRKY.js} +459 -43
  37. package/dist/llm-judge-CvKpaRKY.js.map +1 -0
  38. package/dist/{matrix-CNu13gg8.d.ts → matrix-CUzY_7Ml.d.ts} +2 -2
  39. package/dist/{matrix-CNu13gg8.d.ts.map → matrix-CUzY_7Ml.d.ts.map} +1 -1
  40. package/dist/multishot/golden/index.d.ts +1 -1
  41. package/dist/multishot/index.d.ts +2 -2
  42. package/dist/openapi.json +1 -1
  43. package/dist/{produced-state-B2AhDRnq.js → produced-state-C8rk-GCK.js} +2 -2
  44. package/dist/{produced-state-B2AhDRnq.js.map → produced-state-C8rk-GCK.js.map} +1 -1
  45. package/dist/rl.d.ts +1 -1
  46. package/dist/{search-ledger-CJiAEU3j.js → search-ledger-BbKtG_WF.js} +12 -4
  47. package/dist/search-ledger-BbKtG_WF.js.map +1 -0
  48. package/dist/{search-shipper-DUlwlCsK.js → search-shipper-Cm4Wt9SC.js} +2 -2
  49. package/dist/{search-shipper-DUlwlCsK.js.map → search-shipper-Cm4Wt9SC.js.map} +1 -1
  50. package/dist/{search-summary-BhY8p0Av.js → search-summary-DnDGR702.js} +2 -2
  51. package/dist/{search-summary-BhY8p0Av.js.map → search-summary-DnDGR702.js.map} +1 -1
  52. package/dist/{skillopt-optimization-method-C6DbFKnw.js → skillopt-optimization-method-CIJqP8oS.js} +3 -3
  53. package/dist/{skillopt-optimization-method-C6DbFKnw.js.map → skillopt-optimization-method-CIJqP8oS.js.map} +1 -1
  54. package/dist/{statistical-heldout-D-xBpbrd.d.ts → statistical-heldout-CLfkCc_B.d.ts} +2 -2
  55. package/dist/{statistical-heldout-D-xBpbrd.d.ts.map → statistical-heldout-CLfkCc_B.d.ts.map} +1 -1
  56. package/dist/{store-tool-spans-BxrfuU2t.d.ts → store-tool-spans-E-mdWPAz.d.ts} +3 -3
  57. package/dist/{store-tool-spans-BxrfuU2t.d.ts.map → store-tool-spans-E-mdWPAz.d.ts.map} +1 -1
  58. package/dist/{tool-groups-BC9O7Epn.d.ts → tool-groups-CiFSpk6C.d.ts} +2 -2
  59. package/dist/tool-groups-CiFSpk6C.d.ts.map +1 -0
  60. package/dist/trace-repair/index.d.ts +1 -1
  61. package/dist/traces.d.ts +2 -2
  62. package/dist/{types-BWwRXofp.d.ts → types-DLtLe21j.d.ts} +9 -2
  63. package/dist/types-DLtLe21j.d.ts.map +1 -0
  64. package/dist/{types-qoxUfKQg.d.ts → types-M1Et9e6Z.d.ts} +2 -2
  65. package/dist/{types-qoxUfKQg.d.ts.map → types-M1Et9e6Z.d.ts.map} +1 -1
  66. package/docs/search-ledger.md +37 -9
  67. package/docs/trace-contracts.md +21 -2
  68. package/package.json +1 -1
  69. package/dist/index-DMPLG226.d.ts.map +0 -1
  70. package/dist/llm-judge-Cififl_V.js.map +0 -1
  71. package/dist/search-ledger-CJiAEU3j.js.map +0 -1
  72. package/dist/tool-groups-BC9O7Epn.d.ts.map +0 -1
  73. package/dist/types-BWwRXofp.d.ts.map +0 -1
@@ -3,6 +3,7 @@ import { a as hashCanonical, i as compareCodeUnits, r as canonicalString, t as L
3
3
  import { t as mulberry32 } from "./random-Dn5fPWkt.js";
4
4
  import { o as summarizeNumberSeries, s as weightedComposite, t as confidenceInterval } from "./descriptive-1V17A-qa.js";
5
5
  import { v as wilson } from "./paired-arms-JSDcs2zx.js";
6
+ import { t as minimumPairsForPairedDeltaTest } from "./paired-delta-test-BF-FEP8V.js";
6
7
  import { t as decidePairedPromotion } from "./paired-promotion-decision-DTKl6-G8.js";
7
8
  import { a as heldoutSignificance, i as dimensionRegressions, o as pairHoldout } from "./statistical-heldout-DANVmyug.js";
8
9
  import { i as modelHasSnapshot, l as searchCellRunId } from "./run-record-BRlM99rX.js";
@@ -17,8 +18,8 @@ import { r as summarizeEvaluationUnits, t as defineEvaluationClaim } from "./cla
17
18
  import { f as redactText, n as REDACTION_VERSION, o as detectCredential, s as detectPersonalData } from "./redact-Dk1ZdJEm.js";
18
19
  import { t as detectRewardHacking } from "./reward-hacking-D0XwhVWE.js";
19
20
  import { n as assertProposalFindings, t as combineAbortSignals } from "./abort-signal-CtzAM_sJ.js";
20
- import { a as validateSearchLedgerEvent, d as searchTaskSetDigest, i as replaySearchLedgerText, l as searchCellId, n as openSearchLedger, t as FileSearchLedger, u as searchNodeId } from "./search-ledger-CJiAEU3j.js";
21
- import { c as seedFromDigest, i as estimateNode, n as searchProposerView, s as searchPosterior, t as renderSearchSummary } from "./search-summary-BhY8p0Av.js";
21
+ import { a as validateSearchLedgerEvent, d as searchTaskSetDigest, i as replaySearchLedgerText, l as searchCellId, n as openSearchLedger, t as FileSearchLedger, u as searchNodeId } from "./search-ledger-BbKtG_WF.js";
22
+ import { c as seedFromDigest, i as estimateNode, n as searchProposerView, s as searchPosterior, t as renderSearchSummary } from "./search-summary-DnDGR702.js";
22
23
  import { d as stripFencedJson, o as costReceiptFromLlm, s as costReceiptFromLlmError, u as maximumChargeForLlmRequest } from "./llm-client-c_bKHTXz.js";
23
24
  import { createHash } from "node:crypto";
24
25
  import { writeFileSync } from "node:fs";
@@ -2537,14 +2538,25 @@ function paretoFrontierWithCrowding(candidates, objectives) {
2537
2538
  //#endregion
2538
2539
  //#region src/campaign/allocation.ts
2539
2540
  /**
2541
+ * Allocation: where a search spends rollouts.
2542
+ *
2543
+ * An allocator says which cells a node needs given the evidence so far; the
2544
+ * kernel allocates the ones the ledger does not hold yet, so a resumed search
2545
+ * plans exactly what the interrupted one planned. It also decides which nodes
2546
+ * earn more measurement (`advanced`) and, at close, which were left waiting
2547
+ * (`pruned`). Those are rank decisions: they spend budget and claim nothing.
2548
+ * Expansion (which parent, which operator) belongs to the `SearchPolicy`; the
2549
+ * claim belongs to the claim step.
2550
+ */
2551
+ /**
2540
2552
  * Every node gets every train and selection task at every repeat: the root as
2541
2553
  * `root` cells, every other node as `train` cells (the proposer's feedback) and
2542
2554
  * `screen` cells (the policy's private evidence). This is the fixed plan the
2543
- * generation loop ran and GEPA runs.
2555
+ * generation loop ran and GEPA runs. It has one rung, so it never advances or
2556
+ * prunes a node.
2544
2557
  */
2545
2558
  function uniform(options = {}) {
2546
- const reps = options.reps ?? 1;
2547
- if (!Number.isSafeInteger(reps) || reps < 1) throw new TypeError(`uniform: reps must be a positive integer, got ${String(reps)}`);
2559
+ const reps = positiveInteger("uniform", "reps", options.reps ?? 1);
2548
2560
  const cells = (state, root) => {
2549
2561
  const header = state.header;
2550
2562
  if (!header) return [];
@@ -2561,9 +2573,281 @@ function uniform(options = {}) {
2561
2573
  name: reps === 1 ? "uniform" : `uniform(reps=${reps})`,
2562
2574
  reps,
2563
2575
  plan: (state, nodeId) => cells(state, nodeId === state.rootNodeId),
2564
- screenSize: (state) => cells(state, false).length
2576
+ screenSize: (state) => cells(state, false).length,
2577
+ advance: () => [],
2578
+ prune: () => []
2579
+ };
2580
+ }
2581
+ /**
2582
+ * Asynchronous successive halving (Li et al., 2020) over one seeded
2583
+ * permutation of the ranked split's units, fixed by the search's seed.
2584
+ *
2585
+ * Rung k is the first `units × 2^k` units of the permutation; the top rung is
2586
+ * every unit. The root runs every unit before anything else, so every rung
2587
+ * pairs against it. A new node screens on rung 0 plus `trainUnits` train
2588
+ * units. Every node at a rung runs the same units as its parent, the root and
2589
+ * its siblings, so every contrast pairs.
2590
+ *
2591
+ * A node that finished rung k advances once it ranks in the top
2592
+ * floor(n / eta) of the n nodes that finished rung k, the root included, by
2593
+ * mean over the rung's units; a node with an unscored unit ranks last and
2594
+ * never advances. There is no barrier: a node outside the top waits, because
2595
+ * the set grows as more nodes finish. At close a waiting node is pruned with
2596
+ * its rank. The ranked split is selection, or train when a search declares no
2597
+ * selection split, as the policy's.
2598
+ */
2599
+ function asha(options = {}) {
2600
+ const firstRung = minimumPairsForPairedDeltaTest();
2601
+ const units = positiveInteger("asha", "units", options.units ?? firstRung);
2602
+ const eta = positiveInteger("asha", "eta", options.eta ?? 3);
2603
+ if (eta < 2) throw new TypeError(`asha: eta must be at least 2, got ${eta}`);
2604
+ const trainUnits = nonNegativeInteger("asha", "trainUnits", options.trainUnits ?? 2);
2605
+ const reps = positiveInteger("asha", "reps", options.reps ?? 1);
2606
+ const name = units === firstRung && eta === 3 && trainUnits === 2 && reps === 1 ? "asha" : `asha(units=${units},eta=${eta},train=${trainUnits},reps=${reps})`;
2607
+ const layouts = /* @__PURE__ */ new WeakMap();
2608
+ const layoutOf = (state) => {
2609
+ const header = state.header;
2610
+ if (!header) return null;
2611
+ let layout = layouts.get(header);
2612
+ if (!layout) {
2613
+ layout = ashaLayout(header, {
2614
+ units,
2615
+ trainUnits
2616
+ });
2617
+ layouts.set(header, layout);
2618
+ }
2619
+ return layout;
2620
+ };
2621
+ const cellsThrough = (layout, rung, root) => {
2622
+ const plan = [];
2623
+ const through = root ? layout.top : Math.min(rung, layout.top);
2624
+ layout.order.slice(0, layout.sizes[through]).forEach((unitId, position) => {
2625
+ const stage = root ? "root" : layout.split === "train" ? "train" : position < layout.sizes[0] ? "screen" : "rung";
2626
+ for (const task of layout.tasks.get(unitId)) for (let rep = 0; rep < reps; rep++) plan.push({
2627
+ taskId: task.taskId,
2628
+ split: layout.split,
2629
+ rep,
2630
+ stage
2631
+ });
2632
+ });
2633
+ for (const task of layout.feedback) for (let rep = 0; rep < reps; rep++) plan.push({
2634
+ taskId: task.taskId,
2635
+ split: "train",
2636
+ rep,
2637
+ stage: root ? "root" : "train"
2638
+ });
2639
+ return plan;
2640
+ };
2641
+ /**
2642
+ * Per node: the deepest rung it finished and its unit means on the ranked
2643
+ * split. A later decision (finalist, selected, pruned) does not unfinish a
2644
+ * rung, so every node but an invalid one keeps its place in the ranks; only
2645
+ * an undecided or advanced node is `open` to a new decision.
2646
+ */
2647
+ const standings = (view, layout) => {
2648
+ const { state } = view;
2649
+ const rootId = state.rootNodeId;
2650
+ const standing = [];
2651
+ for (const node of state.nodes()) {
2652
+ if (node.status === "invalid") continue;
2653
+ const root = node.nodeId === rootId;
2654
+ let advancedTo = 0;
2655
+ for (const { decision } of node.decisions) if (decision.status === "advanced") advancedTo = Math.max(advancedTo, decision.rung);
2656
+ const rung = root ? layout.top : Math.min(advancedTo, layout.top);
2657
+ const allocated = /* @__PURE__ */ new Set();
2658
+ let cancelled = false;
2659
+ for (const cell of state.cells({ nodeId: node.nodeId })) {
2660
+ if (cell.split !== layout.split) continue;
2661
+ const position = layout.position.get(cell.unitId);
2662
+ if (position !== void 0 && position < layout.sizes[rung]) {
2663
+ allocated.add(`${cell.taskId}\u0000${cell.rep}`);
2664
+ if (cell.cancelled !== null) cancelled = true;
2665
+ }
2666
+ }
2667
+ const covered = !cancelled && allocated.size === layout.cellsThrough[rung] * reps;
2668
+ const finished = view.idle(node.nodeId) && covered ? rung : root ? -1 : rung - 1;
2669
+ if (finished < 0) continue;
2670
+ const means = /* @__PURE__ */ new Map();
2671
+ for (const unit of state.unitScores(node.nodeId, layout.split)) means.set(unit.unitId, unit.mean);
2672
+ const open = node.status === null || node.status === "advanced";
2673
+ standing.push({
2674
+ nodeId: node.nodeId,
2675
+ ordinal: node.ordinal,
2676
+ root,
2677
+ open,
2678
+ rung,
2679
+ finished,
2680
+ means
2681
+ });
2682
+ }
2683
+ return standing;
2684
+ };
2685
+ /** The nodes that finished rung k, best first; an unscored unit ranks last. */
2686
+ const ranking = (state, layout, standing, k) => {
2687
+ const rungUnits = [...layout.order.slice(0, layout.sizes[k])].sort(compareCodeUnits);
2688
+ const sign = state.header.objective.direction === "maximize" ? 1 : -1;
2689
+ const ranked = [];
2690
+ for (const entry of standing) {
2691
+ if (entry.finished < k) continue;
2692
+ let sum = 0;
2693
+ let complete = true;
2694
+ for (const unitId of rungUnits) {
2695
+ const mean = entry.means.get(unitId);
2696
+ if (mean === void 0) {
2697
+ complete = false;
2698
+ break;
2699
+ }
2700
+ sum += mean;
2701
+ }
2702
+ ranked.push({
2703
+ ...entry,
2704
+ mean: complete ? sum / rungUnits.length : null,
2705
+ sign
2706
+ });
2707
+ }
2708
+ return ranked.sort(compareRanked);
2709
+ };
2710
+ const reason = (ranked, index, k, layout) => {
2711
+ const entry = ranked[index];
2712
+ const top = Math.floor(ranked.length / eta);
2713
+ const mean = entry.mean === null ? "an unscored unit" : `mean ${round$1(entry.mean)}`;
2714
+ return `rank ${index + 1} of ${ranked.length} on rung ${k} (${layout.sizes[k]} units, ${mean}); the top ${top} advance (eta ${eta})`;
2715
+ };
2716
+ return {
2717
+ name,
2718
+ reps,
2719
+ plan(state, nodeId, rung) {
2720
+ const layout = layoutOf(state);
2721
+ return layout ? cellsThrough(layout, rung, nodeId === state.rootNodeId) : [];
2722
+ },
2723
+ screenSize(state) {
2724
+ const layout = layoutOf(state);
2725
+ return layout ? cellsThrough(layout, 0, false).length : 0;
2726
+ },
2727
+ advance(view) {
2728
+ const { state } = view;
2729
+ const layout = layoutOf(state);
2730
+ const rootId = state.rootNodeId;
2731
+ if (!layout || layout.top === 0 || rootId === null) return [];
2732
+ const standing = standings(view, layout);
2733
+ const decisions = [];
2734
+ for (let k = layout.top - 1; k >= 0; k--) {
2735
+ const ranked = ranking(state, layout, standing, k);
2736
+ const top = Math.floor(ranked.length / eta);
2737
+ for (let index = 0; index < top; index++) {
2738
+ const entry = ranked[index];
2739
+ if (!entry.open || entry.root || entry.mean === null) continue;
2740
+ if (entry.finished !== k || entry.rung !== k) continue;
2741
+ decisions.push({
2742
+ nodeId: entry.nodeId,
2743
+ decision: {
2744
+ status: "advanced",
2745
+ rung: k + 1
2746
+ },
2747
+ basis: estimateNode(state, entry.nodeId, {
2748
+ against: rootId,
2749
+ split: layout.split
2750
+ }),
2751
+ rule: name,
2752
+ reason: reason(ranked, index, k, layout)
2753
+ });
2754
+ }
2755
+ }
2756
+ return decisions;
2757
+ },
2758
+ prune(view, keep) {
2759
+ const { state } = view;
2760
+ const layout = layoutOf(state);
2761
+ const rootId = state.rootNodeId;
2762
+ if (!layout || layout.top === 0 || rootId === null) return [];
2763
+ const standing = standings(view, layout);
2764
+ const decisions = [];
2765
+ for (let k = layout.top - 1; k >= 0; k--) {
2766
+ const ranked = ranking(state, layout, standing, k);
2767
+ const top = Math.floor(ranked.length / eta);
2768
+ ranked.forEach((entry, index) => {
2769
+ if (!entry.open || entry.root || entry.nodeId === keep) return;
2770
+ if (entry.finished !== k || entry.rung !== k || entry.means.size === 0) return;
2771
+ const why = index < top && entry.mean !== null ? `it earned rung ${k + 1}, but the cap, the cell limit or the deadline did not admit its cells` : "it waited outside the top when the search closed";
2772
+ decisions.push({
2773
+ nodeId: entry.nodeId,
2774
+ decision: { status: "pruned" },
2775
+ basis: estimateNode(state, entry.nodeId, {
2776
+ against: rootId,
2777
+ split: layout.split
2778
+ }),
2779
+ rule: name,
2780
+ reason: `${reason(ranked, index, k, layout)}; ${why}`
2781
+ });
2782
+ });
2783
+ }
2784
+ return decisions;
2785
+ }
2786
+ };
2787
+ }
2788
+ function compareRanked(left, right) {
2789
+ if (left.mean === null || right.mean === null) {
2790
+ if (left.mean !== right.mean) return left.mean === null ? 1 : -1;
2791
+ } else if (left.mean !== right.mean) return left.sign * (right.mean - left.mean);
2792
+ return left.ordinal - right.ordinal;
2793
+ }
2794
+ function ashaLayout(header, options) {
2795
+ const split = header.splits.selection.tasks.length > 0 ? "selection" : "train";
2796
+ const tasks = unitsOf(header.splits[split].tasks);
2797
+ const order = permute([...tasks.keys()], header.policy.seed, split);
2798
+ const sizes = [];
2799
+ for (let size = options.units;; size *= 2) {
2800
+ sizes.push(Math.min(size, order.length));
2801
+ if (size >= order.length) break;
2802
+ }
2803
+ const cellsThrough = sizes.map((size) => order.slice(0, size).reduce((sum, unitId) => sum + tasks.get(unitId).length, 0));
2804
+ let feedback = [];
2805
+ if (split === "selection") {
2806
+ const train = unitsOf(header.splits.train.tasks);
2807
+ feedback = permute([...train.keys()], header.policy.seed, "train").slice(0, options.trainUnits).flatMap((unitId) => train.get(unitId));
2808
+ }
2809
+ return {
2810
+ split,
2811
+ order,
2812
+ position: new Map(order.map((unitId, index) => [unitId, index])),
2813
+ tasks,
2814
+ sizes,
2815
+ cellsThrough,
2816
+ top: sizes.length - 1,
2817
+ feedback
2565
2818
  };
2566
2819
  }
2820
+ /** Tasks grouped by unit, units and tasks in code-unit order. */
2821
+ function unitsOf(tasks) {
2822
+ const byUnit = /* @__PURE__ */ new Map();
2823
+ for (const task of [...tasks].sort((left, right) => compareCodeUnits(left.taskId, right.taskId))) {
2824
+ const unit = byUnit.get(task.unitId);
2825
+ if (unit) unit.push(task);
2826
+ else byUnit.set(task.unitId, [task]);
2827
+ }
2828
+ return new Map([...byUnit.entries()].sort(([left], [right]) => compareCodeUnits(left, right)));
2829
+ }
2830
+ /** Fisher-Yates over units in code-unit order, from the search seed and the split. */
2831
+ function permute(unitIds, seed, split) {
2832
+ const rng = mulberry32(seed ^ (split === "train" ? 2050776593 : 731729763) | 0);
2833
+ const order = [...unitIds];
2834
+ for (let index = order.length - 1; index > 0; index--) {
2835
+ const other = Math.floor(rng() * (index + 1));
2836
+ [order[index], order[other]] = [order[other], order[index]];
2837
+ }
2838
+ return order;
2839
+ }
2840
+ function positiveInteger(owner, name, value) {
2841
+ if (!Number.isSafeInteger(value) || value < 1) throw new TypeError(`${owner}: ${name} must be a positive integer, got ${String(value)}`);
2842
+ return value;
2843
+ }
2844
+ function nonNegativeInteger(owner, name, value) {
2845
+ if (!Number.isSafeInteger(value) || value < 0) throw new TypeError(`${owner}: ${name} must be a non-negative integer, got ${String(value)}`);
2846
+ return value;
2847
+ }
2848
+ function round$1(value) {
2849
+ return Math.round(value * 1e4) / 1e4;
2850
+ }
2567
2851
  //#endregion
2568
2852
  //#region src/paired-promotion-power.ts
2569
2853
  /**
@@ -3064,6 +3348,76 @@ function decideSearchClaim(state, plan) {
3064
3348
  decisions
3065
3349
  };
3066
3350
  }
3351
+ /**
3352
+ * Make a closed search's claim again from its ledger alone and compare it with
3353
+ * the recorded one, byte for byte: the power check, the finalists, each
3354
+ * finalist's test estimate and deciding interval, the selection, the decision
3355
+ * and the reason. A producer's claim is not evidence until this holds; a store
3356
+ * keeps what this function derives, not what the producer wrote.
3357
+ *
3358
+ * It needs no blob, so it works on a store that keeps digests only. The
3359
+ * finalists are the nodes the ledger decided `finalist`, in decision order.
3360
+ * The one input the ledger cannot replay is whether the budget covered k
3361
+ * finalists' test cells; the claim cells that ran answer it (none ran: the
3362
+ * budget covered none). Test repeats come from the claim cells too; without
3363
+ * test cells, the recorded estimator stands for them (binary needs one repeat,
3364
+ * so any other count reproduces continuous).
3365
+ *
3366
+ * Returns null for a search that made no claim.
3367
+ */
3368
+ function verifySearchClaim(state) {
3369
+ const closed = state.closed;
3370
+ if (!closed) throw new Error(`search ${state.searchId} is open; its claim is made when it closes`);
3371
+ const recorded = closed.claim;
3372
+ if (recorded === null) return null;
3373
+ if (recorded.rule.revision !== SEARCH_CLAIM_RULE.revision) return {
3374
+ status: "unknown",
3375
+ reason: `the claim names rule revision ${recorded.rule.revision}; this code implements ${SEARCH_CLAIM_RULE.revision}`
3376
+ };
3377
+ const claimCells = state.cells().filter((cell) => cell.stage === "claim");
3378
+ const decided = state.nodes().flatMap((node) => {
3379
+ const first = node.decisions.find((record) => record.decision.status === "finalist");
3380
+ return first ? [{
3381
+ nodeId: node.nodeId,
3382
+ sequence: first.sequence
3383
+ }] : [];
3384
+ }).sort((a, b) => a.sequence - b.sequence).map((entry) => entry.nodeId);
3385
+ const reps = claimCells.length > 0 ? 1 + Math.max(...claimCells.map((cell) => cell.rep)) : "adequate" in recorded.power && recorded.power.estimator.kind === "binary" ? 1 : 2;
3386
+ const plan = planSearchClaim(state, {
3387
+ stopReason: closed.reason,
3388
+ reps,
3389
+ affordable: (finalists) => claimCells.length > 0 && finalists <= decided.length
3390
+ });
3391
+ const differences = [];
3392
+ const planned = plan.finalists.map((finalist) => finalist.nodeId);
3393
+ if (canonicalString(planned) !== canonicalString(decided)) differences.push(`finalists: the rule picks [${planned.join(", ")}], the ledger decided [${decided.join(", ")}]`);
3394
+ if (plan.test === "run" !== claimCells.length > 0) differences.push(`test: the plan ${plan.test === "run" ? "runs" : "skips"} the test cells, and ${claimCells.length} ran`);
3395
+ const expected = decideSearchClaim(state, plan).claim;
3396
+ for (const key of [
3397
+ "decision",
3398
+ "selected",
3399
+ "confidence",
3400
+ "power",
3401
+ "reason"
3402
+ ]) if (canonicalString(expected[key]) !== canonicalString(recorded[key])) differences.push(`${key}: the ledger supports ${canonicalString(expected[key])}, the claim records ${canonicalString(recorded[key])}`);
3403
+ const count = Math.max(expected.finalists.length, recorded.finalists.length);
3404
+ for (let index = 0; index < count; index++) {
3405
+ const want = expected.finalists[index];
3406
+ const have = recorded.finalists[index];
3407
+ if (canonicalString(want ?? null) === canonicalString(have ?? null)) continue;
3408
+ const fields = [
3409
+ "nodeId",
3410
+ "promote",
3411
+ "test",
3412
+ "estimate"
3413
+ ].filter((field) => canonicalString(want?.[field] ?? null) !== canonicalString(have?.[field] ?? null));
3414
+ differences.push(`finalist ${index + 1} (${have?.nodeId ?? want?.nodeId}): ${fields.join(", ")} differ from what the ledger supports`);
3415
+ }
3416
+ return differences.length === 0 ? { status: "verified" } : {
3417
+ status: "mismatch",
3418
+ differences
3419
+ };
3420
+ }
3067
3421
  /** Per-finalist confidence for `k` finalists. */
3068
3422
  function bonferroni(k) {
3069
3423
  return 1 - (1 - FAMILY_CONFIDENCE) / k;
@@ -3321,17 +3675,19 @@ const SEARCH_KERNEL_SOURCE = {
3321
3675
  revision: hashCanonical({
3322
3676
  name: "tangle.search-kernel.2026-09",
3323
3677
  dispatch: "claim, then rung and root, then screen, then train; first allocated first within a stage",
3324
- expansion: "when no cell waits, fewer than twice the lanes capacity run, and the cap admits one proposal and its expected screens",
3678
+ expansion: "when no cell waits, fewer than twice the lanes capacity run, the cap admits one proposal and its expected screens, and overspend has not taken the search past its cap",
3325
3679
  reservation: {
3326
3680
  hard: "the lane per-cell maximum",
3327
3681
  estimate: "1.5 times the p99 of the lane settled cells once 20 settled, else the lane prior"
3328
3682
  },
3329
3683
  retries: "a retryable errored attempt runs again, up to maxAttempts",
3684
+ rungs: "when a node finishes its cells, the allocator names the nodes it advances, deepest rung first; each is recorded advanced and its rung allocated when the cap admits the rung",
3330
3685
  resume: "an unrecorded operation is recorded failed at an unknown cost with floor 0; a recorded proposal is finished from its stored output; an unsettled cell is offered to adopt before it runs",
3331
3686
  writers: "one kernel per ledger file on a host, by a pid lock beside the ledger",
3332
3687
  divergence: "a node whose train mean over shared units rises above its parent while its descriptive or bootstrap selection interval against the parent lies wholly on the worse side is decided invalid when its cells finish",
3333
3688
  claim: "with a test split: after expansion stops, the claim plan is stored on the claim operation, the finalists are decided, the root and finalist test cells run together, and the claim decides; the kernel refuses to start a claim without a selection split, a minimumEffect, a pinned judge, or (under a cap) a claim reserve for the root and 3 finalists plus a cap for one screening round",
3334
- close: "without a test split, the policy leader is selected when it has a scored cell; every other undecided node is rejected"
3689
+ close: "the allocator prunes the nodes left waiting on a rung, except the policy leader; then, with a test split, the claim decides; without one, the policy leader is selected when it has a scored cell; every other undecided node is rejected",
3690
+ complete: "a node leads only when it has a scored cell on the ranked split and no cell there ended unscored: a final unscored outcome, or an error with no attempt left"
3335
3691
  })
3336
3692
  };
3337
3693
  const USD_TOLERANCE = 1e-9;
@@ -3527,6 +3883,7 @@ var SearchKernel = class {
3527
3883
  for (const expansion of recorded) await this.finishProposal(expansion);
3528
3884
  for (const node of this.state.nodes()) if (this.admitted.has(node.nodeId) && !isTerminal(node)) await this.allocateFor(node.nodeId);
3529
3885
  for (const nodeId of this.state.nodeIds()) if (this.admitted.has(nodeId) && (this.pending.get(nodeId) ?? 0) === 0) await this.screenDone(nodeId);
3886
+ await this.advance();
3530
3887
  }
3531
3888
  /**
3532
3889
  * A search that will claim must be able to: finalists come from a selection
@@ -3555,7 +3912,7 @@ var SearchKernel = class {
3555
3912
  cellUsd
3556
3913
  });
3557
3914
  if (reservedClaimUsd + USD_TOLERANCE < need) refuse(`its claim reserve $${reservedClaimUsd} is below the $${need} the root and 3 finalists need on ${testTasks} test tasks at $${cellUsd} a cell`);
3558
- const rootCells = this.options.allocation.plan(this.state, this.state.rootNodeId).length;
3915
+ const rootCells = this.options.allocation.plan(this.state, this.state.rootNodeId, 0).length;
3559
3916
  const screens = (this.options.proposer.childrenPerProposal ?? 1) * this.options.allocation.screenSize(this.state);
3560
3917
  const round = this.operationReservation().usd + (rootCells + screens) * cellUsd;
3561
3918
  if (maxUsd - reservedClaimUsd + USD_TOLERANCE < round) refuse(`its cap $${maxUsd} less the claim reserve $${reservedClaimUsd} does not cover the root and one screening round ($${round})`);
@@ -3694,11 +4051,20 @@ var SearchKernel = class {
3694
4051
  if (cell.stage === "claim") return;
3695
4052
  const left = (this.pending.get(cell.nodeId) ?? 1) - 1;
3696
4053
  this.pending.set(cell.nodeId, left);
3697
- if (left === 0) await this.onScreenDone(cell.nodeId);
4054
+ if (left === 0) await this.onNodeIdle(cell.nodeId);
3698
4055
  }
3699
- async onScreenDone(nodeId) {
4056
+ /** Every cell allocated to the node is done: its screen, or a rung. */
4057
+ async onNodeIdle(nodeId) {
3700
4058
  if (!await this.screenDone(nodeId)) return;
3701
- if (this.stopReason === null && !this.failure) await this.allocateFor(nodeId);
4059
+ await this.advance();
4060
+ }
4061
+ /** Record the rank decisions the allocator now supports and allocate the
4062
+ * rungs they open. Past the deadline, once the claim began, or once the
4063
+ * search fails or is aborted, no rung opens; a search that stopped
4064
+ * expanding still measures the nodes that earned it. */
4065
+ async advance() {
4066
+ if (this.claimPlan || this.failure || this.options.signal?.aborted || this.pastDeadline()) return;
4067
+ for (const decision of this.options.allocation.advance(this.allocationView())) await this.allocateFor(decision.nodeId, decision);
3702
4068
  }
3703
4069
  /**
3704
4070
  * A node's allocated cells all finished. A node that diverges (its train
@@ -3707,7 +4073,7 @@ var SearchKernel = class {
3707
4073
  * becomes a parent; any other node is screened. Returns whether it was.
3708
4074
  */
3709
4075
  async screenDone(nodeId) {
3710
- if (!this.claimPlan && !this.screenedSet.has(nodeId)) {
4076
+ if (!this.claimPlan && !this.screenedSet.has(nodeId) && this.state.node(nodeId).status !== "advanced") {
3711
4077
  const divergence = searchDivergence(this.state, nodeId);
3712
4078
  if (divergence) {
3713
4079
  await this.recorder.decideNode({
@@ -3737,10 +4103,19 @@ var SearchKernel = class {
3737
4103
  ...this.screened.slice(index)
3738
4104
  ];
3739
4105
  }
3740
- /** Allocate the cells the allocator plans for a node and the ledger lacks. */
3741
- async allocateFor(nodeId) {
3742
- const plans = this.options.allocation.plan(this.state, nodeId).filter((plan) => !this.state.cell(searchCellId(this.recorder.searchId, nodeId, plan.taskId, plan.split, plan.rep)));
3743
- if (plans.length === 0) return;
4106
+ /**
4107
+ * Allocate the cells the allocator plans for a node through its rung and the
4108
+ * ledger lacks. With a rank decision, the rung is the decision's, and the
4109
+ * decision is recorded first, only once the cap admits the rung's cells.
4110
+ * Returns false when the cap or `maxCells` refused them.
4111
+ */
4112
+ async allocateFor(nodeId, decision) {
4113
+ const rung = decision?.decision.status === "advanced" ? decision.decision.rung : this.state.node(nodeId).rung ?? 0;
4114
+ const plans = this.options.allocation.plan(this.state, nodeId, rung).filter((plan) => !this.state.cell(searchCellId(this.recorder.searchId, nodeId, plan.taskId, plan.split, plan.rep)));
4115
+ if (plans.length === 0) {
4116
+ if (decision) await this.decide(decision);
4117
+ return true;
4118
+ }
3744
4119
  const placed = plans.map((plan) => {
3745
4120
  const laneName = this.options.executor.place({
3746
4121
  ...plan,
@@ -3756,9 +4131,10 @@ var SearchKernel = class {
3756
4131
  });
3757
4132
  const hold = placed.reduce((sum, { reservation }) => sum + reservation.usd, 0);
3758
4133
  const { headroomUsd } = this.state.budget;
3759
- if (headroomUsd !== null && hold > headroomUsd + USD_TOLERANCE) return;
4134
+ if (headroomUsd !== null && hold > headroomUsd + USD_TOLERANCE) return false;
3760
4135
  const { maxCells } = this.state.header.budget;
3761
- if (maxCells !== null && this.state.audit.cells.allocated + placed.length > maxCells) return;
4136
+ if (maxCells !== null && this.state.audit.cells.allocated + placed.length > maxCells) return false;
4137
+ if (decision) await this.decide(decision);
3762
4138
  for (const { plan, lane, reservation } of placed) await this.recorder.allocateCell({
3763
4139
  nodeId,
3764
4140
  taskId: plan.taskId,
@@ -3775,6 +4151,11 @@ var SearchKernel = class {
3775
4151
  }
3776
4152
  this.pending.set(nodeId, (this.pending.get(nodeId) ?? 0) + placed.length);
3777
4153
  this.dispatch();
4154
+ return true;
4155
+ }
4156
+ async decide(decision) {
4157
+ await this.recorder.decideNode(decision);
4158
+ await this.refresh();
3778
4159
  }
3779
4160
  enqueue(cell) {
3780
4161
  this.lanes.get(cell.lane).queues[STAGE_PRIORITY[cell.stage]].push(cell.cellId);
@@ -3942,7 +4323,7 @@ var SearchKernel = class {
3942
4323
  const children = this.options.proposer.childrenPerProposal ?? 1;
3943
4324
  const need = operation.usd + children * screen * this.maxCellReservation();
3944
4325
  const { headroomUsd } = this.state.budget;
3945
- if (headroomUsd !== null && need > headroomUsd + USD_TOLERANCE) return "budget";
4326
+ if (headroomUsd !== null && (need > headroomUsd + USD_TOLERANCE || this.overCap())) return "budget";
3946
4327
  if (maxCells !== null && this.state.audit.cells.allocated + children * screen > maxCells) return "budget";
3947
4328
  const expansion = policy.expand(view);
3948
4329
  if (expansion === null) return "converged";
@@ -4093,6 +4474,8 @@ var SearchKernel = class {
4093
4474
  }
4094
4475
  async close() {
4095
4476
  await this.refresh();
4477
+ const keep = this.options.policy.leader(this.policyView());
4478
+ for (const decision of this.options.allocation.prune(this.allocationView(), keep)) await this.decide(decision);
4096
4479
  if (this.claimPlan) {
4097
4480
  await this.closeWithClaim(this.claimPlan);
4098
4481
  return;
@@ -4102,6 +4485,7 @@ var SearchKernel = class {
4102
4485
  const { split } = view;
4103
4486
  const root = this.state.rootNodeId;
4104
4487
  const rule = this.options.policy.name;
4488
+ const leaderUnits = view.unitScores(leader).map((unit) => unit.unitId);
4105
4489
  const decisions = this.state.nodes().filter((node) => !isTerminal(node)).map((node) => {
4106
4490
  const scored = this.state.scoredCells(node.nodeId, split).length > 0;
4107
4491
  const lead = node.nodeId === leader && scored;
@@ -4110,12 +4494,13 @@ var SearchKernel = class {
4110
4494
  against,
4111
4495
  split
4112
4496
  });
4497
+ const units = new Set(view.unitScores(node.nodeId).map((unit) => unit.unitId));
4113
4498
  return {
4114
4499
  nodeId: node.nodeId,
4115
4500
  decision: { status: lead ? "selected" : "rejected" },
4116
4501
  basis,
4117
4502
  rule,
4118
- reason: lead ? `the leader when the search stopped (${this.stopReason}): a budget decision on the ${split} split, which claims nothing` : !this.screenedSet.has(node.nodeId) || !scored ? "the search stopped before this node was measured" : !view.complete(node.nodeId) ? "it left a unit of its screen unscored, so it could not lead" : "it did not beat the leader on the units they share"
4503
+ reason: lead ? `the leader when the search stopped (${this.stopReason}): a budget decision on the ${split} split, which claims nothing` : !this.screenedSet.has(node.nodeId) || !scored ? "the search stopped before this node was measured" : !view.complete(node.nodeId) ? "it left a unit unscored, so it could not lead" : leaderUnits.some((unitId) => !units.has(unitId)) ? "the search stopped before it was measured on every unit the leader was" : "it did not beat the leader on the units they share"
4119
4504
  };
4120
4505
  });
4121
4506
  for (const decision of decisions) await this.recorder.decideNode(decision);
@@ -4151,22 +4536,35 @@ var SearchKernel = class {
4151
4536
  });
4152
4537
  await this.refresh();
4153
4538
  }
4539
+ /** The closed search, with its claim made again from the ledger alone. A
4540
+ * claim the ledger does not support throws: a tampered ledger, or a
4541
+ * producer and verifier that disagree. */
4154
4542
  closedResult() {
4155
4543
  const state = this.state;
4544
+ const claimVerification = verifySearchClaim(state);
4545
+ if (claimVerification?.status === "mismatch") throw new Error(`runSearch: search ${state.searchId} closed with a claim its ledger does not support: ${claimVerification.differences.join("; ")}`);
4156
4546
  return {
4157
4547
  state,
4158
4548
  leader: state.audit.selectedNodeId ?? state.rootNodeId,
4159
4549
  reason: state.closed.reason,
4160
- claim: state.closed.claim
4550
+ claim: state.closed.claim,
4551
+ claimVerification
4161
4552
  };
4162
4553
  }
4163
4554
  policyView() {
4164
4555
  return searchPolicyView(this.state, {
4165
4556
  screened: this.screened,
4166
4557
  screening: this.admitted.size - this.screenedSet.size,
4167
- expansions: this.completed.length
4558
+ expansions: this.completed.length,
4559
+ maxAttempts: this.maxAttempts
4168
4560
  });
4169
4561
  }
4562
+ allocationView() {
4563
+ return {
4564
+ state: this.state,
4565
+ idle: (nodeId) => this.admitted.has(nodeId) && (this.pending.get(nodeId) ?? 0) === 0
4566
+ };
4567
+ }
4170
4568
  artifact(nodeId) {
4171
4569
  const held = this.artifacts.get(nodeId);
4172
4570
  if (held !== void 0) return held;
@@ -4203,6 +4601,14 @@ var SearchKernel = class {
4203
4601
  usd: estimate(this.operationCosts, this.options.proposer.reservationUsd ?? 0)
4204
4602
  };
4205
4603
  }
4604
+ /** Overspend took committed spend, open holds and the unspent claim reserve
4605
+ * past the cap. Nothing new is proposed then, even at a zero-dollar prior. */
4606
+ overCap() {
4607
+ const { maxUsd } = this.state.header.budget;
4608
+ if (maxUsd === null) return false;
4609
+ const { committedUsd, openReservationUsd } = this.state.audit.spend;
4610
+ return committedUsd + openReservationUsd + this.state.budget.claimReserveUsd > maxUsd + USD_TOLERANCE;
4611
+ }
4206
4612
  pastDeadline() {
4207
4613
  const deadline = this.state.header.budget.deadline;
4208
4614
  return deadline !== null && this.now() >= Date.parse(deadline);
@@ -4216,8 +4622,11 @@ var SearchKernel = class {
4216
4622
  * finished, in registration order; `screening` counts the admitted nodes still
4217
4623
  * being screened. Nodes are ranked on the selection split, or on train when
4218
4624
  * the search declares no selection split. The view reads no test cell.
4625
+ * `maxAttempts` (default 3, the kernel's) says when an errored cell has no
4626
+ * attempt left, which makes its unit a dodge.
4219
4627
  */
4220
4628
  function searchPolicyView(state, input) {
4629
+ const maxAttempts = input.maxAttempts ?? DEFAULT_MAX_ATTEMPTS;
4221
4630
  const header = state.header;
4222
4631
  if (!header) throw new Error(`search ${state.searchId} has not been opened`);
4223
4632
  const split = header.splits.selection.tasks.length > 0 ? "selection" : "train";
@@ -4231,8 +4640,13 @@ function searchPolicyView(state, input) {
4231
4640
  screened: [...input.screened],
4232
4641
  screening: input.screening,
4233
4642
  complete: (nodeId) => {
4234
- const cells = state.cells({ nodeId }).filter((cell) => cell.split === split);
4235
- return cells.length > 0 && cells.every((cell) => cell.score !== null);
4643
+ let scored = false;
4644
+ for (const cell of state.cells({ nodeId })) {
4645
+ if (cell.split !== split) continue;
4646
+ if (cell.score !== null) scored = true;
4647
+ else if (cell.final || cell.outcome === "errored" && cell.attempts >= maxAttempts) return false;
4648
+ }
4649
+ return scored;
4236
4650
  },
4237
4651
  unitScores: (nodeId) => state.unitScores(nodeId, split),
4238
4652
  estimate: (nodeId, against) => estimateNode(state, nodeId, {
@@ -4880,12 +5294,14 @@ function canonicalHeader(header) {
4880
5294
  * claim nothing; a claim comes only from the sealed test split.
4881
5295
  */
4882
5296
  /**
4883
- * The hill climb. The leader starts at the root; a screened node that scored
4884
- * every unit of its screen takes the lead when its mean on the units it shares
4885
- * with the leader beats the leader's mean on those units. Nodes are taken in
4886
- * registration order, so the leader is a pure function of the ledger. The
4887
- * policy expands the leader, and only once every earlier child is screened,
4888
- * so each proposal sees every result before it.
5297
+ * The hill climb. The leader starts at the root; a screened node that dodged no
5298
+ * unit takes the lead when it scored every unit the leader scored and its mean
5299
+ * on them beats the leader's. A node measured on fewer units than the leader,
5300
+ * such as one an allocator has only screened, cannot take the lead on less
5301
+ * evidence than the leader holds. Nodes are taken in registration order, so
5302
+ * the leader is a pure function of the ledger. The policy expands the leader,
5303
+ * and only once every earlier child is screened, so each proposal sees every
5304
+ * result before it.
4889
5305
  */
4890
5306
  function incumbent(options = {}) {
4891
5307
  const { patience } = options;
@@ -4970,20 +5386,20 @@ function hillClimb(spec) {
4970
5386
  }
4971
5387
  };
4972
5388
  }
4973
- /** True when `challenger` improves on `holder` over the units both scored. */
5389
+ /** True when `challenger` scored every unit `holder` scored and improves on
5390
+ * `holder` over them. */
4974
5391
  function beats(view, challenger, holder) {
4975
- const held = new Map(view.unitScores(holder).map((unit) => [unit.unitId, unit.mean]));
5392
+ const held = view.unitScores(holder);
5393
+ if (held.length === 0) return false;
5394
+ const own = new Map(view.unitScores(challenger).map((unit) => [unit.unitId, unit.mean]));
4976
5395
  let challengerSum = 0;
4977
5396
  let holderSum = 0;
4978
- let shared = 0;
4979
- for (const unit of view.unitScores(challenger)) {
4980
- const other = held.get(unit.unitId);
4981
- if (other === void 0) continue;
4982
- challengerSum += unit.mean;
4983
- holderSum += other;
4984
- shared += 1;
5397
+ for (const unit of held) {
5398
+ const mean = own.get(unit.unitId);
5399
+ if (mean === void 0) return false;
5400
+ challengerSum += mean;
5401
+ holderSum += unit.mean;
4985
5402
  }
4986
- if (shared === 0) return false;
4987
5403
  return view.direction === "maximize" ? challengerSum > holderSum : challengerSum < holderSum;
4988
5404
  }
4989
5405
  /** Non-dominated complete screened nodes over the root's units, with crowding. */
@@ -7250,6 +7666,6 @@ function firstString(value) {
7250
7666
  return typeof value === "string" && value.trim() ? value : void 0;
7251
7667
  }
7252
7668
  //#endregion
7253
- export { redTeamDataset as $, createSearchHistoryReceipt as A, decideSearchClaim as B, searchEdgeId as C, assertCompleteSearchHistory as D, SearchHistoryRequiredError as E, runSearch as F, uniform as G, searchClaimReserveUsd as H, searchDivergence as I, runFinalComparison as J, dominates as K, searchExpansionIndex as L, verifySearchHistoryArtifact as M, verifySearchHistoryReceipt as N, assertSearchHistoryAdmissionOptions as O, SEARCH_KERNEL_SOURCE as P, DEFAULT_RED_TEAM_CORPUS as Q, searchPolicyView as R, developmentClaim as S, surfaceNode as T, pairedPromotionPower as U, planSearchClaim as V, requiredPairsForPairedPromotion as W, captureJudge as X, openAutoPr as Y, defaultProductionGate as Z, isProposedCandidate as _, transientDispatchFailure as a, evaluationUnitMap as at, incumbent as b, compareOptimizationMethods as c, runCampaign as ct, combineComparisonCosts as d, tangleTracesRoot as dt, redTeamReport as et, costFromLedgerSummary as f, readCachedCell as ft, runOptimization as g, runImprovementLoop as h, computeManifestHash as ht, quotaExhaustedUntil as i, captureFinalEvidencePolicy as it, searchHistoryCoverageRow as j, assertSearchHistoryMatchesState as k, optimizationTokenUsageFromSummary as l, planCampaignRun as lt, readGepaCandidatePopulationArtifact as m, cellCachePath as mt, JudgeParseError as n, runCanaries as nt, aggregateRunScore as o, reserveFinalEvidence as ot, assertGepaCandidatePopulationSummary as p, buildCellSchedule as pt, paretoFrontier as q, isTransientTransportFailure as r, assertIndependentEvaluationSplit as rt, clamp01 as s, runEval as st, llmJudge as t, scoreRedTeamOutput as tt, executeOptimizationMethod as u, resolveRunDir as ut, labelTrustRank as v, surfaceDiff as w, SearchRecorder as x, crowdedFrontierParent as y, SEARCH_CLAIM_RULE as z };
7669
+ export { defaultProductionGate as $, createSearchHistoryReceipt as A, decideSearchClaim as B, searchEdgeId as C, assertCompleteSearchHistory as D, SearchHistoryRequiredError as E, runSearch as F, requiredPairsForPairedPromotion as G, searchClaimReserveUsd as H, searchDivergence as I, dominates as J, asha as K, searchExpansionIndex as L, verifySearchHistoryArtifact as M, verifySearchHistoryReceipt as N, assertSearchHistoryAdmissionOptions as O, SEARCH_KERNEL_SOURCE as P, captureJudge as Q, searchPolicyView as R, developmentClaim as S, surfaceNode as T, verifySearchClaim as U, planSearchClaim as V, pairedPromotionPower as W, runFinalComparison as X, paretoFrontier as Y, openAutoPr as Z, isProposedCandidate as _, computeManifestHash as _t, transientDispatchFailure as a, assertIndependentEvaluationSplit as at, incumbent as b, compareOptimizationMethods as c, reserveFinalEvidence as ct, combineComparisonCosts as d, planCampaignRun as dt, DEFAULT_RED_TEAM_CORPUS as et, costFromLedgerSummary as f, resolveRunDir as ft, runOptimization as g, cellCachePath as gt, runImprovementLoop as h, buildCellSchedule as ht, quotaExhaustedUntil as i, runCanaries as it, searchHistoryCoverageRow as j, assertSearchHistoryMatchesState as k, optimizationTokenUsageFromSummary as l, runEval as lt, readGepaCandidatePopulationArtifact as m, readCachedCell as mt, JudgeParseError as n, redTeamReport as nt, aggregateRunScore as o, captureFinalEvidencePolicy as ot, assertGepaCandidatePopulationSummary as p, tangleTracesRoot as pt, uniform as q, isTransientTransportFailure as r, scoreRedTeamOutput as rt, clamp01 as s, evaluationUnitMap as st, llmJudge as t, redTeamDataset as tt, executeOptimizationMethod as u, runCampaign as ut, labelTrustRank as v, surfaceDiff as w, SearchRecorder as x, crowdedFrontierParent as y, SEARCH_CLAIM_RULE as z };
7254
7670
 
7255
- //# sourceMappingURL=llm-judge-Cififl_V.js.map
7671
+ //# sourceMappingURL=llm-judge-CvKpaRKY.js.map