@azure-id/orc 2.1.1 → 2.2.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 (145) hide show
  1. package/CHANGELOG.md +320 -0
  2. package/README.md +48 -23
  3. package/bin/build-agents.js +207 -205
  4. package/bin/cli.js +48188 -47417
  5. package/bin/fix.js +21 -18
  6. package/bin/graph-extract.js +314 -6
  7. package/bin/graph-gain.js +83 -2
  8. package/bin/graph-map.js +23 -1
  9. package/bin/graph-notes.js +1 -1
  10. package/bin/graph-query.js +1362 -37
  11. package/bin/graph-resolve.js +1 -1
  12. package/bin/graph-shard.js +29 -6
  13. package/bin/graph-signals.js +5 -3
  14. package/bin/graph.js +7 -3
  15. package/bin/habit.js +1 -1
  16. package/bin/pricing.json +8 -1
  17. package/bin/trace-write.js +40 -11
  18. package/bin/verify-contracts.js +5661 -5552
  19. package/bin/verify-package.js +716 -716
  20. package/bin/webui/api.js +8 -0
  21. package/bin/webui/fixtures/extra.js +2036 -2036
  22. package/bin/webui/fixtures/flow.js +1 -1
  23. package/bin/webui/fixtures/index.js +2 -2
  24. package/bin/webui/fixtures/knowledge.js +8 -1
  25. package/bin/webui/fixtures/pact.js +112 -111
  26. package/bin/webui/fixtures/stats.js +2 -2
  27. package/bin/webui/i18n/en/knowledge.json +2 -0
  28. package/bin/webui/i18n/id/knowledge.json +2 -0
  29. package/bin/webui/js/panels/knowledge.js +17 -0
  30. package/guides/code-graph-benefit.md +116 -0
  31. package/guides/configuration.md +150 -0
  32. package/guides/documents.md +262 -0
  33. package/guides/extra-models.md +448 -0
  34. package/guides/habits-and-gotchas.md +152 -0
  35. package/guides/knowledge-reads.md +190 -0
  36. package/guides/model-selection.md +186 -0
  37. package/guides/rules.md +305 -0
  38. package/guides/status-line.md +344 -0
  39. package/mock-run/orc-cli.md +3 -2
  40. package/mock-run/orc-doc.md +452 -448
  41. package/mock-run/orc.md +157 -157
  42. package/package.json +2 -1
  43. package/templates/agents/MODEL-MAPPING.md +176 -176
  44. package/templates/agents/{orc-executor-haiku-4-5.md → orc-executor-haiku-5-high.md} +21 -8
  45. package/templates/agents/orc-executor-opus-4-7-high.md +17 -5
  46. package/templates/agents/orc-executor-opus-4-7-med.md +17 -5
  47. package/templates/agents/orc-executor-opus-4-8-high.md +17 -5
  48. package/templates/agents/orc-executor-opus-5-high.md +17 -5
  49. package/templates/agents/orc-executor-opus-5-low.md +17 -5
  50. package/templates/agents/orc-executor-opus-5-med.md +17 -5
  51. package/templates/agents/orc-executor-sonnet-4-6-high.md +17 -5
  52. package/templates/agents/orc-executor-sonnet-5-high.md +17 -5
  53. package/templates/agents/orc-executor-sonnet-5-low.md +17 -5
  54. package/templates/agents/orc-executor-sonnet-5-med.md +17 -5
  55. package/templates/agents/{orc-graph-noter-sonnet-4-6-med.md → orc-graph-noter-haiku-5-high.md} +4 -4
  56. package/templates/agents/orc-planner-mini-opus-5-med.md +3 -1
  57. package/templates/agents/orc-planner-mini-sonnet-5-high.md +3 -1
  58. package/templates/agents/orc-planner-opus-5-med.md +3 -1
  59. package/templates/agents/{orc-trace-writer-haiku-4-5.md → orc-trace-writer-haiku-5-high.md} +4 -3
  60. package/templates/commands/orc-doc.md +128 -128
  61. package/templates/commands/orc-export.md +51 -46
  62. package/templates/hooks/README.md +8 -3
  63. package/templates/hooks/orc-effort-guard.js +105 -27
  64. package/templates/hooks/orc-graph-hook.js +252 -4
  65. package/templates/hooks/orc-statusline.js +13 -6
  66. package/templates/hooks/orc-trace.js +1 -1
  67. package/templates/skills/_shared/README.md +2 -2
  68. package/templates/skills/_shared/code-graph.md +185 -251
  69. package/templates/skills/_shared/extra-dispatch.md +1331 -1331
  70. package/templates/skills/_shared/lane-contract.md +7 -3
  71. package/templates/skills/_shared/opus5-only.md +137 -137
  72. package/templates/skills/_shared/phases/execution.md +13 -11
  73. package/templates/skills/_shared/phases/planning.md +27 -9
  74. package/templates/skills/_shared/phases/preflight.md +3 -3
  75. package/templates/skills/_shared/phases/review.md +4 -3
  76. package/templates/skills/_shared/phases/ship.md +7 -10
  77. package/templates/skills/_shared/phases/summary.md +2 -3
  78. package/templates/skills/_shared/phases/trace-verbs.md +21 -16
  79. package/templates/skills/_shared/phases/trace.md +3 -3
  80. package/templates/skills/_shared/phases/wiki-consult.md +2 -2
  81. package/templates/skills/_shared/pr-templates.md +108 -106
  82. package/templates/skills/_shared/read-ladder.md +8 -2
  83. package/templates/skills/_shared/return-validation.md +10 -6
  84. package/templates/skills/_shared/review-slice.md +1 -1
  85. package/templates/skills/_shared/stack-plan.md +135 -135
  86. package/templates/skills/_shared/wait.md +14 -2
  87. package/templates/skills/context-combiner/SKILL.md +2 -2
  88. package/templates/skills/orc/SKILL.md +227 -227
  89. package/templates/skills/orc/config.md +2 -2
  90. package/templates/skills/orc/examples/full-run-mock.md +74 -74
  91. package/templates/skills/orc/schemas/planning-output.md +3 -0
  92. package/templates/skills/orc-aftermath/SKILL.md +15 -15
  93. package/templates/skills/orc-analyze/SKILL.md +2 -2
  94. package/templates/skills/orc-analyze-mini/SKILL.md +2 -2
  95. package/templates/skills/orc-boundary/SKILL.md +15 -15
  96. package/templates/skills/orc-boundary/references/card.md +81 -78
  97. package/templates/skills/orc-boundary/references/gate.md +113 -113
  98. package/templates/skills/orc-brainstorm/SKILL.md +15 -15
  99. package/templates/skills/orc-budget/SKILL.md +15 -15
  100. package/templates/skills/orc-challenge/README.md +1 -1
  101. package/templates/skills/orc-challenge/SKILL.md +16 -16
  102. package/templates/skills/orc-challenge/examples/council-full-roster.md +1 -1
  103. package/templates/skills/orc-claude/SKILL.md +4 -4
  104. package/templates/skills/orc-claude/examples/claude-run-mock.md +1 -1
  105. package/templates/skills/orc-diy/SKILL.md +2 -2
  106. package/templates/skills/orc-diy/references/blocks/wiki.md +26 -26
  107. package/templates/skills/orc-diy/references/flow-schema.md +2 -2
  108. package/templates/skills/orc-doc/README.md +2 -2
  109. package/templates/skills/orc-doc/SKILL.md +501 -490
  110. package/templates/skills/orc-doc/examples/orc-doc-prd-run.md +12 -1
  111. package/templates/skills/orc-doc/references/chunking.md +6 -4
  112. package/templates/skills/orc-doc/references/gates.md +311 -311
  113. package/templates/skills/orc-doc/references/resume-protocol.md +229 -228
  114. package/templates/skills/orc-explain/SKILL.md +88 -88
  115. package/templates/skills/orc-export/SKILL.md +190 -187
  116. package/templates/skills/orc-fast/SKILL.md +213 -210
  117. package/templates/skills/orc-grill/SKILL.md +245 -245
  118. package/templates/skills/orc-handoff/SKILL.md +11 -11
  119. package/templates/skills/orc-learn/SKILL.md +13 -13
  120. package/templates/skills/orc-learn/examples/learn-run-mock.md +2 -2
  121. package/templates/skills/orc-mini/SKILL.md +12 -12
  122. package/templates/skills/orc-mini/examples/mini-run-mock.md +4 -5
  123. package/templates/skills/orc-pact/SKILL.md +15 -15
  124. package/templates/skills/orc-pact/references/gate.md +70 -70
  125. package/templates/skills/orc-pattern/SKILL.md +3 -3
  126. package/templates/skills/orc-poly/SKILL.md +4 -4
  127. package/templates/skills/orc-poly/examples/poly-run-mock.md +51 -51
  128. package/templates/skills/orc-pr-driver/SKILL.md +4 -3
  129. package/templates/skills/orc-pr-driver/references/orc-run-split.md +108 -99
  130. package/templates/skills/orc-pr-setup/SKILL.md +2 -2
  131. package/templates/skills/orc-quick/README.md +535 -536
  132. package/templates/skills/orc-quick/SKILL.md +29 -32
  133. package/templates/skills/orc-quick/references/context-doc.md +145 -145
  134. package/templates/skills/orc-quick/references/dispatch-gate.md +220 -220
  135. package/templates/skills/orc-quick/references/gh-mode.md +2 -1
  136. package/templates/skills/orc-quick/references/look.md +34 -12
  137. package/templates/skills/orc-retro/SKILL.md +2 -2
  138. package/templates/skills/orc-retro/examples/retro-mock.md +2 -2
  139. package/templates/skills/orc-route/SKILL.md +2 -2
  140. package/templates/skills/orc-test/SKILL.md +6 -3
  141. package/templates/skills/orc-verify/SKILL.md +2 -2
  142. package/templates/skills/orc-wait/SKILL.md +10 -2
  143. package/templates/skills/orc-wiki/SKILL.md +4 -4
  144. package/templates/skills/orc-wiki/references/pattern-prewarm.md +19 -19
  145. package/templates/agents/orc-executor-sonnet-4-6-med.md +0 -155
