@skill-harness/core 0.17.0 → 0.18.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 (93) hide show
  1. package/README.md +1 -2
  2. package/dist/adapters/types.d.ts +0 -12
  3. package/dist/capture-trace-types.d.ts +0 -96
  4. package/dist/capture-trace-types.js +0 -4
  5. package/dist/command-cost.d.ts +1 -1
  6. package/dist/command-cost.js +0 -5
  7. package/dist/execution-trace.js +1 -1
  8. package/dist/index.d.ts +3 -23
  9. package/dist/index.js +3 -23
  10. package/dist/instruction-coverage.d.ts +0 -7
  11. package/dist/instruction-coverage.js +5 -7
  12. package/dist/journal.d.ts +0 -8
  13. package/dist/metrics.d.ts +18 -0
  14. package/dist/metrics.js +28 -0
  15. package/dist/redaction.d.ts +6 -0
  16. package/dist/redaction.js +55 -0
  17. package/dist/regate.js +6 -71
  18. package/dist/regrade.d.ts +1 -3
  19. package/dist/regrade.js +1 -21
  20. package/dist/report.d.ts +1 -15
  21. package/dist/report.js +1 -13
  22. package/dist/reps.d.ts +1 -2
  23. package/dist/reps.js +0 -2
  24. package/dist/results.d.ts +0 -9
  25. package/dist/results.js +2 -19
  26. package/dist/run.js +11 -72
  27. package/dist/seeded.d.ts +1 -7
  28. package/dist/seeded.js +5 -11
  29. package/dist/sources.js +4 -9
  30. package/dist/spec.d.ts +0 -13
  31. package/dist/spec.js +6 -48
  32. package/dist/trajectory-events.d.ts +58 -0
  33. package/dist/trajectory-events.js +119 -0
  34. package/package.json +1 -1
  35. package/schemas/results-v2.schema.json +376 -75
  36. package/schemas/specification-v1.schema.json +128 -174
  37. package/dist/adjudication.d.ts +0 -219
  38. package/dist/adjudication.js +0 -422
  39. package/dist/adoption.d.ts +0 -128
  40. package/dist/adoption.js +0 -102
  41. package/dist/affected.d.ts +0 -88
  42. package/dist/affected.js +0 -222
  43. package/dist/capture.d.ts +0 -193
  44. package/dist/capture.js +0 -344
  45. package/dist/comparison.d.ts +0 -97
  46. package/dist/comparison.js +0 -189
  47. package/dist/factory-calibration.d.ts +0 -63
  48. package/dist/factory-calibration.js +0 -115
  49. package/dist/intervention-results.d.ts +0 -6
  50. package/dist/intervention-results.js +0 -52
  51. package/dist/intervention.d.ts +0 -123
  52. package/dist/intervention.js +0 -218
  53. package/dist/investigation.d.ts +0 -94
  54. package/dist/investigation.js +0 -148
  55. package/dist/judge-agreement.d.ts +0 -19
  56. package/dist/judge-agreement.js +0 -31
  57. package/dist/qualification-capture.d.ts +0 -44
  58. package/dist/qualification-capture.js +0 -163
  59. package/dist/qualification-config.d.ts +0 -233
  60. package/dist/qualification-config.js +0 -694
  61. package/dist/qualification-lock.d.ts +0 -15
  62. package/dist/qualification-lock.js +0 -87
  63. package/dist/qualification-oauth-directory.d.ts +0 -79
  64. package/dist/qualification-oauth-directory.js +0 -444
  65. package/dist/qualification-panel-store.d.ts +0 -14
  66. package/dist/qualification-panel-store.js +0 -188
  67. package/dist/qualification-panels.d.ts +0 -99
  68. package/dist/qualification-panels.js +0 -91
  69. package/dist/qualification-process.d.ts +0 -13
  70. package/dist/qualification-process.js +0 -190
  71. package/dist/qualification-runner.d.ts +0 -203
  72. package/dist/qualification-runner.js +0 -2037
  73. package/dist/qualification-store.d.ts +0 -187
  74. package/dist/qualification-store.js +0 -833
  75. package/dist/qualification-validation.d.ts +0 -12
  76. package/dist/qualification-validation.js +0 -8
  77. package/dist/screen.d.ts +0 -31
  78. package/dist/screen.js +0 -105
  79. package/dist/trajectory-gates.d.ts +0 -137
  80. package/dist/trajectory-gates.js +0 -576
  81. package/dist/trusted-host-supervision.d.ts +0 -25
  82. package/dist/trusted-host-supervision.js +0 -94
  83. package/dist/work-capture-schema.d.ts +0 -38
  84. package/dist/work-capture-schema.js +0 -33
  85. package/dist/work-capture.d.ts +0 -43
  86. package/dist/work-capture.js +0 -81
  87. package/dist/work-signals.d.ts +0 -55
  88. package/dist/work-signals.js +0 -71
  89. package/schemas/qualification-cell-result-v1.schema.json +0 -32
  90. package/schemas/qualification-config-v1.schema.json +0 -244
  91. package/schemas/qualification-invocation-request-v1.schema.json +0 -59
  92. package/schemas/qualification-judge-panel-result-v1.schema.json +0 -42
  93. package/schemas/trajectory-event-v1.schema.json +0 -80
