shapeup-sdlc 1.7.0 → 3.0.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/.claude/settings.local.example.json +5 -5
- package/.claude-plugin/plugin.json +1 -1
- package/AGENTS.md +17 -3
- package/README.md +124 -103
- package/SECURITY.md +37 -30
- package/bin/init.mjs +77 -47
- package/bin/lib/grant.mjs +145 -0
- package/commands/build.md +7 -6
- package/commands/ship.md +29 -16
- package/commands/wire.md +1 -1
- package/hooks/dispatch-receipt.mjs +195 -0
- package/hooks/gate-intake.mjs +3 -3
- package/hooks/gate-zerowork.mjs +25 -24
- package/hooks/hooks.json +9 -48
- package/hooks/lib/decision.mjs +19 -8
- package/hooks/safety-spine.mjs +3 -3
- package/hooks/sandbox-guard.mjs +84 -40
- package/{skills/tech-lead/scripts/compile-order.mjs → kernel/compile.mjs} +283 -41
- package/{skills/tech-lead/scripts/gate-answers.mjs → kernel/gate.mjs} +58 -14
- package/kernel/harness.mjs +134 -0
- package/{skills/tech-lead/scripts/fit-check.mjs → kernel/init/fit.mjs} +15 -12
- package/{skills/tech-lead/scripts/init-run.mjs → kernel/init/run.mjs} +152 -31
- package/{skills/tech-lead/scripts → kernel}/lib/argv.mjs +52 -31
- package/{skills/tech-lead/scripts/lib/contract-md.mjs → kernel/lib/contract.mjs} +251 -7
- package/kernel/lib/paths.mjs +491 -0
- package/kernel/probe/concurrency.mjs +510 -0
- package/{skills/tech-lead/scripts/aegis-digest.mjs → kernel/probe/digest.mjs} +9 -10
- package/kernel/probe/eval.mjs +77 -0
- package/kernel/probe/leg.mjs +125 -0
- package/{skills/tech-lead/scripts/resume-state.mjs → kernel/probe/resume.mjs} +204 -63
- package/{skills/tech-lead/scripts → kernel/probe}/stats.mjs +14 -9
- package/kernel/probe/t0.mjs +66 -0
- package/{skills/ba-pitch-analyzer/scripts/board-derive.mjs → kernel/reduce/board.mjs} +99 -23
- package/kernel/reduce/graph.mjs +437 -0
- package/{skills/tech-lead/scripts/hill-derive.mjs → kernel/reduce/hill.mjs} +28 -9
- package/kernel/reduce/ingest.mjs +633 -0
- package/{hooks/slop-cleaner.mjs → kernel/reduce/leftovers.mjs} +40 -57
- package/{skills/tech-lead/scripts/ship-report.mjs → kernel/reduce/ship.mjs} +61 -13
- package/{skills/tech-lead/scripts/run-snapshot.mjs → kernel/reduce/snapshot.mjs} +21 -15
- package/{skills/spec-evaluator/scripts/verdict-ledger.mjs → kernel/reduce/verdict.mjs} +13 -7
- package/kernel/report/export.mjs +321 -0
- package/kernel/report/facts.mjs +209 -0
- package/{skills/tech-lead/scripts/budget-check.mjs → kernel/verify/budget.mjs} +15 -12
- package/kernel/verify/dispatch.mjs +114 -0
- package/{skills/tech-lead/scripts/validate-envelope.mjs → kernel/verify/envelope.mjs} +20 -15
- package/{skills/tech-lead/scripts/lib → kernel/verify}/ratchet-tree.mjs +36 -14
- package/kernel/verify/skills.mjs +125 -0
- package/kernel/verify/spec.mjs +559 -0
- package/{skills/tech-lead/scripts/t0-verify.mjs → kernel/verify/t0.mjs} +134 -24
- package/{skills/tech-lead/scripts/trace-lint.mjs → kernel/verify/trace.mjs} +26 -11
- package/oracles/http-oracle.mjs +1 -1
- package/oracles/process-oracle.mjs +1 -1
- package/oracles/snapshot-oracle.mjs +1 -1
- package/oracles/test-oracle.mjs +1 -1
- package/package.json +11 -9
- package/skills/ba-pitch-analyzer/SKILL.md +5 -5
- package/skills/ba-pitch-analyzer/assets/templates/_index.tmpl.md +1 -1
- package/skills/ba-pitch-analyzer/assets/templates/api-feasibility.tmpl.md +12 -7
- package/skills/ba-pitch-analyzer/assets/templates/contracts/third-party-api.contract.tmpl.md +6 -3
- package/skills/ba-pitch-analyzer/assets/templates/cross-context/migration-plan.tmpl.md +5 -4
- package/skills/ba-pitch-analyzer/assets/templates/cross-context/team-handoff.tmpl.md +23 -13
- package/skills/ba-pitch-analyzer/assets/templates/scope-summary.tmpl.md +17 -12
- package/skills/ba-pitch-analyzer/assets/templates/synthesis.tmpl.md +17 -38
- package/skills/ba-pitch-analyzer/assets/templates/task.tmpl.md +3 -0
- package/skills/ba-pitch-analyzer/references/contract-patterns.md +8 -4
- package/skills/ba-pitch-analyzer/references/doc-schemas.md +2 -0
- package/skills/ba-pitch-analyzer/references/task-generation.md +2 -2
- package/skills/qa-edge-hunter/SKILL.md +7 -3
- package/skills/scope-architect/SKILL.md +40 -6
- package/skills/solution-architect/SKILL.md +19 -4
- package/skills/spec-evaluator/SKILL.md +12 -2
- package/skills/task-executor/SKILL.md +7 -6
- package/skills/tech-lead/SKILL.md +50 -38
- package/skills/tech-lead/references/gates.md +71 -20
- package/skills/tech-lead/references/protocol.md +832 -0
- package/skills/tech-lead/schemas/domain.schema.json +341 -66
- package/skills/tech-lead/schemas/work-order.schema.json +11 -2
- package/skills/tech-lead/schemas/work-result.schema.json +1 -1
- package/skills/tech-lead/workflows/shapeup-run.js +1327 -750
- package/hooks/anti-rationalization.mjs +0 -238
- package/hooks/compact-snapshot.mjs +0 -47
- package/hooks/gate-deadline.mjs +0 -147
- package/hooks/gate-l2.mjs +0 -161
- package/hooks/session-rehydrate.mjs +0 -108
- package/skills/ba-pitch-analyzer/scripts/spec-lint.mjs +0 -239
- package/skills/spec-evaluator/README.md +0 -93
- package/skills/tech-lead/README.md +0 -71
- package/skills/tech-lead/references/delegation.md +0 -261
- package/skills/tech-lead/references/hard-rules.md +0 -34
- package/skills/tech-lead/references/invocation.md +0 -45
- package/skills/tech-lead/references/ledger-schema.md +0 -213
- package/skills/tech-lead/references/round-protocol.md +0 -234
- package/skills/tech-lead/references/state-model.md +0 -66
- package/skills/tech-lead/scripts/ingest-result.mjs +0 -258
- package/skills/tech-lead/scripts/lib/is-main.mjs +0 -81
- package/skills/tech-lead/scripts/lib/paths.mjs +0 -280
- package/skills/tech-lead/scripts/run-workflow.mjs +0 -381
- package/skills/translator/README.md +0 -66
|
@@ -4,13 +4,56 @@
|
|
|
4
4
|
"description": "The CENTRAL domain registry of the pure-skill architecture. Every shared field that crosses a skill boundary is defined here exactly once, with its meaning, owner, and storage tier annotated — work-order.schema.json and work-result.schema.json $ref into $defs below instead of re-defining records inline, and no skill may introduce a cross-boundary field that is not registered here first. Annotation keys: x-tier = SHARED (committed under shapeup/, survives clone+crash) | LOCAL (gitignored under .shapeup/, regenerable run-trace) | EMBEDDED (a record type that only lives inside another entity); x-location = the canonical path; x-writer = the single component allowed to write it; x-readers = who consumes it. The x-erd block is the machine-readable entity-relationship map; x-payload-by-worker is the authoritative table of which WorkOrder payload fields each worker may rely on.",
|
|
5
5
|
"x-erd": {
|
|
6
6
|
"description": "Relationship map. Cardinality reads left-to-right (WorkOrder 1:1 WorkResult = every order has exactly one result). Join keys: <slug> (the feature) is the aggregate root every path is keyed off; scope_id is the STABLE cross-machine key (boards regenerate; hill shards, T0 history and branches join on it); TASK-NNN ids are machine-local and must never be joined across machines (board regeneration joins on scope, not task id).",
|
|
7
|
+
"external": {
|
|
8
|
+
"WorkOrder": "work-order.schema.json",
|
|
9
|
+
"WorkResult": "work-result.schema.json"
|
|
10
|
+
},
|
|
11
|
+
"projection": {
|
|
12
|
+
"description": "How `kernel/reduce/graph.mjs`'s node vocabulary maps onto this catalog. The projection uses short names on purpose — a graph is read by hand — so the mapping is declared rather than inferred. A `type` of null is a KNOWN GAP: the projection emits that node and this schema has never typed it. The structural suite asserts this map is TOTAL against the node types the projection actually emits, so a new node type cannot appear without either a type or an explicit gap.",
|
|
13
|
+
"nodes": {
|
|
14
|
+
"Run": {
|
|
15
|
+
"type": null,
|
|
16
|
+
"gap": "the run receipt's own record — emitted by reduce graph, never typed here"
|
|
17
|
+
},
|
|
18
|
+
"Order": {
|
|
19
|
+
"type": "WorkOrder",
|
|
20
|
+
"external": true
|
|
21
|
+
},
|
|
22
|
+
"Result": {
|
|
23
|
+
"type": "WorkResult",
|
|
24
|
+
"external": true
|
|
25
|
+
},
|
|
26
|
+
"Verdict": {
|
|
27
|
+
"type": "Verdict"
|
|
28
|
+
},
|
|
29
|
+
"Trial": {
|
|
30
|
+
"type": "TrialRow"
|
|
31
|
+
},
|
|
32
|
+
"GateDecision": {
|
|
33
|
+
"type": null,
|
|
34
|
+
"gap": "a gate decision row — emitted by reduce graph, never typed here"
|
|
35
|
+
},
|
|
36
|
+
"Scope": {
|
|
37
|
+
"type": "ScopeContract"
|
|
38
|
+
},
|
|
39
|
+
"UseCase": {
|
|
40
|
+
"type": "UseCase"
|
|
41
|
+
},
|
|
42
|
+
"Requirement": {
|
|
43
|
+
"type": "RequirementClause"
|
|
44
|
+
},
|
|
45
|
+
"Seam": {
|
|
46
|
+
"type": "Seam"
|
|
47
|
+
}
|
|
48
|
+
}
|
|
49
|
+
},
|
|
7
50
|
"relationships": [
|
|
8
51
|
{
|
|
9
52
|
"from": "WorkOrder",
|
|
10
53
|
"to": "WorkResult",
|
|
11
54
|
"cardinality": "1:1",
|
|
12
55
|
"via": "order_id",
|
|
13
|
-
"note": "the envelope port — compile
|
|
56
|
+
"note": "the envelope port — harness compile emits, worker answers, harness reduce ingest applies"
|
|
14
57
|
},
|
|
15
58
|
{
|
|
16
59
|
"from": "WorkOrder",
|
|
@@ -28,28 +71,35 @@
|
|
|
28
71
|
},
|
|
29
72
|
{
|
|
30
73
|
"from": "TaskRef",
|
|
31
|
-
"to": "UseCase
|
|
74
|
+
"to": "UseCase",
|
|
32
75
|
"cardinality": "N:1..N",
|
|
33
76
|
"via": "use_case_refs[]",
|
|
34
77
|
"note": "the LOCAL→SHARED traceability anchor (single-anchor rule on reconcile) — spec-evaluator's traceability source. Tier direction: persisted links flow LOCAL→SHARED only; a committed spec doc never references a machine-local task id back (spec-lint TIER-DIRECTION/UC-ANCHOR)"
|
|
35
78
|
},
|
|
36
79
|
{
|
|
37
|
-
"from": "AcResult
|
|
38
|
-
"to": "RequirementClause
|
|
80
|
+
"from": "AcResult",
|
|
81
|
+
"to": "RequirementClause",
|
|
39
82
|
"cardinality": "N:0..N",
|
|
40
83
|
"via": "acceptance_criteria[].covers[]",
|
|
41
84
|
"note": "the covers-closure anchor — same sanctioned LOCAL→SHARED direction as use_case_refs. trace-lint asserts every status:covered REQ-id is named by ≥1 AC's covers[]; a REQ neither covered nor CUT is red. REQ-ids are stable cross-machine keys (supersede-never-delete), never renumbered like TASK-NNN"
|
|
42
85
|
},
|
|
43
86
|
{
|
|
44
|
-
"from": "CriterionVerdict
|
|
45
|
-
"to": "RequirementClause
|
|
87
|
+
"from": "CriterionVerdict",
|
|
88
|
+
"to": "RequirementClause",
|
|
89
|
+
"cardinality": "N:0..N",
|
|
90
|
+
"via": "traces_to[]",
|
|
91
|
+
"note": "optional finding→REQ back-link (LOCAL→SHARED) so an edge case maps to a business requirement by id, not by grepping the ledger; the lint only checks the id resolves in the registry — purely a navigation anchor split from a compound ERD node; CriterionVerdict carries its own traces_to[]"
|
|
92
|
+
},
|
|
93
|
+
{
|
|
94
|
+
"from": "Discovery",
|
|
95
|
+
"to": "RequirementClause",
|
|
46
96
|
"cardinality": "N:0..N",
|
|
47
97
|
"via": "traces_to[]",
|
|
48
|
-
"note": "optional finding→REQ back-link (LOCAL→SHARED) so an edge case maps to a business requirement by id, not by grepping the ledger; the lint only checks the id resolves in the registry — purely a navigation anchor"
|
|
98
|
+
"note": "optional finding→REQ back-link (LOCAL→SHARED) so an edge case maps to a business requirement by id, not by grepping the ledger; the lint only checks the id resolves in the registry — purely a navigation anchor split from a compound ERD node; Discovery carries its own traces_to[]"
|
|
49
99
|
},
|
|
50
100
|
{
|
|
51
101
|
"from": "WiringMap",
|
|
52
|
-
"to": "UseCase
|
|
102
|
+
"to": "UseCase",
|
|
53
103
|
"cardinality": "1:N",
|
|
54
104
|
"via": "entries[].use_case",
|
|
55
105
|
"note": "reachability map: per UC engine → wiring seam → entry-point call site → player-visible affordance. trace-lint asserts each UC's engine reaches ProjectProfile.entry_point via the import graph; an unreachable engine (0 import sites) is red"
|
|
@@ -89,7 +139,7 @@
|
|
|
89
139
|
},
|
|
90
140
|
{
|
|
91
141
|
"from": "TaskResult",
|
|
92
|
-
"to": "
|
|
142
|
+
"to": "TaskRef",
|
|
93
143
|
"cardinality": "N:1",
|
|
94
144
|
"via": "task_id",
|
|
95
145
|
"note": "ingest ticks AC boxes, flips frontmatter status, appends the Execution Log"
|
|
@@ -136,11 +186,33 @@
|
|
|
136
186
|
"via": "path + sha256",
|
|
137
187
|
"note": "content-addressed evidence the generator cannot fabricate"
|
|
138
188
|
},
|
|
189
|
+
{
|
|
190
|
+
"from": "ScopeContract",
|
|
191
|
+
"to": "UseCase",
|
|
192
|
+
"cardinality": "1:N",
|
|
193
|
+
"via": "use_cases[]",
|
|
194
|
+
"note": "the scope's anchor into the committed spec — the SCOPE-ANCHOR mirror of a task's use_case_refs"
|
|
195
|
+
},
|
|
139
196
|
{
|
|
140
197
|
"from": "ScopeContract",
|
|
141
198
|
"to": "TaskRef",
|
|
142
199
|
"cardinality": "1:N",
|
|
143
|
-
"via": "tasks
|
|
200
|
+
"via": "DERIVED — the board tasks whose use_case_refs meet this scope's use_cases (lib/contract.mjs tasksForScope)",
|
|
201
|
+
"note": "never stored: task ids are machine-local and the contract is committed, so the relation is re-derived per machine from two artifacts that are each valid alone. scope_id is the stable key on this side"
|
|
202
|
+
},
|
|
203
|
+
{
|
|
204
|
+
"from": "ScopeContract",
|
|
205
|
+
"to": "RequirementClause",
|
|
206
|
+
"cardinality": "1:N",
|
|
207
|
+
"via": "covers[]",
|
|
208
|
+
"note": "REQ-ids, the same stable key an AC's covers: clause uses"
|
|
209
|
+
},
|
|
210
|
+
{
|
|
211
|
+
"from": "ScopeContract",
|
|
212
|
+
"to": "ScopeContract",
|
|
213
|
+
"cardinality": "N:N",
|
|
214
|
+
"via": "depends_on[]",
|
|
215
|
+
"note": "build order, in the same tier as the contracts it orders — what scope_waves/scope_deps level"
|
|
144
216
|
},
|
|
145
217
|
{
|
|
146
218
|
"from": "ScopeContract",
|
|
@@ -217,6 +289,13 @@
|
|
|
217
289
|
"cardinality": "1:N",
|
|
218
290
|
"via": "scopes[].scope_id",
|
|
219
291
|
"note": "every FINISHED scope's fixtures re-run on each later attempt"
|
|
292
|
+
},
|
|
293
|
+
{
|
|
294
|
+
"from": "UseCase",
|
|
295
|
+
"to": "Seam",
|
|
296
|
+
"cardinality": "1:N",
|
|
297
|
+
"via": "wiring-map entries[].wiring_seam",
|
|
298
|
+
"note": "projected by reduce graph as UseCase -DEPENDS_ON-> Seam. NOTE: the projection reads `row.seam`/`row.entry_point` while WiringEntry declares `wiring_seam`/`entry_call_site` — see harness-defects"
|
|
220
299
|
}
|
|
221
300
|
]
|
|
222
301
|
},
|
|
@@ -398,7 +477,7 @@
|
|
|
398
477
|
"Substrate": {
|
|
399
478
|
"description": "The write contract of one order — mode/flag differences ARE write-contract differences (one whitelist template per operation, compile-order substrateFor()). Enforced mechanically by the sandbox hook; a worker needing a file outside it must ESCALATE (substrate-expansion), never write.",
|
|
400
479
|
"x-tier": "EMBEDDED",
|
|
401
|
-
"x-writer": "compile
|
|
480
|
+
"x-writer": "harness compile (templates) / scope-architect (per-scope globs)",
|
|
402
481
|
"type": "object",
|
|
403
482
|
"properties": {
|
|
404
483
|
"allowed": {
|
|
@@ -449,7 +528,7 @@
|
|
|
449
528
|
"TaskRef": {
|
|
450
529
|
"description": "One task as carried inside a WorkOrder — parsed from the LOCAL board file (.shapeup/<slug>/tasks/TASK-*.md frontmatter + AC checkboxes) by compile-order parseTaskFile(). NOTE: task ids are machine-local (boards regenerate and renumber); never join on id across machines — the scope is the stable key.",
|
|
451
530
|
"x-tier": "EMBEDDED",
|
|
452
|
-
"x-writer": "compile
|
|
531
|
+
"x-writer": "harness compile (from the board ba-pitch-analyzer generated)",
|
|
453
532
|
"type": "object",
|
|
454
533
|
"required": [
|
|
455
534
|
"id"
|
|
@@ -510,7 +589,7 @@
|
|
|
510
589
|
"items": {
|
|
511
590
|
"type": "string"
|
|
512
591
|
},
|
|
513
|
-
"description": "Explicit dependencies. The inverse (unlocks) is ALWAYS derived by board
|
|
592
|
+
"description": "Explicit dependencies. The inverse (unlocks) is ALWAYS derived by harness reduce board, never hand-authored — hand-authored inverses drift asymmetric, observed repeatedly."
|
|
514
593
|
},
|
|
515
594
|
"use_case_refs": {
|
|
516
595
|
"type": "array",
|
|
@@ -518,6 +597,10 @@
|
|
|
518
597
|
"type": "string"
|
|
519
598
|
},
|
|
520
599
|
"description": "UC ids this task implements (e.g. UC-CreateOrder) — the task's LOCAL→SHARED anchor into the committed spec and spec-evaluator's traceability source. Links flow one direction: the LOCAL task cites the SHARED UC; a committed doc never links a task id back (ids are machine-local)."
|
|
600
|
+
},
|
|
601
|
+
"scope_id": {
|
|
602
|
+
"type": "string",
|
|
603
|
+
"description": "OPTIONAL: the scope that builds this task. The DISAMBIGUATOR, not the primary link — dispatch normally derives a scope's tasks by intersecting the contract's use_cases[] with this task's use_case_refs[], and that is a partition only while each scope owns its own use cases. When several scopes implement one use case (a four-scope, one-UC cut is ordinary) the UC anchor cannot say who builds what and every scope claims every task; spec-lint SCOPE-PARTITION reds that, and this field resolves it. Same sanctioned LOCAL→SHARED direction as use_case_refs: the volatile board names the stable scope_id, never the reverse."
|
|
521
604
|
}
|
|
522
605
|
}
|
|
523
606
|
},
|
|
@@ -543,17 +626,24 @@
|
|
|
543
626
|
}
|
|
544
627
|
},
|
|
545
628
|
"AegisTriple": {
|
|
546
|
-
"description": "One digested failure —
|
|
629
|
+
"description": "One digested failure — harness probe digest distills raw build/test/Playwright logs into these so the next attempt gets a few lines of signal instead of a stack-trace dump. Appears as T0Artifact.discovered_tasks[] (red attempts) and as WorkOrder payload.digested_errors[] (the next attempt's starting bug list).",
|
|
547
630
|
"x-tier": "EMBEDDED",
|
|
548
|
-
"x-writer": "
|
|
631
|
+
"x-writer": "harness probe digest (regex pass; Sonnet fallback only on unrecognized formats)",
|
|
549
632
|
"type": "object",
|
|
550
633
|
"properties": {
|
|
551
634
|
"file": {
|
|
552
|
-
"type":
|
|
635
|
+
"type": [
|
|
636
|
+
"string",
|
|
637
|
+
"null"
|
|
638
|
+
],
|
|
553
639
|
"description": "Source file of the failure; null/absent when the log line carried no location (raw triple — never invented)."
|
|
554
640
|
},
|
|
555
641
|
"line": {
|
|
556
|
-
"type":
|
|
642
|
+
"type": [
|
|
643
|
+
"integer",
|
|
644
|
+
"null"
|
|
645
|
+
],
|
|
646
|
+
"description": "Line of the failure; null/absent when the log line carried no location. Paired with `file` — a triple has both or neither, and neither is ever invented to satisfy a shape."
|
|
557
647
|
},
|
|
558
648
|
"core_message": {
|
|
559
649
|
"type": "string",
|
|
@@ -622,12 +712,40 @@
|
|
|
622
712
|
}
|
|
623
713
|
}
|
|
624
714
|
},
|
|
715
|
+
"UseCase": {
|
|
716
|
+
"description": "One use case — the STABLE anchor both tiers name, and the only identifier the scope↔task relation is re-derived through. A UC id is assigned once and frozen: it behaves like scope_id and REQ-id, never like TASK-NNN. Referenced three ways across the tree (`UC-x`, `[[UC-x]]`, `[[usecases/UC-x]]`); `kernel/lib/contract.mjs` ucId() is the single normaliser, and both sides of any join must pass through it or they disagree about a UC they both hold.",
|
|
717
|
+
"x-tier": "SHARED",
|
|
718
|
+
"x-location": "shapeup/<slug>/spec/usecases/UC-*.md",
|
|
719
|
+
"x-writer": "ba-pitch-analyzer (operation: analyze; reconcile MAY append, never renumber)",
|
|
720
|
+
"x-readers": "scope-architect (use_cases[]), solution-architect (wiring-map entries), spec-evaluator (the grading criterion), harness verify spec (SCOPE-ANCHOR + UC-ANCHOR), harness reduce graph",
|
|
721
|
+
"type": "object",
|
|
722
|
+
"required": [
|
|
723
|
+
"id"
|
|
724
|
+
],
|
|
725
|
+
"properties": {
|
|
726
|
+
"id": {
|
|
727
|
+
"type": "string",
|
|
728
|
+
"description": "`UC-*`, matching the filename stem. Frozen once assigned — every use_cases[] and use_case_refs[] link rots if it is renumbered."
|
|
729
|
+
},
|
|
730
|
+
"title": {
|
|
731
|
+
"type": "string",
|
|
732
|
+
"description": "What the user can do."
|
|
733
|
+
},
|
|
734
|
+
"invariants": {
|
|
735
|
+
"type": "array",
|
|
736
|
+
"items": {
|
|
737
|
+
"type": "string"
|
|
738
|
+
},
|
|
739
|
+
"description": "`[INV-NN]` markers declared in the body; the source of regression tasks and Test Surface rows."
|
|
740
|
+
}
|
|
741
|
+
}
|
|
742
|
+
},
|
|
625
743
|
"ScopeContract": {
|
|
626
|
-
"description": "A vertical scope as a committed, mechanically enforceable contract — Shape Up's 'map the scopes' as data. Sliced by business flow (one call chain: UI screen + API route + use case + repository), NEVER by directory (PA1). The sandbox hook enforces the substrate, t0-verify runs the fixtures, the evaluator asserts against the manifest. Superseded contracts are kept, never deleted (branch and T0 history stay attributable). ON-DISK FORMAT IS MARKDOWN (ADR-0001): frontmatter carries the scalars and [a, b] lists, a markdown table carries the one array-of-objects field, and prose carries the rationale a reviewer reads. THIS SCHEMA DESCRIBES THE PARSED OBJECT — the wire form embedded in the WorkOrder envelope — not the file. `
|
|
744
|
+
"description": "A vertical scope as a committed, mechanically enforceable contract — Shape Up's 'map the scopes' as data. Sliced by business flow (one call chain: UI screen + API route + use case + repository), NEVER by directory (PA1). The sandbox hook enforces the substrate, t0-verify runs the fixtures, the evaluator asserts against the manifest. Superseded contracts are kept, never deleted (branch and T0 history stay attributable). ON-DISK FORMAT IS MARKDOWN (ADR-0001): frontmatter carries the scalars and [a, b] lists, a markdown table carries the one array-of-objects field, and prose carries the rationale a reviewer reads. THIS SCHEMA DESCRIBES THE PARSED OBJECT — the wire form embedded in the WorkOrder envelope — not the file. `kernel/lib/contract.mjs` is the only reader/writer of the file form; everything downstream of that parse sees exactly this shape.",
|
|
627
745
|
"x-tier": "SHARED",
|
|
628
746
|
"x-location": "shapeup/<slug>/scopes/<scope-id>.md",
|
|
629
747
|
"x-writer": "scope-architect (SOLE writer — a hand-edit anywhere else is a defect)",
|
|
630
|
-
"x-readers": "compile
|
|
748
|
+
"x-readers": "harness compile, sandbox-guard hook, harness verify t0, harness verify spec, spec-evaluator, scope-hammer, tech-lead",
|
|
631
749
|
"type": "object",
|
|
632
750
|
"required": [
|
|
633
751
|
"scope_id"
|
|
@@ -646,12 +764,26 @@
|
|
|
646
764
|
],
|
|
647
765
|
"description": "LAYER_CAKE = thin balanced UI+backend · ICEBERG = complexity on one side · CHOWDER = true strays with no shared flow (the one deliberate exception to cross-layer slicing)."
|
|
648
766
|
},
|
|
649
|
-
"
|
|
767
|
+
"use_cases": {
|
|
650
768
|
"type": "array",
|
|
651
769
|
"items": {
|
|
652
770
|
"type": "string"
|
|
653
771
|
},
|
|
654
|
-
"description": "
|
|
772
|
+
"description": "The COMMITTED use cases this scope implements (`UC-*`, resolving to spec/usecases/UC-*.md) — the scope's anchor into the spec and the join the scope↔task relation is re-derived through. Mirrors the board's own `use_case_refs` in the sanctioned LOCAL→SHARED direction. This REPLACES the former `tasks[]` id list: a contract is committed and a board is not, so naming task ids put a pointer into a gitignored, per-machine tier that resolved to nothing on every other clone without a single check going red. spec-lint SCOPE-ANCHOR reds an empty or unresolvable anchor."
|
|
773
|
+
},
|
|
774
|
+
"covers": {
|
|
775
|
+
"type": "array",
|
|
776
|
+
"items": {
|
|
777
|
+
"type": "string"
|
|
778
|
+
},
|
|
779
|
+
"description": "Optional REQ-ids from requirements.md this scope answers for — the same stable, never-renumbered key an AC's `covers:` clause uses. Projected as the Scope→Requirement COVERS edge in the run graph."
|
|
780
|
+
},
|
|
781
|
+
"depends_on": {
|
|
782
|
+
"type": "array",
|
|
783
|
+
"items": {
|
|
784
|
+
"type": "string"
|
|
785
|
+
},
|
|
786
|
+
"description": "scope_ids this scope must build AFTER. Build order lives in the same tier as the contracts it orders: this was previously derived from the LOCAL board (contract tasks → task depends_on → owning scope), which collapsed to no edges whenever the board was absent and silently degraded the scheduler to an unscheduled fan-out. An id naming a scope not in the run is dropped by the scheduler (fail-open) and reported by spec-lint SCOPE-DEPS."
|
|
655
787
|
},
|
|
656
788
|
"allowed_file_substrate": {
|
|
657
789
|
"type": "array",
|
|
@@ -679,7 +811,7 @@
|
|
|
679
811
|
"items": {
|
|
680
812
|
"type": "string"
|
|
681
813
|
},
|
|
682
|
-
"description": "Command(s) that drive this scope end-to-end (the T0 layer). Too speculative to fixture → an explicit TBD flag, never an invented fixture."
|
|
814
|
+
"description": "Command(s) that drive this scope end-to-end (the T0 layer). EACH MUST EXIT 0 WHEN THE SCOPE IS CORRECT — `harness verify t0` scores a fixture as failed on any non-zero exit, so a fixture written as a bare error-path invocation (`todo done abc # exit 1`) can never pass and the scope can never go T0-green however correct the code is. Assert error paths INSIDE a test file that itself exits 0 (`node --test test/commands/done.test.js`), which is what the expected non-zero exit belongs in. Too speculative to fixture → an explicit TBD flag, never an invented fixture."
|
|
683
815
|
},
|
|
684
816
|
"db_probe": {
|
|
685
817
|
"type": "string",
|
|
@@ -708,6 +840,23 @@
|
|
|
708
840
|
}
|
|
709
841
|
}
|
|
710
842
|
},
|
|
843
|
+
"ScopeBoard": {
|
|
844
|
+
"description": "The scope board — a HUMAN-READABLE PROJECTION of the contracts, not a source. Every column restates something `scopes/*.md` already declares, so it can be regenerated from them and deleting it loses nothing. It deliberately carries no `wave` column: waves are Kahn levels of `depends_on` and `probe resume` derives them, and a hand-authored copy of a derived value is the same defect as the hand-authored `unlocks` that `deriveUnlocks` exists to prevent. Nothing parses this file — that is only safe while it stays a view; the moment it holds a fact of its own it needs a reader and a lint like every other contract.",
|
|
845
|
+
"x-tier": "SHARED",
|
|
846
|
+
"x-location": "shapeup/<slug>/scope-board.md",
|
|
847
|
+
"x-writer": "scope-architect (regenerated whenever the contracts change)",
|
|
848
|
+
"x-readers": "humans, in a pull request. No code reads it — by design.",
|
|
849
|
+
"type": "object",
|
|
850
|
+
"properties": {
|
|
851
|
+
"rows": {
|
|
852
|
+
"type": "array",
|
|
853
|
+
"description": "One row per scope: scope_id · topology_type · use_cases · depends_on · substrate size · lint status. All projected from the contract.",
|
|
854
|
+
"items": {
|
|
855
|
+
"type": "object"
|
|
856
|
+
}
|
|
857
|
+
}
|
|
858
|
+
}
|
|
859
|
+
},
|
|
711
860
|
"AcResult": {
|
|
712
861
|
"description": "One acceptance criterion's outcome with evidence. 'ac' carries the checkbox text VERBATIM — ingest ticks boxes by substring-matching it. No recorded evidence = the worker reports fail by its own hand.",
|
|
713
862
|
"x-tier": "EMBEDDED",
|
|
@@ -796,7 +945,7 @@
|
|
|
796
945
|
"description": "The universal currency of surprise: one raw discovered line. Producers: task-executor (marker +, P3.7), qa-edge-hunter (always ~, repro required), ba-pitch-analyzer (overflow reports). NO producer writes the ledger — ingest-result appends every entry to discovery/ledger.md (single-writer, mechanically). Promotion ~ → must-have is always a human act at SHIP S.0/GATE H.",
|
|
797
946
|
"x-tier": "EMBEDDED (projection into the LOCAL discovery ledger)",
|
|
798
947
|
"x-location": ".shapeup/<slug>/discovery/ledger.md",
|
|
799
|
-
"x-writer": "ingest
|
|
948
|
+
"x-writer": "harness reduce ingest",
|
|
800
949
|
"x-readers": "ba-pitch-analyzer (reconcile), scope-architect (map-scopes), scope-hammer (census), qa-edge-hunter (covered-territory context)",
|
|
801
950
|
"type": "object",
|
|
802
951
|
"required": [
|
|
@@ -1073,11 +1222,11 @@
|
|
|
1073
1222
|
}
|
|
1074
1223
|
},
|
|
1075
1224
|
"T0Artifact": {
|
|
1076
|
-
"description": "The mechanical verification verdict for one build attempt — the evidence layer under the LLM judge. Written by
|
|
1225
|
+
"description": "The mechanical verification verdict for one build attempt — the evidence layer under the LLM judge. Written by harness verify t0 from actually running the scope's fixtures + DB probe + seesaw; zero LLM tokens. spec-evaluator must cite it (sha256) on scoped specs. Red artifacts carry AEGIS triples that become the next attempt's digested_errors.",
|
|
1077
1226
|
"x-tier": "LOCAL",
|
|
1078
1227
|
"x-location": ".shapeup/<slug>/t0/verdicts/r<N>-a<M>-t<T>.json (schema_version 2; the unsuffixed r<N>-a<M>.json of schema_version 1 is still readable)",
|
|
1079
|
-
"x-writer": "t0
|
|
1080
|
-
"x-readers": "compile
|
|
1228
|
+
"x-writer": "harness verify t0",
|
|
1229
|
+
"x-readers": "harness compile (next attempt), spec-evaluator (citation), tech-lead (hill derivation, GATE L2.3), scope-hammer (stall census)",
|
|
1081
1230
|
"type": "object",
|
|
1082
1231
|
"properties": {
|
|
1083
1232
|
"schema_version": {
|
|
@@ -1097,6 +1246,11 @@
|
|
|
1097
1246
|
"type": "integer",
|
|
1098
1247
|
"description": "schema_version 2+: the retry ordinal within (round, attempt). Written with flag 'wx', so a retry of the SAME attempt lands beside its predecessor instead of destroying it (invariant I4)."
|
|
1099
1248
|
},
|
|
1249
|
+
"run_id": {
|
|
1250
|
+
"type": "string",
|
|
1251
|
+
"description": "OPTIONAL (v1.8) — the run key (mintRunId in lib/paths.mjs). (round, attempt, trial) addresses an artifact within a run and repeats in the next one, so the evidence layer needed this to be groupable by run.",
|
|
1252
|
+
"pattern": "^[a-z0-9][a-z0-9-]*-[0-9]{8}T[0-9]{6}Z-[0-9a-f]{8}$"
|
|
1253
|
+
},
|
|
1100
1254
|
"at": {
|
|
1101
1255
|
"type": "string",
|
|
1102
1256
|
"description": "ISO timestamp."
|
|
@@ -1192,8 +1346,8 @@
|
|
|
1192
1346
|
"description": "One row per T0 run — the ratchet's history, and the artifact that makes 'is attempt N+1 better than attempt N?' answerable. Append-only (I4: every superseded object remains addressable). baseline_trial is the parent link: that single field IS the experiment DAG (lineage, PARENT_OF, and a genuine SUPERSEDES edge) delivered without a graph store. Written by t0-verify, NOT ingest-result: a trial row is a mechanical fact produced by running commands, in the same class as the verdict artifact t0-verify already owns, and carries no worker claim to apply.",
|
|
1193
1347
|
"x-tier": "LOCAL",
|
|
1194
1348
|
"x-location": ".shapeup/<slug>/t0/trials.jsonl",
|
|
1195
|
-
"x-writer": "
|
|
1196
|
-
"x-readers": "compile
|
|
1349
|
+
"x-writer": "harness verify t0 (append-only)",
|
|
1350
|
+
"x-readers": "harness compile (payload.trial_history — the paper's inspect()), harness probe stats --ratchet (improvement_rate, monotone_rate, sawtooth_count)",
|
|
1197
1351
|
"type": "object",
|
|
1198
1352
|
"properties": {
|
|
1199
1353
|
"schema_version": {
|
|
@@ -1207,6 +1361,11 @@
|
|
|
1207
1361
|
"minimum": 1,
|
|
1208
1362
|
"description": "Monotone ordinal across the run's whole ledger — what baseline_trial points at."
|
|
1209
1363
|
},
|
|
1364
|
+
"run_id": {
|
|
1365
|
+
"type": "string",
|
|
1366
|
+
"description": "OPTIONAL (v1.8) — the run key (mintRunId in lib/paths.mjs), read off the receipt in the run root t0-verify was pointed at. `trial` is monotone WITHIN a run and restarts at 1 in the next one, so ratchet history could not be split by run without it.",
|
|
1367
|
+
"pattern": "^[a-z0-9][a-z0-9-]*-[0-9]{8}T[0-9]{6}Z-[0-9a-f]{8}$"
|
|
1368
|
+
},
|
|
1210
1369
|
"round": {
|
|
1211
1370
|
"type": "integer"
|
|
1212
1371
|
},
|
|
@@ -1280,7 +1439,7 @@
|
|
|
1280
1439
|
"x-tier": "LOCAL",
|
|
1281
1440
|
"x-location": ".shapeup/<slug>/seesaw/registry.json",
|
|
1282
1441
|
"x-writer": "tech-lead (when a scope reaches FINISHED)",
|
|
1283
|
-
"x-readers": "t0
|
|
1442
|
+
"x-readers": "harness verify t0",
|
|
1284
1443
|
"type": "object",
|
|
1285
1444
|
"properties": {
|
|
1286
1445
|
"scopes": {
|
|
@@ -1306,8 +1465,8 @@
|
|
|
1306
1465
|
"description": "One appended line of judge history (JSONL). Never rewritten — flips across runs are detected here and force confidence low. run auto-increments per append batch.",
|
|
1307
1466
|
"x-tier": "LOCAL",
|
|
1308
1467
|
"x-location": ".shapeup/<slug>/evaluation/.verdicts-<target>.jsonl",
|
|
1309
|
-
"x-writer": "ingest
|
|
1310
|
-
"x-readers": "spec-evaluator (read-only flip detection), verdict
|
|
1468
|
+
"x-writer": "harness reduce ingest (from Verdict.criteria[])",
|
|
1469
|
+
"x-readers": "spec-evaluator (read-only flip detection), harness reduce verdict",
|
|
1311
1470
|
"type": "object",
|
|
1312
1471
|
"properties": {
|
|
1313
1472
|
"run": {
|
|
@@ -1369,10 +1528,10 @@
|
|
|
1369
1528
|
},
|
|
1370
1529
|
"MetricsRow": {
|
|
1371
1530
|
"description": "One SHIP-time harvest row (facts only — copied from structured output that already exists; never a newly computed verdict/score, which would be a second judge behind spec-evaluator). Sharded per machine so concurrent runs never merge-conflict.",
|
|
1372
|
-
"x-tier": "
|
|
1531
|
+
"x-tier": "LOCAL",
|
|
1373
1532
|
"x-location": ".shapeup/metrics/<machine-id>.jsonl",
|
|
1374
1533
|
"x-writer": "tech-lead (SHIP S.6)",
|
|
1375
|
-
"x-readers": "
|
|
1534
|
+
"x-readers": "harness probe stats (read-only projection), harness report export (the run dimension)",
|
|
1376
1535
|
"type": "object",
|
|
1377
1536
|
"properties": {
|
|
1378
1537
|
"schema_version": {
|
|
@@ -1383,7 +1542,12 @@
|
|
|
1383
1542
|
},
|
|
1384
1543
|
"at": {
|
|
1385
1544
|
"type": "string",
|
|
1386
|
-
"description": "OPTIONAL (v1.2) — ISO harvest timestamp; enables real trend-over-time in stats.
|
|
1545
|
+
"description": "OPTIONAL (v1.2) — ISO harvest timestamp; enables real trend-over-time in harness probe stats. Older rows lack it and fall back to shard append order."
|
|
1546
|
+
},
|
|
1547
|
+
"run_id": {
|
|
1548
|
+
"type": "string",
|
|
1549
|
+
"description": "OPTIONAL (v1.8) — the run key (mintRunId in lib/paths.mjs), COPIED from the receipt at SHIP S.6. This is the harvest row's only link to the run trace that produced it: everything else here is a count, and `feature_slug` groups runs together rather than apart.",
|
|
1550
|
+
"pattern": "^[a-z0-9][a-z0-9-]*-[0-9]{8}T[0-9]{6}Z-[0-9a-f]{8}$"
|
|
1387
1551
|
},
|
|
1388
1552
|
"feature_slug": {
|
|
1389
1553
|
"type": "string"
|
|
@@ -1411,7 +1575,7 @@
|
|
|
1411
1575
|
},
|
|
1412
1576
|
"attempt_exhaustions": {
|
|
1413
1577
|
"type": "integer",
|
|
1414
|
-
"description": "OPTIONAL (v1.2) — scopes whose inner attempt_budget tripped this run, COPIED at SHIP S.6 from the queued GATE H hammer proposals (a fact registered at the source; stats
|
|
1578
|
+
"description": "OPTIONAL (v1.2) — scopes whose inner attempt_budget tripped this run, COPIED at SHIP S.6 from the queued GATE H hammer proposals (a fact registered at the source; harness probe stats must never re-derive it)."
|
|
1415
1579
|
},
|
|
1416
1580
|
"qa_findings": {
|
|
1417
1581
|
"type": "object",
|
|
@@ -1433,7 +1597,7 @@
|
|
|
1433
1597
|
},
|
|
1434
1598
|
"ratchet": {
|
|
1435
1599
|
"type": "object",
|
|
1436
|
-
"description": "OPTIONAL (v1.5) — the DAY-1 exit measurement, COPIED from `stats
|
|
1600
|
+
"description": "OPTIONAL (v1.5) — the DAY-1 exit measurement, COPIED from `harness probe stats --ratchet` over this run's t0/trials.jsonl before the LOCAL trace is wiped. This is the only place the ratchet numbers survive the run, and the only reason they can be compared across machines: `.shapeup/` is gitignored, so a measurement left there answers the question exactly once and then deletes itself. Facts only — every field is a count or a ratio over recorded trial rows, never a grade.",
|
|
1437
1601
|
"properties": {
|
|
1438
1602
|
"trials": {
|
|
1439
1603
|
"type": "integer"
|
|
@@ -1464,7 +1628,7 @@
|
|
|
1464
1628
|
},
|
|
1465
1629
|
"hooks": {
|
|
1466
1630
|
"type": "object",
|
|
1467
|
-
"description": "OPTIONAL (v1.5) — the DAY-2 exit measurement, COPIED from `stats
|
|
1631
|
+
"description": "OPTIONAL (v1.5) — the DAY-2 exit measurement, COPIED from `harness probe stats --hooks` over .shapeup/decisions.jsonl. Makes 'never had to fire' and 'never ran' separable across runs: before the decision ledger both produced exit 0 and empty stdout, which is why several enforcement tools were unscoreable.",
|
|
1468
1632
|
"properties": {
|
|
1469
1633
|
"evaluations": {
|
|
1470
1634
|
"type": "integer"
|
|
@@ -1544,11 +1708,11 @@
|
|
|
1544
1708
|
}
|
|
1545
1709
|
},
|
|
1546
1710
|
"RunSnapshot": {
|
|
1547
|
-
"description": "Mechanical mid-run state digest, derived ONLY from files (active-scope pointer, harness-run.md frontmatter, board frontmatter, t0/verdicts filenames, orders/ vs results/) — never from conversation memory. The
|
|
1711
|
+
"description": "Mechanical mid-run state digest, derived ONLY from files (active-scope pointer, harness-run.md frontmatter, board frontmatter, t0/verdicts filenames, orders/ vs results/) — never from conversation memory. The continuity reflex: after any context loss the orchestrator re-derives this from disk rather than trusting a lossy summary — or, on a cold startup, rather than re-opening a run that is already open.",
|
|
1548
1712
|
"x-tier": "LOCAL",
|
|
1549
|
-
"x-location": ".shapeup/<slug>/run-snapshot.json (
|
|
1550
|
-
"x-writer": "
|
|
1551
|
-
"x-readers": "
|
|
1713
|
+
"x-location": ".shapeup/<slug>/run-snapshot.json (written by harness reduce snapshot --write; also emitted ephemerally on stdout by harness reduce snapshot)",
|
|
1714
|
+
"x-writer": "harness reduce snapshot --write (never a worker; this is LOCAL derived cache, harness reduce ingest remains the sole writer of SHARED state)",
|
|
1715
|
+
"x-readers": "tech-lead (--from resume aid), human",
|
|
1552
1716
|
"type": "object",
|
|
1553
1717
|
"required": [
|
|
1554
1718
|
"schema_version",
|
|
@@ -1653,14 +1817,14 @@
|
|
|
1653
1817
|
},
|
|
1654
1818
|
"rehydrate_hint": {
|
|
1655
1819
|
"type": "string",
|
|
1656
|
-
"description": "The composed one-paragraph instruction
|
|
1820
|
+
"description": "The composed one-paragraph instruction for resuming after a context loss: re-read run-state, trust the files, not the summary."
|
|
1657
1821
|
}
|
|
1658
1822
|
}
|
|
1659
1823
|
},
|
|
1660
1824
|
"StatsReport": {
|
|
1661
1825
|
"description": "The telemetry read-plane's output — an aggregate projection over the MetricsRow shards. Aggregates COPIED facts only (counts, rates, trends over already-recorded fields); it never grades, so it can never become a second judge. Malformed rows are skipped fail-open and counted; pathology rows (sandbox-guard/safety-spine denials share the shards) are partitioned, not errors.",
|
|
1662
1826
|
"x-tier": "EMBEDDED (ephemeral projection — printed to stdout, never persisted; the metrics JSONL stays the only source of truth)",
|
|
1663
|
-
"x-writer": "stats
|
|
1827
|
+
"x-writer": "harness probe stats (read-only over metrics/ — writes nothing)",
|
|
1664
1828
|
"x-readers": "human / CLI / CI",
|
|
1665
1829
|
"type": "object",
|
|
1666
1830
|
"required": [
|
|
@@ -1806,7 +1970,7 @@
|
|
|
1806
1970
|
}
|
|
1807
1971
|
},
|
|
1808
1972
|
"Lane": {
|
|
1809
|
-
"description": "The run's lane (full|tiny), computed by fit
|
|
1973
|
+
"description": "The run's lane (full|tiny), computed by harness init fit at GATE L0.3 and recorded in harness-run.md frontmatter `lane:` (with its evidence, and marked overridden when --lane/--tiny outranks the recommendation); RunArgs.lane carries it to the workflow launch. The lane is pipeline knowledge: the orchestrator compiles it away into existing registered knobs (lens, budgets, gate policy) — it NEVER rides in WorkOrderPayload, so workers stay pipeline-blind.",
|
|
1810
1974
|
"x-tier": "EMBEDDED (recorded in harness-run.md frontmatter `lane:` — never a WorkOrderPayload field)",
|
|
1811
1975
|
"x-writer": "tech-lead (GATE L0 lane selection)",
|
|
1812
1976
|
"x-readers": "tech-lead only",
|
|
@@ -1857,7 +2021,7 @@
|
|
|
1857
2021
|
"x-tier": "SHARED",
|
|
1858
2022
|
"x-location": "shapeup/<slug>/requirements.md",
|
|
1859
2023
|
"x-writer": "ba-pitch-analyzer (operation: coverage) — extraction only; CUT status is a PO governance edit (same class as a round-ledger Decision)",
|
|
1860
|
-
"x-readers": "trace
|
|
2024
|
+
"x-readers": "harness verify trace (covers-closure oracle), tech-lead, human (coverage/cut audit)",
|
|
1861
2025
|
"type": "object",
|
|
1862
2026
|
"required": [
|
|
1863
2027
|
"id",
|
|
@@ -1923,12 +2087,32 @@
|
|
|
1923
2087
|
}
|
|
1924
2088
|
}
|
|
1925
2089
|
},
|
|
2090
|
+
"Seam": {
|
|
2091
|
+
"description": "How one use case's engine attaches to the entry point — the `wiring_seam` value of a WiringEntry, promoted to a first-class node by `reduce graph` so a verdict can be traced back through the seam to the objective. Not a file: it exists only as a cell in the committed wiring map and as a node in the derived run graph.",
|
|
2092
|
+
"x-tier": "EMBEDDED (a WiringEntry.wiring_seam value; promoted to a node by reduce graph)",
|
|
2093
|
+
"x-writer": "solution-architect (operation: wire), inside wiring-map.md",
|
|
2094
|
+
"type": "object",
|
|
2095
|
+
"properties": {
|
|
2096
|
+
"seam": {
|
|
2097
|
+
"type": "string",
|
|
2098
|
+
"description": "The attachment mechanism — a route registration, an event handler, a direct call from the composition root."
|
|
2099
|
+
},
|
|
2100
|
+
"engine": {
|
|
2101
|
+
"type": "string",
|
|
2102
|
+
"description": "The repo-relative module the seam attaches."
|
|
2103
|
+
},
|
|
2104
|
+
"entry_point": {
|
|
2105
|
+
"type": "string",
|
|
2106
|
+
"description": "The call site the seam reaches from."
|
|
2107
|
+
}
|
|
2108
|
+
}
|
|
2109
|
+
},
|
|
1926
2110
|
"WiringMap": {
|
|
1927
|
-
"description": "The reachability map — per UC, the chain from engine to a player-visible affordance (spine v1.3). Written DIRECTLY by solution-architect at gate L1a.5 (precedent: ScopeContract is written directly by scope-architect, bypassing ingest-result). Its purpose: no engine ships orphaned from the running application. trace-lint folds reachability into its covers-closure pass — a UC whose engine does not reach ProjectProfile.entry_point via the import graph is red. A Mermaid view is auto-rendered from this map (a view of a checked graph, so it cannot drift). ON-DISK FORMAT IS MARKDOWN (ADR-0001): frontmatter carries the scalars and [a, b] lists, a markdown table carries the one array-of-objects field, and prose carries the rationale a reviewer reads. THIS SCHEMA DESCRIBES THE PARSED OBJECT — the wire form embedded in the WorkOrder envelope — not the file. `
|
|
2111
|
+
"description": "The reachability map — per UC, the chain from engine to a player-visible affordance (spine v1.3). Written DIRECTLY by solution-architect at gate L1a.5 (precedent: ScopeContract is written directly by scope-architect, bypassing ingest-result). Its purpose: no engine ships orphaned from the running application. trace-lint folds reachability into its covers-closure pass — a UC whose engine does not reach ProjectProfile.entry_point via the import graph is red. A Mermaid view is auto-rendered from this map (a view of a checked graph, so it cannot drift). ON-DISK FORMAT IS MARKDOWN (ADR-0001): frontmatter carries the scalars and [a, b] lists, a markdown table carries the one array-of-objects field, and prose carries the rationale a reviewer reads. THIS SCHEMA DESCRIBES THE PARSED OBJECT — the wire form embedded in the WorkOrder envelope — not the file. `kernel/lib/contract.mjs` is the only reader/writer of the file form; everything downstream of that parse sees exactly this shape.",
|
|
1928
2112
|
"x-tier": "SHARED",
|
|
1929
2113
|
"x-location": "shapeup/<slug>/wiring-map.md",
|
|
1930
2114
|
"x-writer": "solution-architect (SOLE writer, direct — like scope-architect writes scopes/*.md)",
|
|
1931
|
-
"x-readers": "trace
|
|
2115
|
+
"x-readers": "harness verify trace (reachability oracle), scope-architect (integration seam at slicing time), tech-lead",
|
|
1932
2116
|
"type": "object",
|
|
1933
2117
|
"required": [
|
|
1934
2118
|
"schema_version",
|
|
@@ -1959,11 +2143,11 @@
|
|
|
1959
2143
|
}
|
|
1960
2144
|
},
|
|
1961
2145
|
"ProjectProfile": {
|
|
1962
|
-
"description": "The archetype + entry-point declaration reachability depends on (spine v1.3). Exists for ONE load-bearing reason: reachability must know the entry point, and that is archetype-specific (main.js for a client-only game is not the seam for a web-service). SHARED — a declaration that must survive `rm -rf .shapeup/` + clone cannot live in the gitignored run-trace. Role-gating (skip SysRS/Auth/CI-CD) is explicitly OUT of scope — those roles are not workers; the profile is introduced only as the entry-point/archetype declaration. ON-DISK FORMAT IS MARKDOWN (ADR-0001): frontmatter carries the scalars and [a, b] lists, a markdown table carries the one array-of-objects field, and prose carries the rationale a reviewer reads. THIS SCHEMA DESCRIBES THE PARSED OBJECT — the wire form embedded in the WorkOrder envelope — not the file. `
|
|
2146
|
+
"description": "The archetype + entry-point declaration reachability depends on (spine v1.3). Exists for ONE load-bearing reason: reachability must know the entry point, and that is archetype-specific (main.js for a client-only game is not the seam for a web-service). SHARED — a declaration that must survive `rm -rf .shapeup/` + clone cannot live in the gitignored run-trace. Role-gating (skip SysRS/Auth/CI-CD) is explicitly OUT of scope — those roles are not workers; the profile is introduced only as the entry-point/archetype declaration. ON-DISK FORMAT IS MARKDOWN (ADR-0001): frontmatter carries the scalars and [a, b] lists, a markdown table carries the one array-of-objects field, and prose carries the rationale a reviewer reads. THIS SCHEMA DESCRIBES THE PARSED OBJECT — the wire form embedded in the WorkOrder envelope — not the file. `kernel/lib/contract.mjs` is the only reader/writer of the file form; everything downstream of that parse sees exactly this shape.",
|
|
1963
2147
|
"x-tier": "SHARED",
|
|
1964
2148
|
"x-location": "shapeup/<slug>/project-profile.md",
|
|
1965
|
-
"x-writer": "tech-lead (GATE L0 — not compile
|
|
1966
|
-
"x-readers": "trace
|
|
2149
|
+
"x-writer": "tech-lead (GATE L0 — not harness compile, which stays pipeline-blind)",
|
|
2150
|
+
"x-readers": "harness verify trace (reachability entry_point), solution-architect (wire), tech-lead",
|
|
1967
2151
|
"type": "object",
|
|
1968
2152
|
"required": [
|
|
1969
2153
|
"schema_version",
|
|
@@ -2050,7 +2234,7 @@
|
|
|
2050
2234
|
},
|
|
2051
2235
|
"bugs": {
|
|
2052
2236
|
"type": "array",
|
|
2053
|
-
"description": "
|
|
2237
|
+
"description": "The previous round's FAIL verdict, addressed to the scope whose substrate contains each cited file — touch nothing else. Written by `harness compile` from results/evaluate-r<N-1>.json, never by a caller: a build order is addressed by scope/round/attempt and carries no caller payload, and the verdict must survive the relaunch that separates two rounds. Present on any r≥2 execute order whose predecessor failed; an entry matching no scope's substrate is marked `unowned` and sent to all of them rather than dropped."
|
|
2054
2238
|
},
|
|
2055
2239
|
"spec_folder": {
|
|
2056
2240
|
"type": "string",
|
|
@@ -2129,8 +2313,11 @@
|
|
|
2129
2313
|
"description": "qa-edge-hunter: the PASS EVAL report — negative-space input; its covered territory is subtracted from charters."
|
|
2130
2314
|
},
|
|
2131
2315
|
"app_url": {
|
|
2132
|
-
"type":
|
|
2133
|
-
|
|
2316
|
+
"type": [
|
|
2317
|
+
"string",
|
|
2318
|
+
"null"
|
|
2319
|
+
],
|
|
2320
|
+
"description": "qa-edge-hunter: the running app to hunt (one real request at Q0, not a ping). NULL for a deliverable that is not served over HTTP — a CLI, a library, a batch job — where Q0 drives the binary instead. It was a bare string, so the first genuinely non-UI run could not compile a QA order at all: the payload carries null, the order fails its own schema, and the hunt is skipped for a reason that looks nothing like 'this deliverable has no URL'."
|
|
2134
2321
|
},
|
|
2135
2322
|
"ledger": {
|
|
2136
2323
|
"type": "string",
|
|
@@ -2170,10 +2357,10 @@
|
|
|
2170
2357
|
}
|
|
2171
2358
|
},
|
|
2172
2359
|
"ResumeState": {
|
|
2173
|
-
"description": "The fast-forward derivation: which phase a launch resumes at, derived from artifacts on disk and NEVER from stored state or conversation memory. Produced by
|
|
2360
|
+
"description": "The fast-forward derivation: which phase a launch resumes at, derived from artifacts on disk and NEVER from stored state or conversation memory. Produced by kernel/probe/resume.mjs on stdout and consumed by shapeup-run.js's preamble on every launch, fresh or relaunch alike. Every phase predicate is an artifact test — `has_orient_artifacts` exists because the ORIENT branch was once gated on the ledger's stored `status` instead, which a silent courier failure left stale, and a completed ORIENT phase was re-dispatched on resume. `next_phase` is a convenience derived from the same booleans, which all travel too: a caller is never forced to trust a summary it cannot re-derive.",
|
|
2174
2361
|
"x-tier": "EMBEDDED",
|
|
2175
|
-
"x-location": "stdout of resume
|
|
2176
|
-
"x-writer": "resume
|
|
2362
|
+
"x-location": "stdout of harness probe resume — never written to disk (the run's state IS the artifacts this record reports on)",
|
|
2363
|
+
"x-writer": "harness probe resume (deriving; the same script's --set-status / --set-active-scope operations write, and report their own outcome record instead)",
|
|
2177
2364
|
"x-readers": "shapeup-run.js (the fast-forward preamble, one call per launch)",
|
|
2178
2365
|
"type": "object",
|
|
2179
2366
|
"required": [
|
|
@@ -2204,7 +2391,46 @@
|
|
|
2204
2391
|
"string",
|
|
2205
2392
|
"null"
|
|
2206
2393
|
],
|
|
2207
|
-
"description": "The ledger's stored status, reported for the readers that legitimately hold a MID_RUN set over it (
|
|
2394
|
+
"description": "The ledger's stored status, reported for the readers that legitimately hold a MID_RUN set over it (harness reduce snapshot, and the ship report's census). NOT a resume predicate: no phase decision in shapeup-run.js may branch on this field."
|
|
2395
|
+
},
|
|
2396
|
+
"lens": {
|
|
2397
|
+
"type": [
|
|
2398
|
+
"string",
|
|
2399
|
+
"null"
|
|
2400
|
+
],
|
|
2401
|
+
"description": "From harness-run.md frontmatter; forwarded to the analyze dispatch. Null when the ledger names none — an unknown value is an ABSENT key in the order, never a null."
|
|
2402
|
+
},
|
|
2403
|
+
"stack": {
|
|
2404
|
+
"type": [
|
|
2405
|
+
"string",
|
|
2406
|
+
"null"
|
|
2407
|
+
],
|
|
2408
|
+
"description": "From harness-run.md frontmatter; forwarded to the orient dispatch. Null when the ledger names none."
|
|
2409
|
+
},
|
|
2410
|
+
"run_cmd": {
|
|
2411
|
+
"type": [
|
|
2412
|
+
"string",
|
|
2413
|
+
"null"
|
|
2414
|
+
],
|
|
2415
|
+
"description": "How to run the feature, from harness-run.md frontmatter; forwarded to the evaluate dispatch so the judge exercises a running thing. Null when the ledger names none."
|
|
2416
|
+
},
|
|
2417
|
+
"app_url": {
|
|
2418
|
+
"type": [
|
|
2419
|
+
"string",
|
|
2420
|
+
"null"
|
|
2421
|
+
],
|
|
2422
|
+
"description": "Where the feature answers, from harness-run.md frontmatter; forwarded to the QA hunt. Null when the ledger names none."
|
|
2423
|
+
},
|
|
2424
|
+
"eval_dimensions": {
|
|
2425
|
+
"type": "array",
|
|
2426
|
+
"items": {
|
|
2427
|
+
"type": "string"
|
|
2428
|
+
},
|
|
2429
|
+
"description": "The dimensions this run's EVAL grades, from harness-run.md frontmatter. Defaults to [\"spec-conformance\"] rather than empty, so a ledger that names none still produces a graded run — and the ship sign-off reports the complement as the dimensions the run did NOT cover."
|
|
2430
|
+
},
|
|
2431
|
+
"orient_dir": {
|
|
2432
|
+
"type": "string",
|
|
2433
|
+
"description": "The run's LOCAL orient directory, resolved for the analyze dispatch: ORIENT's spike and code-surface notes are working artifacts, not deliverables, so they live in the gitignored tier (ADR-0001)."
|
|
2208
2434
|
},
|
|
2209
2435
|
"has_orient_artifacts": {
|
|
2210
2436
|
"type": "boolean",
|
|
@@ -2227,7 +2453,7 @@
|
|
|
2227
2453
|
},
|
|
2228
2454
|
"scope_files": {
|
|
2229
2455
|
"type": "array",
|
|
2230
|
-
"description": "MAP SCOPES finished when non-empty. Each entry carries a RESOLVED path, never a bare filename — compile
|
|
2456
|
+
"description": "MAP SCOPES finished when non-empty. Each entry carries a RESOLVED path, never a bare filename — harness compile and harness verify t0 resolve --scope against cwd, and a bare id makes compile-order exit 2, which the attempt loop reads as the stagnation breaker.",
|
|
2231
2457
|
"items": {
|
|
2232
2458
|
"type": "object",
|
|
2233
2459
|
"required": [
|
|
@@ -2244,12 +2470,42 @@
|
|
|
2244
2470
|
}
|
|
2245
2471
|
}
|
|
2246
2472
|
},
|
|
2473
|
+
"scope_waves": {
|
|
2474
|
+
"type": "array",
|
|
2475
|
+
"description": "The same scopes as scope_files, grouped into dependency WAVES: no wave contains a scope that depends on one still in flight. Levelled by `probe resume` from each contract's own `depends_on` — declared in the same COMMITTED tier as the contracts it orders, so it survives the clone that a join through machine-local task ids never could. Under the edge-released scheduler this is an ORDER and a cross-check rather than a barrier: the orchestrator trusts `scope_deps` only when Kahn-levelling it reproduces this field, so an edge lost crossing the sub-agent boundary degrades to wave release instead of starting a scope early. ADDITIVE: a consumer that ignores it, or a tree where no contract declares `depends_on`, every declared id names a scope not in the run, or the relation is cyclic, gets a single wave containing everything, which is the unscheduled fixed-width fan-out this replaced.",
|
|
2476
|
+
"items": {
|
|
2477
|
+
"type": "array",
|
|
2478
|
+
"items": {
|
|
2479
|
+
"type": "string"
|
|
2480
|
+
}
|
|
2481
|
+
}
|
|
2482
|
+
},
|
|
2483
|
+
"scope_deps": {
|
|
2484
|
+
"type": "array",
|
|
2485
|
+
"description": "The dependency edges the waves were levelled from, as `[dependant, dependency]` pairs, so a scope can be released the moment ITS OWN dependencies are green rather than when its whole wave finishes. Same parse as scope_waves; the two validate each other. ADDITIVE — absent, unusable or disagreeing with scope_waves, release falls back to the wave boundary.",
|
|
2486
|
+
"items": {
|
|
2487
|
+
"type": "array",
|
|
2488
|
+
"items": {
|
|
2489
|
+
"type": "string"
|
|
2490
|
+
}
|
|
2491
|
+
}
|
|
2492
|
+
},
|
|
2493
|
+
"scope_exclusions": {
|
|
2494
|
+
"type": "array",
|
|
2495
|
+
"description": "Pairs of scopes that may not build AT THE SAME TIME because both declare a write to one path — `substrate.shared` is the sanctioned escape from the disjointness rule, so the lint passes it and the substrate wall permits that path to every live order. Measured: three concurrent writers to one entry point lost work in 20 of 20 trials, because an edit is read-modify-write and the later writer drops the earlier one silently. Unlike scope_deps these pairs are UNORDERED — neither scope waits for the other, they merely never overlap — and unlike a dependency they cost concurrency rather than buying correctness in sequence, which is why the release ceiling they imply is reported before a run spends anything.",
|
|
2496
|
+
"items": {
|
|
2497
|
+
"type": "array",
|
|
2498
|
+
"items": {
|
|
2499
|
+
"type": "string"
|
|
2500
|
+
}
|
|
2501
|
+
}
|
|
2502
|
+
},
|
|
2247
2503
|
"pending_orders": {
|
|
2248
2504
|
"type": "array",
|
|
2249
2505
|
"items": {
|
|
2250
2506
|
"type": "string"
|
|
2251
2507
|
},
|
|
2252
|
-
"description": "Order files with no result beside them. Diagnostic only — build orders carry no scope id, so this set is not an audit trail of build dispatches (see compile
|
|
2508
|
+
"description": "Order files with no result beside them. Diagnostic only — build orders carry no scope id, so this set is not an audit trail of build dispatches (see harness compile's order-id note)."
|
|
2253
2509
|
},
|
|
2254
2510
|
"eval_rounds_done": {
|
|
2255
2511
|
"type": "array",
|
|
@@ -2267,12 +2523,12 @@
|
|
|
2267
2523
|
"map-scopes",
|
|
2268
2524
|
"build"
|
|
2269
2525
|
],
|
|
2270
|
-
"description": "The first phase whose artifacts are incomplete. Derived from the booleans above, in that order. The same table (resume
|
|
2526
|
+
"description": "The first phase whose artifacts are incomplete. Derived from the booleans above, in that order. The same table (harness probe resume PHASE_ARTIFACT) answers `--require <phase>`, the post-condition shapeup-run.js checks after every phase dispatch — resume and completion are ONE predicate by construction."
|
|
2271
2527
|
}
|
|
2272
2528
|
}
|
|
2273
2529
|
},
|
|
2274
2530
|
"RunArgs": {
|
|
2275
|
-
"description": "C1 — the launch half of the workflow's only conversation. Compiled ONCE by tech-lead at GATE L0 from init
|
|
2531
|
+
"description": "C1 — the launch half of the workflow's only conversation. Compiled ONCE by tech-lead at GATE L0 from harness init run output + the L0.8 model matrix + budgets, written to .shapeup/<slug>/run-args.json and handed to the harness run launch as one JSON literal — the workflow cannot ask follow-ups and cannot read config files itself, so everything a run will ever need travels in this one record. A workflow script validates its own subset of this shape in code (no runtime schema check at the C1 boundary itself); this entry is the central-registry definition the workflow script and the tech-lead skill both read as the one true shape.",
|
|
2276
2532
|
"x-tier": "EMBEDDED",
|
|
2277
2533
|
"x-location": ".shapeup/<slug>/run-args.json — written fresh by tech-lead on every launch and relaunch; the workflow receives it as its args and never reads other config",
|
|
2278
2534
|
"x-writer": "tech-lead (GATE L0, on every launch AND every relaunch after a paused gate)",
|
|
@@ -2292,6 +2548,11 @@
|
|
|
2292
2548
|
"type": "string",
|
|
2293
2549
|
"description": "The feature slug this run builds — the aggregate root every path is keyed off."
|
|
2294
2550
|
},
|
|
2551
|
+
"runId": {
|
|
2552
|
+
"type": "string",
|
|
2553
|
+
"description": "OPTIONAL (v1.8) — the run key, COPIED from harness init run's `run_id` output. Carried here so harness run stamps every journal row without a receipt lookup per launch; a launch without it falls back to reading the receipt, so this is an optimisation, not the source of truth. This is identity, which x-not-here explicitly admits to RunArgs — it is not run config the ledger already carries.",
|
|
2554
|
+
"pattern": "^[a-z0-9][a-z0-9-]*-[0-9]{8}T[0-9]{6}Z-[0-9a-f]{8}$"
|
|
2555
|
+
},
|
|
2295
2556
|
"autoLevel": {
|
|
2296
2557
|
"type": "string",
|
|
2297
2558
|
"enum": [
|
|
@@ -2299,7 +2560,7 @@
|
|
|
2299
2560
|
"auto",
|
|
2300
2561
|
"unattended"
|
|
2301
2562
|
],
|
|
2302
|
-
"description": "Resolved once at GATE L0; governs which gates pre-approve and what on_missing does (gate
|
|
2563
|
+
"description": "Resolved once at GATE L0; governs which gates pre-approve and what on_missing does (harness gate)."
|
|
2303
2564
|
},
|
|
2304
2565
|
"answers": {
|
|
2305
2566
|
"type": "string",
|
|
@@ -2341,7 +2602,7 @@
|
|
|
2341
2602
|
},
|
|
2342
2603
|
"startedAt": {
|
|
2343
2604
|
"type": "string",
|
|
2344
|
-
"description": "ISO timestamp, passed in because Date.now() is unavailable inside a workflow script by design — the deadline breaker (budget
|
|
2605
|
+
"description": "ISO timestamp, passed in because Date.now() is unavailable inside a workflow script by design — the deadline breaker (harness verify budget) computes elapsed time itself, in Node, where the clock lives."
|
|
2345
2606
|
},
|
|
2346
2607
|
"lane": {
|
|
2347
2608
|
"$ref": "#/$defs/Lane",
|
|
@@ -2350,11 +2611,25 @@
|
|
|
2350
2611
|
"noEval": {
|
|
2351
2612
|
"type": "boolean",
|
|
2352
2613
|
"description": "If true, skips the EVAL phase completely. Rides here rather than in the ledger because there is no frontmatter line that carries it — contrast eval_dimensions, which does."
|
|
2614
|
+
},
|
|
2615
|
+
"noQa": {
|
|
2616
|
+
"type": "boolean",
|
|
2617
|
+
"description": "If true, skips the QA Edge Hunt (`--no-qa`). Rides here for the same reason as noEval: no frontmatter line carries it. It is declared because the workflow reads it — an arg the script consumes and this record omits is a switch the launcher never learns to send, which is a documented flag that does nothing."
|
|
2618
|
+
},
|
|
2619
|
+
"maxParallelScopes": {
|
|
2620
|
+
"type": "integer",
|
|
2621
|
+
"minimum": 1,
|
|
2622
|
+
"default": 4,
|
|
2623
|
+
"description": "How many scopes may build at once (`--parallel-scopes`). A dial rather than a constant because concurrency is a COST question before it is a speed one: every extra leg is another worker's full context. 1 restores sequential scope building, which is the mitigation when a worker archetype proves unsafe to run beside itself."
|
|
2624
|
+
},
|
|
2625
|
+
"adversarialVerify": {
|
|
2626
|
+
"type": "boolean",
|
|
2627
|
+
"description": "If true, each FAIL finding gets one independent skeptic before it costs a whole fix round (`--adversarial-verify`). Off by default: it is a pure addition that spends one sub-agent per finding, and the single-judge invariant is unaffected — a refutation retracts a finding, it never issues a verdict."
|
|
2353
2628
|
}
|
|
2354
2629
|
}
|
|
2355
2630
|
},
|
|
2356
2631
|
"RunReturn": {
|
|
2357
|
-
"description": "C1 — the return half of the workflow's only conversation. The ONLY way the workflow speaks back to tech-lead, so it is a tagged union keyed on `status` — the skill branches on the tag, never on prose (the same exit-code discipline gate
|
|
2632
|
+
"description": "C1 — the return half of the workflow's only conversation. The ONLY way the workflow speaks back to tech-lead, so it is a tagged union keyed on `status` — the skill branches on the tag, never on prose (the same exit-code discipline harness gate already applies to gate sign-off, extended to the orchestrator's own return value). A gate resolved 'ask' (exit 4) always returns `paused`; a gate resolved 'abort' (exit 5) always returns `aborted`; any circuit breaker tripping (outer round_budget, inner attempt_budget, or the deadline breaker) returns `gate_h`; a full run whose final EVAL passes returns `shipped`. The union is written as a superset of what one inner round can itself produce (`paused`, `aborted`, `gate_h`, or a round-complete carrying a verdict) — `shipped` belongs only to a full run. It is deliberately NOT narrowed, because the round-scoped subset is what a `workflow()` child would return if the fan-out this design anticipates ever spends that nesting level.",
|
|
2358
2633
|
"x-tier": "EMBEDDED",
|
|
2359
2634
|
"x-location": "in-memory only — a Workflow return value, never written to disk",
|
|
2360
2635
|
"x-writer": "the workflow runtime (shapeup-run — the sole writer)",
|
|
@@ -2423,7 +2698,7 @@
|
|
|
2423
2698
|
"items": {
|
|
2424
2699
|
"type": "string"
|
|
2425
2700
|
},
|
|
2426
|
-
"description": "paused: the decisions VALID_BY_GATE allows at this gate (gate
|
|
2701
|
+
"description": "paused: the decisions VALID_BY_GATE allows at this gate (harness gate)."
|
|
2427
2702
|
},
|
|
2428
2703
|
"context": {
|
|
2429
2704
|
"type": "object",
|
|
@@ -2435,7 +2710,7 @@
|
|
|
2435
2710
|
},
|
|
2436
2711
|
"reason": {
|
|
2437
2712
|
"type": "string",
|
|
2438
|
-
"description": "aborted: the attributable reason (gate
|
|
2713
|
+
"description": "aborted: the attributable reason (harness gate's own `reason` field, carried through verbatim)."
|
|
2439
2714
|
},
|
|
2440
2715
|
"breaker": {
|
|
2441
2716
|
"type": "string",
|