@@ -31,7 +31,7 @@ const diy = {
31
31
  { key: "planning", value: "own-planner", default: "auto", is_set: true, desc: "Planning route.", options: ["auto", "own-planner", "superpowers", "openspec"] },
32
32
  { key: "pattern", value: "ask", default: "ask", is_set: false, desc: "Code-pattern gate on a cache miss.", options: ["ask", "off", "on"] },
33
33
  { key: "scoring", value: "on", default: "on", is_set: false, desc: "Rubric scoring.", options: ["on", "off"] },
34
- { key: "fixed_executor", value: "", default: "", is_set: false, desc: "Executor used for every task when scoring is off.", options: ["orc-executor-haiku-4-5", "orc-executor-sonnet-4-6-med", "orc-executor-sonnet-5-high", "orc-executor-opus-4-8-high", "orc-executor-opus-5-high"] },
34
+ { key: "fixed_executor", value: "", default: "", is_set: false, desc: "Executor used for every task when scoring is off.", options: ["orc-executor-haiku-5-high", "orc-executor-sonnet-5-high", "orc-executor-opus-4-8-high", "orc-executor-opus-5-high"] },
35
35
  { key: "review", value: "blocking-only", default: "full", is_set: true, desc: "Review phase depth.", options: ["on", "off", "blocking-only"] },
36
36
  { key: "security", value: "off", default: "off", is_set: false, desc: "Security pass.", options: ["off", "ask", "on", "always"] },
37
37
  { key: "verify", value: "smoke", default: "full", is_set: true, desc: "Verification depth.", options: ["full", "off", "smoke"] },
@@ -21,7 +21,7 @@
21
21
  // case here; it is never an edit to a 1 700-line module.
22
22
  const { PROJECT, doctor, where } = require("./shell.js");
23
23
  const { config } = require("./settings.js");
24
- const { wiki, wikiDocs, wikiShow, wikiCoverage, wikiCoverageFull, wikiUnregistered, wikiPlan, wikiDebt, wikiUsage, patterns, patternShow, gotchas, gotchasArchived, gotchaPrunePreview, wikiImpact, graph, graphGain, graphGainMeasured } = require("./knowledge.js");
24
+ const { wiki, wikiDocs, wikiShow, wikiCoverage, wikiCoverageFull, wikiUnregistered, wikiPlan, wikiDebt, wikiUsage, patterns, patternShow, gotchas, gotchasArchived, gotchaPrunePreview, wikiImpact, graph, graphSemi, graphGain, graphGainMeasured } = require("./knowledge.js");
25
25
  const { runs, runDetail, runDetailClosed, aftermath } = require("./runs.js");
26
26
  const { stats, budgetForecast, budgetRates } = require("./stats.js");
27
27
  const { pact } = require("./pact.js");
@@ -309,7 +309,7 @@ module.exports.get = function get(route, q) {
309
309
  return wikiImpact;
310
310
  // v1.8.0 — the code graph, DRIFTED (the state the card must be designed for).
311
311
  case "/api/graph":
312
- return graph;
312
+ return q && q.mode === "semi" ? graphSemi : graph;
313
313
  // v1.8.2 W4b — the gain meter, and the A/B behind its second button.
314
314
  case "/api/graph/gain":
315
315
  return graphGain;
@@ -309,6 +309,8 @@ const graph = {
309
309
  generation: 42,
310
310
  gen_id: "c878981d",
311
311
  state: "drifted",
312
+ // v2.2.0 — the configured `code_graph`, added by the API (not by the CLI).
313
+ mode: "on",
312
314
  behind: { added: 1, changed: 3, deleted: 0 },
313
315
  engine_stale: false,
314
316
  auto_update: true,
@@ -334,6 +336,11 @@ const graph = {
334
336
 
335
337
  // v1.8.2 W4b — `orc graph gain --json`. The fixture carries the ESTIMATE word
336
338
  // and a RANGE, because those are the two things the card must never lose.
339
+ // v2.2.0 — the same index under `code_graph: semi`. `graph status` (no
340
+ // --if-enabled) answers the index state; the API adds `mode` from the config.
341
+ // Served on /api/graph?mode=semi so the default tab stays DRIFTED.
342
+ const graphSemi = { ...graph, state: "fresh", behind: { added: 0, changed: 0, deleted: 0 }, mode: "semi" };
343
+
337
344
  const graphGain = {
338
345
  ok: true,
339
346
  state: "rows",
@@ -376,4 +383,4 @@ const graphGainMeasured = {
376
383
  "executor windows and session totals are kept apart: the main session is 74–80% of a run and the graph never touches it. Every delta is printed beside the OFF group's own spread — a delta smaller than that spread is noise, not a result.",
377
384
  };
378
385
 
379
- module.exports = { wiki, wikiDocs, wikiShow, wikiCoverage, wikiCoverageFull, wikiUnregistered, wikiPlan, wikiDebt, wikiUsage, patterns, patternShow, gotchas, gotchasArchived, gotchaPrunePreview, wikiImpact, graph, graphGain, graphGainMeasured };
386
+ module.exports = { wiki, wikiDocs, wikiShow, wikiCoverage, wikiCoverageFull, wikiUnregistered, wikiPlan, wikiDebt, wikiUsage, patterns, patternShow, gotchas, gotchasArchived, gotchaPrunePreview, wikiImpact, graph, graphSemi, graphGain, graphGainMeasured };
@@ -1,111 +1,112 @@
1
- "use strict";
2
- /* fixtures/pact.js — canned data for `orc ui --fixtures`.
3
- The invariant ledger, carrying one of each state — BROKEN, DRIFTED,
4
- UNCHECKABLE, HOLDING.
5
-
6
- THE RULE FOR EVERY FILE IN HERE: carry ONE OF EVERY STATE, including the
7
- ugly ones. You cannot DESIGN a STALE chip on a fresh wiki, and a state
8
- with no fixture is a state nobody has ever looked at. A per-state count
9
- test asserts this, so a new state cannot ship without one.
10
-
11
- Shapes MUST match what `bin/cli.js --json` really emits — a drifted
12
- fixture is worse than no fixture. */
13
-
14
- const { PROJECT } = require("./shell.js");
15
-
16
- const pact = {
17
- ok: true,
18
- ledger: PROJECT + "/.claude/orc/pact/ledger.json",
19
- doc: PROJECT + "/PACT.md",
20
- doc_exists: true,
21
- entries: 5,
22
- retired: 1,
23
- counts: { HOLDING: 2, DRIFTED: 1, UNCHECKABLE: 1, BROKEN: 1 },
24
- line: "pact: 2 holding · 1 drifted · 1 uncheckable · 1 BROKEN",
25
- rows: [
26
- {
27
- id: "PACT-014",
28
- statement: "A payment is never written to the ledger twice for one idempotency key.",
29
- origin: { lane: "orc-grill", run: "run-grill-checkout-100826-141130", kind: "constraint" },
30
- anchors: ["src/payments/ledger.ts:88", "src/payments/idempotency.ts"],
31
- check: { kind: "test", ref: "npm test -- idempotency" },
32
- verified_commit: "8a62b4f1c9",
33
- confidence: "high",
34
- last_check: { status: "fail", commit: "8a62b4f1c9", at: "09-08-2026 11:20:04", ref: "npm test -- idempotency" },
35
- // A real-looking failure, not a placeholder: the panel has to lay out a
36
- // multi-line check output that does not fit its card.
37
- history: [
38
- { at: "09-08-2026 11:20:04", status: "fail", commit: "8a62b4f1c9" },
39
- { at: "02-08-2026 09:14:51", status: "pass", commit: "c273793aa1" },
40
- ],
41
- retired: false,
42
- state: "BROKEN",
43
- why: "check failed at 8a62b4f1 (09-08-2026 11:20:04)",
44
- distance: 3,
45
- },
46
- {
47
- id: "PACT-002",
48
- statement: "Refund windows are configured, never hardcoded.",
49
- origin: { lane: "orc-brainstorm", run: "run-brainstorm-refunds-010826-101010", kind: "constraint" },
50
- anchors: ["src/billing/refund.ts"],
51
- check: { kind: "grep", ref: "REFUND_WINDOW_DAYS" },
52
- verified_commit: "c273793aa1",
53
- confidence: "medium",
54
- last_check: { status: "pass", commit: "c273793aa1", at: "01-08-2026 10:11:02", ref: "REFUND_WINDOW_DAYS" },
55
- history: [{ at: "01-08-2026 10:11:02", status: "pass", commit: "c273793aa1" }],
56
- retired: false,
57
- state: "DRIFTED",
58
- why: "6 commits since c273793a touched 1 anchored file",
59
- distance: 6,
60
- },
61
- {
62
- id: "PACT-007",
63
- statement: "The admin export never contains a raw email address.",
64
- origin: { lane: "user", run: null, kind: "constraint" },
65
- anchors: ["src/admin/export.ts"],
66
- check: { kind: "manual", ref: null },
67
- verified_commit: "783f6971aa",
68
- confidence: "low",
69
- last_check: null,
70
- history: [],
71
- retired: false,
72
- state: "UNCHECKABLE",
73
- // The long day count: an UNCHECKABLE promise nobody has looked at for
74
- // months is the case this state exists to make visible.
75
- why: "no cheap check exists — this promise is held by review, not by a runner",
76
- distance: null,
77
- },
78
- {
79
- id: "PACT-001",
80
- statement: "Every outbound webhook is signed with the tenant's current secret.",
81
- origin: { lane: "orc", run: "run-orc-webhooks-120726-084500", kind: "constraint" },
82
- anchors: ["src/webhooks/sign.ts:40"],
83
- check: { kind: "command", ref: "npm run test:webhooks" },
84
- verified_commit: "e9dad01bb2",
85
- confidence: "high",
86
- last_check: { status: "pass", commit: "e9dad01bb2", at: "05-08-2026 16:02:11", ref: "npm run test:webhooks" },
87
- history: [{ at: "05-08-2026 16:02:11", status: "pass", commit: "e9dad01bb2" }],
88
- retired: false,
89
- state: "HOLDING",
90
- why: "verified at e9dad01b; no commit since has touched its anchors",
91
- distance: 0,
92
- },
93
- {
94
- id: "PACT-009",
95
- statement: "Session cookies are always SameSite=Lax.",
96
- origin: { lane: "orc-grill", run: "run-grill-auth-200626-113000", kind: "constraint" },
97
- anchors: ["src/auth/session.ts"],
98
- check: { kind: "grep", ref: "SameSite=Lax" },
99
- verified_commit: "cc4778e0aa",
100
- confidence: "high",
101
- last_check: { status: "pass", commit: "cc4778e0aa", at: "21-06-2026 09:00:00", ref: "SameSite=Lax" },
102
- history: [{ at: "21-06-2026 09:00:00", status: "pass", commit: "cc4778e0aa" }],
103
- retired: false,
104
- state: "HOLDING",
105
- why: "verified at cc4778e0; no commit since has touched its anchors",
106
- distance: 0,
107
- },
108
- ],
109
- };
110
-
111
- module.exports = { pact };
1
+ "use strict";
2
+ /* fixtures/pact.js — canned data for `orc ui --fixtures`.
3
+ The invariant ledger, carrying one of each state — BROKEN, DRIFTED,
4
+ UNCHECKABLE, HOLDING.
5
+
6
+ THE RULE FOR EVERY FILE IN HERE: carry ONE OF EVERY STATE, including the
7
+ ugly ones. You cannot DESIGN a STALE chip on a fresh wiki, and a state
8
+ with no fixture is a state nobody has ever looked at. A per-state count
9
+ test asserts this, so a new state cannot ship without one.
10
+
11
+ Shapes MUST match what `bin/cli.js --json` really emits — a drifted
12
+ fixture is worse than no fixture. */
13
+
14
+ const { PROJECT } = require("./shell.js");
15
+
16
+ const pact = {
17
+ ok: true,
18
+ ledger: PROJECT + "/.claude/orc/pact/ledger.json",
19
+ doc: PROJECT + "/PACT.md",
20
+ doc_exists: true,
21
+ entries: 5,
22
+ retired: 1,
23
+ counts: { HOLDING: 2, DRIFTED: 1, UNCHECKABLE: 1, BROKEN: 1 },
24
+ line: "pact: 2 holding · 1 drifted · 1 uncheckable · 1 BROKEN",
25
+ rows: [
26
+ {
27
+ id: "PACT-014",
28
+ statement: "A payment is never written to the ledger twice for one idempotency key.",
29
+ origin: { lane: "orc-grill", run: "run-grill-checkout-100826-141130", kind: "constraint" },
30
+ anchors: ["src/payments/ledger.ts:88", "src/payments/idempotency.ts"],
31
+ check: { kind: "test", ref: "npm test -- idempotency" },
32
+ verified_commit: "8a62b4f1c9",
33
+ confidence: "high",
34
+ last_check: { status: "fail", commit: "8a62b4f1c9", at: "09-08-2026 11:20:04", ref: "npm test -- idempotency" },
35
+ // A real-looking failure, not a placeholder: the panel has to lay out a
36
+ // multi-line check output that does not fit its card.
37
+ history: [
38
+ { at: "09-08-2026 11:20:04", status: "fail", commit: "8a62b4f1c9" },
39
+ { at: "02-08-2026 09:14:51", status: "pass", commit: "c273793aa1" },
40
+ ],
41
+ retired: false,
42
+ state: "BROKEN",
43
+ why: "check failed at 8a62b4f1 (09-08-2026 11:20:04)",
44
+ distance: 3,
45
+ },
46
+ {
47
+ id: "PACT-002",
48
+ statement: "Refund windows are configured, never hardcoded.",
49
+ origin: { lane: "orc-brainstorm", run: "run-brainstorm-refunds-010826-101010", kind: "constraint" },
50
+ anchors: ["src/billing/refund.ts"],
51
+ check: { kind: "grep", ref: "REFUND_WINDOW_DAYS" },
52
+ verified_commit: "c273793aa1",
53
+ confidence: "medium",
54
+ last_check: { status: "pass", commit: "c273793aa1", at: "01-08-2026 10:11:02", ref: "REFUND_WINDOW_DAYS" },
55
+ history: [{ at: "01-08-2026 10:11:02", status: "pass", commit: "c273793aa1" }],
56
+ retired: false,
57
+ state: "DRIFTED",
58
+ why: "6 commits since c273793a touched 1 of 1 anchored file (src/billing/refund.ts)",
59
+ distance: 6,
60
+ touched_files: ["src/billing/refund.ts"],
61
+ },
62
+ {
63
+ id: "PACT-007",
64
+ statement: "The admin export never contains a raw email address.",
65
+ origin: { lane: "user", run: null, kind: "constraint" },
66
+ anchors: ["src/admin/export.ts"],
67
+ check: { kind: "manual", ref: null },
68
+ verified_commit: "783f6971aa",
69
+ confidence: "low",
70
+ last_check: null,
71
+ history: [],
72
+ retired: false,
73
+ state: "UNCHECKABLE",
74
+ // The long day count: an UNCHECKABLE promise nobody has looked at for
75
+ // months is the case this state exists to make visible.
76
+ why: "no cheap check exists — this promise is held by review, not by a runner",
77
+ distance: null,
78
+ },
79
+ {
80
+ id: "PACT-001",
81
+ statement: "Every outbound webhook is signed with the tenant's current secret.",
82
+ origin: { lane: "orc", run: "run-orc-webhooks-120726-084500", kind: "constraint" },
83
+ anchors: ["src/webhooks/sign.ts:40"],
84
+ check: { kind: "command", ref: "npm run test:webhooks" },
85
+ verified_commit: "e9dad01bb2",
86
+ confidence: "high",
87
+ last_check: { status: "pass", commit: "e9dad01bb2", at: "05-08-2026 16:02:11", ref: "npm run test:webhooks" },
88
+ history: [{ at: "05-08-2026 16:02:11", status: "pass", commit: "e9dad01bb2" }],
89
+ retired: false,
90
+ state: "HOLDING",
91
+ why: "verified at e9dad01b; no commit since has touched its anchors",
92
+ distance: 0,
93
+ },
94
+ {
95
+ id: "PACT-009",
96
+ statement: "Session cookies are always SameSite=Lax.",
97
+ origin: { lane: "orc-grill", run: "run-grill-auth-200626-113000", kind: "constraint" },
98
+ anchors: ["src/auth/session.ts"],
99
+ check: { kind: "grep", ref: "SameSite=Lax" },
100
+ verified_commit: "cc4778e0aa",
101
+ confidence: "high",
102
+ last_check: { status: "pass", commit: "cc4778e0aa", at: "21-06-2026 09:00:00", ref: "SameSite=Lax" },
103
+ history: [{ at: "21-06-2026 09:00:00", status: "pass", commit: "cc4778e0aa" }],
104
+ retired: false,
105
+ state: "HOLDING",
106
+ why: "verified at cc4778e0; no commit since has touched its anchors",
107
+ distance: 0,
108
+ },
109
+ ],
110
+ };
111
+
112
+ module.exports = { pact };
@@ -82,7 +82,7 @@ const budgetForecast = {
82
82
  fixed_roles: [
83
83
  { role: "orc-system-analyst-opus-5-high", samples: 11, p50: { input: 6100, cache_write: 41000, cache_read: 82000, output: 9000 }, p90: { input: 8600, cache_write: 58000, cache_read: 116000, output: 13000 } },
84
84
  { role: "orc-planner-opus-5-med", samples: 11, p50: { input: 5000, cache_write: 33000, cache_read: 68000, output: 7400 }, p90: { input: 7100, cache_write: 47000, cache_read: 96000, output: 10500 } },
85
- { role: "orc-trace-writer-haiku-4-5", samples: 41, p50: { input: 900, cache_write: 3000, cache_read: 5400, output: 700 }, p90: { input: 1300, cache_write: 4400, cache_read: 7800, output: 1000 } },
85
+ { role: "orc-trace-writer-haiku-5-high", samples: 41, p50: { input: 900, cache_write: 3000, cache_read: 5400, output: 700 }, p90: { input: 1300, cache_write: 4400, cache_read: 7800, output: 1000 } },
86
86
  ],
87
87
  low_confidence_bands: 1,
88
88
  min_samples: 5,
@@ -117,7 +117,7 @@ const budgetRates = {
117
117
  },
118
118
  roles: {
119
119
  "orc-system-analyst-opus-5-high": { samples: 11, p50: { input: 6100, cache_write: 41000, cache_read: 82000, output: 9000 }, p90: { input: 8600, cache_write: 58000, cache_read: 116000, output: 13000 }, peak_p50: 88000, peak_p90: 131000 },
120
- "orc-trace-writer-haiku-4-5": { samples: 41, p50: { input: 900, cache_write: 3000, cache_read: 5400, output: 700 }, p90: { input: 1300, cache_write: 4400, cache_read: 7800, output: 1000 }, peak_p50: 9000, peak_p90: 14000 },
120
+ "orc-trace-writer-haiku-5-high": { samples: 41, p50: { input: 900, cache_write: 3000, cache_read: 5400, output: 700 }, p90: { input: 1300, cache_write: 4400, cache_read: 7800, output: 1000 }, peak_p50: 9000, peak_p90: 14000 },
121
121
  },
122
122
  lanes: {},
123
123
  unattributed: { blocks: 12, tokens: { input: 900, cache_write: 12000, cache_read: 24000, output: 1100 } },
@@ -5,6 +5,8 @@
5
5
  "knowledge.graph.unknownHint": "The CLI did not answer. Run the command in a terminal to see why.",
6
6
  "knowledge.graph.off": "The code graph is off.",
7
7
  "knowledge.graph.offHint": "It is off by default. When it is on, code lanes build a local map of the code for free and keep it current.",
8
+ "knowledge.graph.semi": "semi — kept current, lanes do not read it",
9
+ "knowledge.graph.semiHint": "The graph is kept current, but no lane reads it. To enable reading, run this command:",
8
10
  "knowledge.graph.none": "The graph is on, but no index exists yet. The next code lane builds it, or press the button.",
9
11
  "knowledge.graph.files": "Files",
10
12
  "knowledge.graph.symbols": "Symbols",
@@ -5,6 +5,8 @@
5
5
  "knowledge.graph.unknownHint": "CLI tidak menjawab. Jalankan perintahnya di terminal untuk melihat penyebabnya.",
6
6
  "knowledge.graph.off": "Graf kode mati.",
7
7
  "knowledge.graph.offHint": "Default-nya mati. Jika menyala, lane kode membuat peta kode lokal secara gratis dan menjaganya tetap baru.",
8
+ "knowledge.graph.semi": "semi — selalu diperbarui, lane tidak membacanya",
9
+ "knowledge.graph.semiHint": "Graph selalu diperbarui, tetapi tidak ada lane yang membacanya. Untuk mengaktifkan pembacaan, jalankan perintah ini:",
8
10
  "knowledge.graph.none": "Graf menyala, tetapi indeksnya belum ada. Lane kode berikutnya akan membuatnya, atau tekan tombolnya.",
9
11
  "knowledge.graph.files": "File",
10
12
  "knowledge.graph.symbols": "Simbol",
@@ -149,6 +149,19 @@ function knowledgeHeaderStrip(d) {
149
149
  return strip;
150
150
  }
151
151
 
152
+ /* v2.2.0 — code_graph: semi. `graph status` answers the INDEX state, and
153
+ the API adds the configured `mode`. A semi graph is kept current but no lane
154
+ reads it, so the panel says so next to the state, with the one command that
155
+ enables reading. The mode word is a config VALUE — never translated. */
156
+ function graphSemiNote(g) {
157
+ if (!g || g.mode !== "semi") return null;
158
+ const box = el("div", "cg-semi");
159
+ const row = el("div", "row-actions");
160
+ row.append(chip("SEMI", "idle"), el("span", "note", t("knowledge.graph.semi")));
161
+ box.append(row, el("div", "note", t("knowledge.graph.semiHint")), el("pre", "cmd", "orc config set code_graph on"));
162
+ return box;
163
+ }
164
+
152
165
  /* THE CODE GRAPH CARD (v1.8.0). Every value is `orc graph status --json`'s, and
153
166
  the state word is never replaced by a friendlier synonym. An update is FREE
154
167
  (parser only, no model), so it is a button; an OFF graph shows the one config
@@ -167,6 +180,8 @@ function graphCard(g, body, gain, exact) {
167
180
  return c;
168
181
  }
169
182
  if (exact) c.append(el("div", "note", t("knowledge.cg.exact.lead")));
183
+ const semiG = graphSemiNote(g);
184
+ if (semiG && !exact) c.append(semiG);
170
185
  const head = el("div", "row-actions");
171
186
  head.append(chip(String(g.state).toUpperCase(), g.state === "fresh" ? "ok" : g.state === "drifted" ? "warn" : "idle", g.state === "drifted"));
172
187
  const upd = el("button", "btn btn-sm", "orc graph update");
@@ -1228,6 +1243,8 @@ function cgStateCard(g, body) {
1228
1243
  return c;
1229
1244
  }
1230
1245
  c.append(el("div", "note", t("knowledge.cg.state.lead")));
1246
+ const semiS = graphSemiNote(g);
1247
+ if (semiS) c.append(semiS);
1231
1248
  const ladder = el("div", "cg-ladder");
1232
1249
  const steps = [
1233
1250
  ["OFF", t("knowledge.cg.state.off"), t("knowledge.cg.state.toNone")],
@@ -0,0 +1,116 @@
1
+ # When the code graph helps (with live numbers)
2
+
3
+ Short version: **the code graph saves search work when the task must find code
4
+ or follow a change across files.** It does not help a change inside one file
5
+ that you already named. It gives no benefit until it has its data.
6
+
7
+ ---
8
+
9
+ ## 1. What the code graph does for you
10
+
11
+ The code graph is a structure index of your project: files, symbols, callers,
12
+ imports, routes and tests. The lanes read it when they plan and slice a task.
13
+ The graph hook reads it when the main session searches for a known symbol.
14
+ The key `code_graph` sets the mode: `off`, `semi` or `on`.
15
+
16
+ ---
17
+
18
+ ## 2. Before you see a benefit: the graph needs its data
19
+
20
+ > [!NOTE]
21
+ > - Run `orc graph update` ONE time first. This is a cold build. In the eval
22
+ > repo (a company Vue repo: 799 files, 8,531 symbols) it took about 3.5 s.
23
+ > With no index, every graph read answers "no index". The lane then works as
24
+ > with the graph off.
25
+ > - After that, the hooks keep the index current: after each executor, and on
26
+ > read. `orc graph status` shows `fresh`.
27
+ > - The 2.2.0 upgrade rebuilds the index one time (engine `graph@7`).
28
+ > - Notes (one sentence per function) are OPTIONAL stored knowledge. A noter
29
+ > dispatch writes them, and that dispatch costs tokens. The structure layer
30
+ > is free.
31
+
32
+ ---
33
+
34
+ ## 3. The evidence (real repo, live runs)
35
+
36
+ How we measured:
37
+
38
+ - The repo is a real company Vue 2.7 dashboard repo.
39
+ - The lane is `/orc-quick`. The main session is Opus 5.5 medium. The executor
40
+ is pinned to `orc-executor-opus-5-low`.
41
+ - Each task ran with the graph OFF and with the graph ON. The table shows
42
+ medians (or means where it says so).
43
+ - We checked each run: lint, jest, and a Playwright journey where the task has
44
+ a UI. The same grader graded each run against the same lane dossier.
45
+
46
+ | Task | What it is | Runs (OFF / ON) | Cost | Time | Tokens | Grade |
47
+ |---|---|---|---|---|---|---|
48
+ | RMT1 | Build step 1 of a new 4-step flow from a requirement document (route shell, API call, i18n, journey spec) | 5 / 3 | −9.6 % | −28.4 % | −15.8 % | equal (84) |
49
+ | RMT2 | Change one helper's signature and every caller (5 caller files, 1 test) | 3 / 3 | −2.0 % | −8.6 % | −4.2 % | equal (86) |
50
+ | RMT3 | Build step 2 on top of the built step 1 | 2 / 2 (means) | −8.9 % | +4.0 % | −14.0 % | 80 vs 85 (one ON run missed a display detail) |
51
+ | RMT4 | Change behaviour across the built step 1 + step 2 page; ON had stored notes | 2 / 2 (means) | +7.7 % | +45.5 % | +4.4 % | 77 vs 85.5 (one ON run 66 for stray git-hook files, the other 88) |
52
+
53
+ e2e: every RMT1/RMT3/RMT4 run that passed reached every journey step in both
54
+ arms.
55
+
56
+ N = 2–5 per arm. A difference under about 10 % is inside the run-to-run noise
57
+ of one task.
58
+
59
+ ---
60
+
61
+ ## 4. Where the graph helps
62
+
63
+ - **Finding the code to copy or to change.** The executor's exploration fell
64
+ 40–74 % (RMT1, RMT3 phase split).
65
+ - **Changes that ripple across files.** Callers, props / emits, routes and the
66
+ tests that reach a caller come in one card. This card replaces a grep, a
67
+ test hunt and a coverage check.
68
+ - **The main session's own search.** The hook answers a search for a known
69
+ symbol with its callers, tests and coverage (one time per name, 3 per run at
70
+ most). When an executor returns, the hook gives the affected tests.
71
+ - **Time.** The clearest win is on new-feature work (RMT1 −28 %).
72
+
73
+ ---
74
+
75
+ ## 5. Where it does not help (or helps very little)
76
+
77
+ RMT4 is the live example. It is a small follow-up change inside a page that
78
+ the agent reads in a few calls. There was no gain, also with stored notes.
79
+
80
+ - **A change inside ONE named file with no outside effect.** Both arms read
81
+ that file. ORC skips the anchors.
82
+ - **Very small tasks.** The lane's own overhead (config, trace, questions) is
83
+ most of the cost. The graph is break-even.
84
+ - **Test writing and coverage work.** The graph does not write tests. A
85
+ project rule such as "> 90 % branch coverage" can cost more than all that the
86
+ graph saves. We saw this in both arms.
87
+ - **No index, or a stale index.** The lane falls back to Grep. There is no
88
+ harm and no gain.
89
+
90
+ ---
91
+
92
+ ## 6. Turn it on
93
+
94
+ ```bash
95
+ orc config set code_graph on
96
+ orc graph update
97
+ ```
98
+
99
+ Run `orc graph update` one time. The modes are:
100
+
101
+ - `on` — the hooks keep the graph current, and the lanes read it.
102
+ - `semi` — the hooks keep the graph current. No lane reads it.
103
+ - `off` — nothing.
104
+
105
+ For the other keys (`code_graph_notes`, `code_graph_card_budget` and more),
106
+ see [configuration](configuration.md).
107
+
108
+ ---
109
+
110
+ ## 7. What it costs
111
+
112
+ - **Structure:** zero tokens. Local files under `.claude/orc/graph/`. No
113
+ background process.
114
+ - **Cards:** a few hundred tokens each, with a cap.
115
+ - **Hook cards:** 3 per run at most in the main session.
116
+ - **Notes:** optional. Each batch costs a noter dispatch.