@@ -4,197 +4,134 @@
4
4
  "title": "skill-harness specification v1",
5
5
  "type": "object",
6
6
  "additionalProperties": false,
7
- "required": ["skill", "judge_persona", "ship_bar", "scenarios"],
7
+ "required": [
8
+ "skill",
9
+ "judge_persona",
10
+ "ship_bar",
11
+ "scenarios"
12
+ ],
8
13
  "properties": {
9
- "schema": { "const": 1 },
10
- "skill": { "type": "string", "minLength": 1 },
11
- "judge_persona": { "type": "string", "minLength": 1 },
12
- "ship_bar": {
13
- "type": "object",
14
- "additionalProperties": false,
15
- "required": ["total", "min_pass"],
16
- "properties": {
17
- "total": { "type": "integer", "minimum": 1 },
18
- "min_pass": { "type": "integer", "minimum": 1 },
19
- "no_critical_fail": { "type": "boolean" }
20
- }
14
+ "schema": {
15
+ "const": 1
21
16
  },
22
- "critical": { "type": "array", "items": { "type": "string" }, "uniqueItems": true },
23
- "adjudication": { "type": "object" },
24
- "scenarios": { "type": "array", "items": { "$ref": "#/$defs/scenario" } }
25
- },
26
- "$defs": {
27
- "stringList": { "type": "array", "items": { "type": "string", "minLength": 1 }, "minItems": 1, "uniqueItems": true },
28
- "predicate": {
29
- "oneOf": [
30
- { "type": ["string", "number", "boolean"] },
31
- {
32
- "type": "object",
33
- "additionalProperties": false,
34
- "properties": {
35
- "equals": {},
36
- "contains": { "type": "string" },
37
- "starts_with": { "type": "string" },
38
- "ends_with": { "type": "string" },
39
- "matches": { "type": "string" },
40
- "exists": { "type": "boolean" },
41
- "any": { "$ref": "#/$defs/predicate" }
42
- },
43
- "minProperties": 1
44
- }
45
- ]
46
- },
47
- "count": {
48
- "type": "object",
49
- "additionalProperties": false,
50
- "properties": {
51
- "min": { "type": "integer", "minimum": 0 },
52
- "max": { "type": "integer", "minimum": 0 }
53
- }
17
+ "skill": {
18
+ "type": "string",
19
+ "minLength": 1
54
20
  },
55
- "selector": {
56
- "type": "object",
57
- "additionalProperties": false,
58
- "required": ["event"],
59
- "properties": {
60
- "event": { "type": "string", "minLength": 1 },
61
- "where": { "type": "object", "additionalProperties": { "$ref": "#/$defs/predicate" } },
62
- "select": { "enum": ["first", "last", "all"] }
63
- }
21
+ "judge_persona": {
22
+ "type": "string",
23
+ "minLength": 1
64
24
  },
65
- "requiredSelector": {
25
+ "ship_bar": {
66
26
  "type": "object",
67
27
  "additionalProperties": false,
68
- "required": ["event"],
28
+ "required": [
29
+ "total",
30
+ "min_pass"
31
+ ],
69
32
  "properties": {
70
- "event": { "type": "string", "minLength": 1 },
71
- "where": { "type": "object", "additionalProperties": { "$ref": "#/$defs/predicate" } },
72
- "select": { "enum": ["first", "last", "all"] },
73
- "count": { "$ref": "#/$defs/count" }
33
+ "total": {
34
+ "type": "integer",
35
+ "minimum": 1
36
+ },
37
+ "min_pass": {
38
+ "type": "integer",
39
+ "minimum": 1
40
+ },
41
+ "no_critical_fail": {
42
+ "type": "boolean"
43
+ }
74
44
  }
75
45
  },
76
- "correlation": {
77
- "type": "object",
78
- "additionalProperties": false,
79
- "required": ["left", "right"],
80
- "properties": {
81
- "left": { "$ref": "#/$defs/selector" },
82
- "right": { "$ref": "#/$defs/selector" },
83
- "same": { "$ref": "#/$defs/stringList" },
84
- "different": { "$ref": "#/$defs/stringList" },
85
- "order": { "enum": ["before", "after"] }
46
+ "critical": {
47
+ "type": "array",
48
+ "items": {
49
+ "type": "string"
86
50
  },
87
- "anyOf": [{ "required": ["same"] }, { "required": ["different"] }, { "required": ["order"] }]
88
- },
89
- "freshness": {
90
- "type": "object",
91
- "additionalProperties": false,
92
- "required": ["subject", "after"],
93
- "properties": {
94
- "subject": { "$ref": "#/$defs/selector" },
95
- "after": { "type": "array", "items": { "$ref": "#/$defs/selector" }, "minItems": 1 },
96
- "same": { "$ref": "#/$defs/stringList" }
97
- }
98
- },
99
- "unique": {
100
- "type": "object",
101
- "additionalProperties": false,
102
- "required": ["events", "fields"],
103
- "properties": {
104
- "events": { "$ref": "#/$defs/selector" },
105
- "fields": { "$ref": "#/$defs/stringList" }
106
- }
51
+ "uniqueItems": true
107
52
  },
108
- "forbidAfter": {
109
- "type": "object",
110
- "additionalProperties": false,
111
- "required": ["anchor", "forbidden"],
112
- "properties": {
113
- "anchor": { "$ref": "#/$defs/selector" },
114
- "forbidden": { "type": "array", "items": { "$ref": "#/$defs/selector" }, "minItems": 1 },
115
- "same": { "$ref": "#/$defs/stringList" },
116
- "anchor_optional": { "type": "boolean" }
53
+ "scenarios": {
54
+ "type": "array",
55
+ "items": {
56
+ "$ref": "#/$defs/scenario"
117
57
  }
118
- },
119
- "approvalAssertion": {
120
- "type": "object",
121
- "additionalProperties": false,
122
- "required": ["grant", "use"],
123
- "properties": {
124
- "grant": { "$ref": "#/$defs/selector" },
125
- "use": { "$ref": "#/$defs/selector" },
126
- "same": { "$ref": "#/$defs/stringList" },
127
- "scopes": { "$ref": "#/$defs/stringList" },
128
- "sources": { "$ref": "#/$defs/stringList" },
129
- "unexpired": { "type": "boolean" },
130
- "max_uses": { "type": "integer", "minimum": 1 }
131
- }
132
- },
133
- "coverageAssertion": {
134
- "type": "object",
135
- "additionalProperties": false,
136
- "required": ["requirements"],
137
- "properties": {
138
- "requirements": { "$ref": "#/$defs/stringList" },
139
- "events": { "$ref": "#/$defs/selector" }
140
- }
141
- },
142
- "trajectory": {
143
- "type": "object",
144
- "additionalProperties": false,
145
- "required": ["version"],
146
- "properties": {
147
- "version": { "const": "1.0" },
148
- "require": { "type": "array", "items": { "$ref": "#/$defs/requiredSelector" }, "minItems": 1 },
149
- "forbid": { "type": "array", "items": { "$ref": "#/$defs/selector" }, "minItems": 1 },
150
- "ordered": { "type": "array", "items": { "type": "array", "items": { "$ref": "#/$defs/selector" }, "minItems": 1 }, "minItems": 1 },
151
- "correlate": { "type": "array", "items": { "$ref": "#/$defs/correlation" }, "minItems": 1 },
152
- "freshness": { "type": "array", "items": { "$ref": "#/$defs/freshness" }, "minItems": 1 },
153
- "unique": { "type": "array", "items": { "$ref": "#/$defs/unique" }, "minItems": 1 },
154
- "forbid_after": { "type": "array", "items": { "$ref": "#/$defs/forbidAfter" }, "minItems": 1 },
155
- "approvals": { "type": "array", "items": { "$ref": "#/$defs/approvalAssertion" }, "minItems": 1 },
156
- "coverage": { "type": "array", "items": { "$ref": "#/$defs/coverageAssertion" }, "minItems": 1 }
157
- },
158
- "minProperties": 2
159
- },
58
+ }
59
+ },
60
+ "$defs": {
160
61
  "scenario": {
161
62
  "type": "object",
162
63
  "additionalProperties": false,
163
- "required": ["id", "title", "turns", "checklist"],
64
+ "required": [
65
+ "id",
66
+ "title",
67
+ "turns",
68
+ "checklist"
69
+ ],
164
70
  "properties": {
165
- "id": { "type": "string", "minLength": 1 },
166
- "title": { "type": "string", "minLength": 1 },
167
- "critical": { "type": "boolean" },
168
- "mode": { "enum": ["inline", "seeded"] },
169
- "fixture": { "type": "string" },
170
- "turns": { "type": "array", "items": { "type": "string" }, "minItems": 1 },
171
- "checklist": { "type": "array", "items": { "type": "string" }, "minItems": 1 },
172
- "covers": { "type": "array", "items": { "type": "string" } },
173
- "reps": { "type": "integer", "minimum": 1 },
174
- "pass_threshold": { "type": "number", "minimum": 0, "maximum": 1 },
175
- "system_prompt_file": { "type": "string" },
71
+ "id": {
72
+ "type": "string",
73
+ "minLength": 1
74
+ },
75
+ "title": {
76
+ "type": "string",
77
+ "minLength": 1
78
+ },
79
+ "critical": {
80
+ "type": "boolean"
81
+ },
82
+ "mode": {
83
+ "enum": [
84
+ "inline",
85
+ "seeded"
86
+ ]
87
+ },
88
+ "fixture": {
89
+ "type": "string"
90
+ },
91
+ "turns": {
92
+ "type": "array",
93
+ "items": {
94
+ "type": "string"
95
+ },
96
+ "minItems": 1
97
+ },
98
+ "checklist": {
99
+ "type": "array",
100
+ "items": {
101
+ "type": "string"
102
+ },
103
+ "minItems": 1
104
+ },
105
+ "covers": {
106
+ "type": "array",
107
+ "items": {
108
+ "type": "string"
109
+ }
110
+ },
111
+ "reps": {
112
+ "type": "integer",
113
+ "minimum": 1
114
+ },
115
+ "pass_threshold": {
116
+ "type": "number",
117
+ "minimum": 0,
118
+ "maximum": 1
119
+ },
120
+ "system_prompt_file": {
121
+ "type": "string"
122
+ },
176
123
  "env": {
177
124
  "type": "object",
178
125
  "additionalProperties": false,
179
126
  "properties": {
180
127
  "workspace": {},
181
- "remote": { "type": "boolean" },
182
- "extensions": { "type": "array", "items": { "type": "string" } },
183
- "event_sources": {
128
+ "remote": {
129
+ "type": "boolean"
130
+ },
131
+ "extensions": {
184
132
  "type": "array",
185
133
  "items": {
186
- "type": "object",
187
- "additionalProperties": false,
188
- "required": ["adapter", "path"],
189
- "properties": {
190
- "adapter": { "enum": ["normalized-v1", "principal-assurance-v1", "pi-daddy-v1", "pi-daddy-ledger-v3"] },
191
- "path": {
192
- "type": "string",
193
- "minLength": 1,
194
- "pattern": "^(?!/)(?![A-Za-z]:[\\\\/])(?!.*\\\\)(?!.*//)(?!.*(?:^|/)\\.\\.?(?:/|$)).+$"
195
- },
196
- "required": { "type": "boolean" }
197
- }
134
+ "type": "string"
198
135
  }
199
136
  }
200
137
  }
@@ -203,12 +140,29 @@
203
140
  "type": "object",
204
141
  "additionalProperties": false,
205
142
  "properties": {
206
- "vitest": { "type": "boolean" },
207
- "diff_contains": { "type": "array", "items": { "type": "string", "minLength": 1 } },
208
- "diff_excludes": { "type": "array", "items": { "type": "string", "minLength": 1 } },
209
- "post_test": { "type": "string" },
210
- "trace": { "type": "object" },
211
- "trajectory": { "$ref": "#/$defs/trajectory" }
143
+ "vitest": {
144
+ "type": "boolean"
145
+ },
146
+ "diff_contains": {
147
+ "type": "array",
148
+ "items": {
149
+ "type": "string",
150
+ "minLength": 1
151
+ }
152
+ },
153
+ "diff_excludes": {
154
+ "type": "array",
155
+ "items": {
156
+ "type": "string",
157
+ "minLength": 1
158
+ }
159
+ },
160
+ "post_test": {
161
+ "type": "string"
162
+ },
163
+ "trace": {
164
+ "type": "object"
165
+ }
212
166
  }
213
167
  }
214
168
  }
@@ -1,219 +0,0 @@
1
- import type { HarnessAdapter, ModelRef } from "./adapters/types.js";
2
- import type { ScenarioResult, AdjudicationResult, Judgment, ResultsFile, CriterionVote } from "./results.js";
3
- import type { Scenario, ShipBar, Spec } from "./spec.js";
4
- import type { Verdict } from "./score.js";
5
- /**
6
- * Confidence-aware adjudication: decide which judged cells are untrustworthy
7
- * enough to be worth asking again, collapse the resulting votes, and project the
8
- * outcome into the fields the existing scorer already understands.
9
- *
10
- * Two rules govern everything here.
11
- *
12
- * **Spend is never implicit.** A spec may declare triggers, but only an explicit
13
- * `--auto-rejudge` (or a confirmed extension dialog) authorizes a second call.
14
- * `plan(...)` is a pure function that returns what WOULD be spent; nothing in
15
- * this module calls a judge.
16
- *
17
- * **Unresolved disagreement must not resolve itself.** When two judges disagree
18
- * and no third is authorized, the cell projects to `suspect: true` — which the
19
- * existing ship bar already treats as blocking. That is deliberate reuse rather
20
- * than a parallel gate: a second ship rule could drift out of step with the
21
- * first, and a disagreement that quietly became a PASS is the exact failure this
22
- * feature exists to prevent.
23
- */
24
- export type TriggerKind = "ambiguous" | "contradictory" | "non_unanimous" | "ship_deciding";
25
- /** Maximum judgments per cell, first wave included. Hard cap, not a default. */
26
- export declare const MAX_JUDGMENTS = 3;
27
- export interface CellState {
28
- id: string;
29
- /** First-wave verdict for the cell (already aggregated over reps). */
30
- verdict: Verdict;
31
- reason: string;
32
- /** The judge misfired, or the cell is otherwise untrustworthy. */
33
- suspect: boolean;
34
- /** Per-rep verdicts, when the cell ran with reps. Empty for a single-rep cell. */
35
- repVerdicts?: Verdict[];
36
- criteria?: CriterionVote[];
37
- /** Delivery prerequisite for schema-3 cells; non-PASS cells are never judged. */
38
- deliveryStatus?: "PASS" | "NOT-MEASURED" | "ERROR";
39
- /** The actual selected repetition's primary vote; aggregate fields remain for planning only. */
40
- primaryJudgment?: Judgment;
41
- }
42
- export interface TriggerDecision {
43
- id: string;
44
- triggers: TriggerKind[];
45
- }
46
- export interface PlanInput {
47
- cells: CellState[];
48
- scenarios: Scenario[];
49
- shipBar: ShipBar;
50
- critical: string[];
51
- /** Which trigger classes are enabled. Defaults to all four. */
52
- enabled?: TriggerKind[];
53
- /** A tie-break judge exists, so a third call is permitted on disagreement. */
54
- tieBreakAvailable: boolean;
55
- }
56
- export interface AdjudicationPlan {
57
- decisions: TriggerDecision[];
58
- /** Cells that will be re-judged at least once. */
59
- triggered: string[];
60
- /**
61
- * Triggered cells whose VERDICT this plan provably cannot settle.
62
- *
63
- * Their first-wave judgment misfired, so it is not a clean vote (see
64
- * `collapseJudgments`). With no tie-break judge, one extra call reaches at most
65
- * one clean vote and a collapse needs two: the cell returns `unresolved` and
66
- * stays `suspect: true` whatever the second judge says.
67
- *
68
- * They are still re-judged, and deliberately so — the second opinion is the
69
- * evidence an author reads to resolve the misfire by hand, which is the only
70
- * way these cells ever get resolved. What was missing was saying so: the
71
- * preflight offered them alongside cells a call could actually settle, so the
72
- * buyer could not tell which was which. This list is that disclosure.
73
- */
74
- needsTieBreak: string[];
75
- /**
76
- * Exact upper bound on ADDITIONAL judge calls this plan can make.
77
- *
78
- * Deliberately a call count, not a cost estimate. The default judge runs on a
79
- * Claude subscription and reports no per-call usage back to the harness, so a
80
- * dollar figure there would be invented. Count is the only honest unit.
81
- */
82
- maxAdditionalCalls: number;
83
- }
84
- /**
85
- * Classify triggers and compute the spend ceiling. Pure — calls nothing.
86
- *
87
- * Triggers are computed from the COMPLETE first wave, never incrementally. A
88
- * `ship_deciding` cell can only be identified once every other cell's verdict is
89
- * known, and computing it mid-wave would make the trigger set depend on the order
90
- * scenarios happened to finish in.
91
- */
92
- export declare function planAdjudication(input: PlanInput): AdjudicationPlan;
93
- export type AdjudicationState = "confirmed" | "tie_broken" | "unresolved";
94
- /**
95
- * Collapse the judgments recorded for one cell.
96
- *
97
- * A judgment is a CLEAN vote only if it is a plain PASS or FAIL from a judge that
98
- * did not misfire. Ambiguous, suspect and unreadable judgments are recorded in
99
- * full but never counted — a malformed answer is not evidence, and letting one
100
- * cast a deciding vote would launder exactly the unreliability being measured.
101
- */
102
- export declare function collapseJudgments(judgments: Judgment[], trigger: TriggerKind): AdjudicationResult;
103
- /**
104
- * Project an adjudication onto the compatibility fields the scorer reads.
105
- *
106
- * `unresolved` becomes `suspect: true`, which the existing ship bar already
107
- * blocks on. The raw judgments survive on the result either way — an author
108
- * resolving this needs to see what each judge actually said, not just the
109
- * collapsed answer.
110
- */
111
- export declare function boundAdjudicationToRepetitions(result: ScenarioResult, scenario: Scenario, adj: AdjudicationResult): AdjudicationResult;
112
- export declare function projectAdjudication(result: ScenarioResult, adj: AdjudicationResult): ScenarioResult;
113
- /** Apply the one-transcript bound and label it only when the bound changed the panel result. */
114
- export declare function projectAdjudicationForScenario(result: ScenarioResult, scenario: Scenario, adj: AdjudicationResult): ScenarioResult;
115
- /** Ask one judge about one cell's saved transcript. Supplied by the caller. */
116
- export type RejudgeFn = (id: string, judge: ModelRef) => Promise<{
117
- verdict: Verdict;
118
- reason: string;
119
- suspect: boolean;
120
- criteria?: CriterionVote[];
121
- }>;
122
- export interface RunAdjudicationOptions {
123
- plan: AdjudicationPlan;
124
- cells: CellState[];
125
- /** The judge that produced the first wave — recorded as judgment 1. */
126
- primaryJudge: ModelRef;
127
- secondaryJudge: ModelRef;
128
- /** Absent means a disagreement stays unresolved rather than being tie-broken. */
129
- tieBreakJudge?: ModelRef;
130
- rejudge: RejudgeFn;
131
- log?: (msg: string) => void;
132
- }
133
- export interface RunAdjudicationResult {
134
- /** Per triggered cell, the collapsed adjudication. Cells that did not trigger are absent. */
135
- byId: Map<string, AdjudicationResult>;
136
- /** Judge calls actually made. Never exceeds `plan.maxAdditionalCalls`. */
137
- callsMade: number;
138
- }
139
- /**
140
- * Execute an adjudication plan.
141
- *
142
- * ONE implementation, called from `run`, `grade` and the review server's rejudge
143
- * path. The plan's three collapse policies were the most likely thing to be
144
- * reimplemented three times and to disagree — a cell that shipped from the CLI
145
- * and blocked in the browser would be worse than no feature.
146
- *
147
- * The tie-break call is made only when the secondary genuinely disagreed. A third
148
- * opinion on a settled cell is spend with no decision attached to it.
149
- */
150
- export declare function runAdjudication(opts: RunAdjudicationOptions): Promise<RunAdjudicationResult>;
151
- export interface AdjudicateRunOptions {
152
- runDir: string;
153
- spec: Spec;
154
- adapter: HarnessAdapter;
155
- /** The first-wave results this adjudication refines. */
156
- results: ResultsFile;
157
- primaryJudge: ModelRef;
158
- secondaryJudge: ModelRef;
159
- tieBreakJudge?: ModelRef;
160
- specDir: string;
161
- now: () => string;
162
- log?: (msg: string) => void;
163
- }
164
- /**
165
- * Adjudicate a completed run: plan, disclose the ceiling, execute, persist.
166
- *
167
- * Re-judges the SAME saved transcripts — no subject re-run, so the model's
168
- * behavior is held fixed and any movement is the judge. That is what makes this
169
- * a measurement of judge reliability rather than another sample of the model.
170
- */
171
- export declare function adjudicateRun(opts: AdjudicateRunOptions): Promise<ResultsFile>;
172
- /**
173
- * Build the plan's input cells from a run.
174
- *
175
- * EXPORTED so the CLI, the review server and the pi extension all price the work
176
- * exactly as `adjudicateRun` will perform it. When the preflight built cells
177
- * without `repVerdicts` and the executor built them with, the browser could show
178
- * "no cell triggered" and then spend on non-unanimous cells nobody was told
179
- * about — inverting the one invariant this feature actually promises.
180
- */
181
- export declare function cellsFromResults(runDir: string, results: ResultsFile): CellState[];
182
- /**
183
- * Resolve and validate the extra judges.
184
- *
185
- * Every configured judge passes the SAME two gates the primary does: the metered
186
- * refusal and the judge≠subject check. A secondary judge is still a judge — a
187
- * feature that multiplies judge calls is the last place to let one slip past the
188
- * policy that exists because a default once billed a corpus by accident.
189
- *
190
- * Returns null when adjudication was not authorized, so callers can treat "not
191
- * enabled" and "enabled with no triggers" as different things.
192
- */
193
- export declare function resolveAdjudicationJudges(opts: {
194
- enabled: boolean;
195
- primary: ModelRef;
196
- secondaryToken?: string;
197
- tieBreakToken?: string;
198
- /**
199
- * The run's recorded subject, as a raw token.
200
- *
201
- * A TOKEN rather than a parsed ref, and parsed only after the `enabled` check:
202
- * an eagerly-parsed argument threw on any run whose recorded model is not
203
- * `provider:model` — which killed the whole regrade over a provenance oddity in
204
- * a field only used for a warning.
205
- */
206
- subjectToken: string;
207
- parseRef: (token: string) => ModelRef;
208
- assertAllowed: (judge: ModelRef, source: string) => void;
209
- resemblesSubject: (judge: ModelRef, subject: ModelRef) => boolean;
210
- warn: (msg: string) => void;
211
- }): {
212
- secondary: ModelRef;
213
- tieBreak?: ModelRef;
214
- } | null;
215
- /** Human-readable preflight line. Counts, never dollars — see `maxAdditionalCalls`. */
216
- export declare function formatAdjudicationPlan(plan: AdjudicationPlan, judges: {
217
- secondary: ModelRef;
218
- tieBreak?: ModelRef;
219
- }): string;