@azure-id/orc 1.4.2 → 1.5.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 (36) hide show
  1. package/CHANGELOG.md +111 -0
  2. package/README.md +46 -46
  3. package/bin/cli.js +5918 -400
  4. package/bin/mockrun-catalog.js +4 -0
  5. package/bin/verify-contracts.js +4475 -4410
  6. package/bin/verify-package.js +21 -2
  7. package/bin/webui/api.js +108 -8
  8. package/bin/webui/app.html +9 -0
  9. package/bin/webui/css/06-responsive.css +14 -0
  10. package/bin/webui/css/panels/test.css +132 -0
  11. package/bin/webui/fixtures/index.js +23 -1
  12. package/bin/webui/fixtures/test.js +547 -0
  13. package/bin/webui/i18n/en/common.json +1 -0
  14. package/bin/webui/i18n/en/nav.json +1 -0
  15. package/bin/webui/i18n/en/overview.json +4 -0
  16. package/bin/webui/i18n/en/test.json +141 -0
  17. package/bin/webui/i18n/id/common.json +1 -0
  18. package/bin/webui/i18n/id/nav.json +1 -0
  19. package/bin/webui/i18n/id/overview.json +4 -0
  20. package/bin/webui/i18n/id/test.json +141 -0
  21. package/bin/webui/js/01-i18n.js +1 -0
  22. package/bin/webui/js/panels/challenge.js +8 -3
  23. package/bin/webui/js/panels/overview.js +10 -0
  24. package/bin/webui/js/panels/test.js +733 -0
  25. package/bin/webui/serve.js +572 -557
  26. package/mock-run/orc-test.md +327 -0
  27. package/package.json +1 -1
  28. package/templates/agents/MODEL-MAPPING.md +2 -0
  29. package/templates/agents/orc-test-designer-opus-5-high.md +158 -0
  30. package/templates/agents/orc-test-interpreter-opus-5-low.md +130 -0
  31. package/templates/commands/orc-test.md +66 -0
  32. package/templates/skills/_shared/extra-dispatch.md +1346 -1337
  33. package/templates/skills/_shared/live-target.md +188 -0
  34. package/templates/skills/_shared/phases/trace.md +2 -2
  35. package/templates/skills/_shared/wait.md +241 -240
  36. package/templates/skills/orc-test/SKILL.md +233 -0
package/CHANGELOG.md CHANGED
@@ -10,6 +10,117 @@ Format: `### v<version> — <title> _(<date>)_`.
10
10
 
11
11
  ---
12
12
 
13
+ ### v1.5.0 - the lane that runs the test _(2026-09-07)_
14
+
15
+ **Still on the unscoped `orc` package?** Do this once first - your `orc upgrade`
16
+ is the pre-v0.56.0 one and cannot install itself. Full detail in the CAUTION at
17
+ the top of this file.
18
+
19
+ - **Step 1 - release the command from the old package:** `npm uninstall -g orc`
20
+ - **Step 2 - install the current package:** `npm i -g @azure-id/orc`
21
+ - **Step 3 - re-apply it to your project:** `orc update`
22
+
23
+ **Do not use `npm i -g -f`.** Full detail in v0.56.0 below.
24
+
25
+ Every other testing surface in ORC **writes** tests. `/orc-test` **runs** them.
26
+
27
+ It points at a running API - yours, on your laptop, or one you were given
28
+ permission to touch - sends real requests, writes down what came back, and
29
+ stops. The split is the whole design:
30
+
31
+ > **The CLI executes and measures. The model designs and interprets.**
32
+ > A model never sends a request. The CLI never decides what a response means.
33
+
34
+ That split is what makes the report worth reading. A number in it was measured
35
+ by a program. A sentence in it was written by a model that only ever saw
36
+ evidence on disk.
37
+
38
+ **Three rules hold it together**, each a registered contract:
39
+
40
+ - **`a lane that reports a result it did not observe`** - three verdicts, and
41
+ `unknown` is the honest one. A case nobody ran is never a pass.
42
+ - **`a lane that sends traffic to a target nobody authorized`** - the target is
43
+ frozen once, a remote one **requires** a written statement of who said yes,
44
+ and every request is fenced to one origin.
45
+ - **`a lane that fixes the system under test`** - it reports and hands back. Not
46
+ to fix a boot failure, not to add a `data-testid`, not to relax a check.
47
+
48
+ **The free pass runs first, and always.** `orc test surface` reads your
49
+ repository and the target's own spec document for zero model tokens, and the
50
+ **code-vs-live diff** falls out of it: a route that answers at the target and is
51
+ in **no file in your repository** is undocumented surface nobody reviews and
52
+ nobody patches. It is derived from the two spec documents and from nothing else
53
+ - no route is ever called to produce it. With no spec at the target the diff
54
+ reads **NOT MEASURED, with the reason**, because an empty list there would say
55
+ "no shadow APIs", which is a claim nobody made.
56
+
57
+ **The case matrix derives itself.** The tiers come out of the schema for free.
58
+ What costs anything is a **gap** - what a schema cannot know, like what a valid
59
+ email looks like in your business, or which order two calls have to happen in.
60
+ That is the only part a model is paid for.
61
+
62
+ **The security tier is a closed set** - the OWASP API Top 10 (2023), ten rows,
63
+ never extended on the fly, and **all ten render in every state**. A category ORC
64
+ could not measure says `UNCHECKABLE`, **keeps its slot**, carries its own
65
+ reason, never becomes a pass, and never changes the exit code. Reporting an
66
+ unmeasured category as clean is the single most damaging thing a security report
67
+ can do, because somebody then ships on it. It **detects and never exploits**:
68
+ every probe shows the condition and stops there.
69
+
70
+ **When your app is broken, it stops.** `orc test env` finds the start command,
71
+ sees the process is alive, reads the exact line in the log - and **will not open
72
+ that file**. It names the environment values that are absent and writes a value
73
+ for none of them, because a placeholder in a real environment is a
74
+ credential-shaped lie and only you know the right one.
75
+
76
+ **The runner is the only place in ORC that sends a request to a system it did
77
+ not start**, so everything in it exists to make sure ORC's own run is never the
78
+ incident. A red happy path **stops the ladder** - a 500 on every request will
79
+ "prove" a dozen vulnerabilities that are one bug. The pace is the target's, and
80
+ the CLI applies it. **A 429 is a result**: it means rate limiting works, so ORC
81
+ records it and backs off rather than pushing through, which is how a staging
82
+ scan becomes a lockout. Failed logins are capped per identity. **Redaction is
83
+ structural** - every credential is replaced before the bytes reach disk, not in
84
+ a review step afterwards.
85
+
86
+ **A finding has to point at something.** One that cites evidence which does not
87
+ resolve on disk is **dropped by name and counted**. Severity is ORC's; if the
88
+ interpreting model disagrees, its word is kept beside ORC's and printed, so a
89
+ disagreement is visible instead of invisible. **A flake is recorded, never
90
+ retried away** - the instability is the finding.
91
+
92
+ **The front end drives Playwright as a script**, not as an agent loop: a step an
93
+ LLM took is not a step you can re-run. ORC **names** the install command and
94
+ never runs it - it does not install into your project.
95
+
96
+ **`orc ui` ▸ Test** renders all of it and works out none of it. Five tabs, a
97
+ button for every free action, and **`orc test run` as a command you copy** -
98
+ never a button. It costs no model tokens, so the usual rule would make it one;
99
+ it sends real traffic, and a page that can start a scan against a live host is a
100
+ page that can start one by accident.
101
+
102
+ **The run folder is never staged.** It holds real response bodies from a real
103
+ system - the most sensitive thing ORC writes to disk. `orc doctor` tells you if
104
+ it is not git-ignored, and it will not edit `.gitignore` for you.
105
+
106
+ Five config keys: `test_gate` (warn only - the payoff is knowing, not gating),
107
+ `test_security_tier`, `test_max_rps`, `test_case_budget`, `test_ui_driver`. Five
108
+ more were **refused**, with the reasons written down so nobody proposes them
109
+ again - among them `test_retries`, because a flake is recorded rather than
110
+ retried away, and `test_auto_fix`, which is this lane's premise inverted.
111
+
112
+ **And one bug that was not in this lane.** Writing the tests isolated an
113
+ intermittent failure that turned out to be real: `orc ui` compressed its API
114
+ answers but not its **static files**, guarded by a comment reading *"No asset is
115
+ over 64 KiB today"* that had been false for two releases. `js/panels/extra.js`
116
+ is 138 KB. Over a Windows loopback socket a response that size loses its tail
117
+ roughly one time in six - which in a browser is a panel script that stops in the
118
+ middle of a function, with nothing in any log to say so. Both paths now share
119
+ one encoder. **A stale comment can guard a live bug for longer than the bug
120
+ would have survived alone.**
121
+
122
+ ---
123
+
13
124
  ### v1.4.2 - the panel that stops reloading, and the fields you could not read back _(2026-09-05)_
14
125
 
15
126
  **Still on the unscoped `orc` package?** Do this once first - your `orc upgrade`
package/README.md CHANGED
@@ -14,7 +14,7 @@
14
14
  ![Dependencies](https://img.shields.io/badge/dependencies-zero-lightgrey.svg?style=for-the-badge)
15
15
  ![GitHub stars](https://img.shields.io/github/stars/azure-id/orc?style=for-the-badge&color=yellow)
16
16
 
17
- **Latest: v1.4.2** · updated 2026-09-05 · [full changelog](CHANGELOG.md)
17
+ **Latest: v1.5.0** · updated 2026-09-07 · [full changelog](CHANGELOG.md)
18
18
 
19
19
  **On npm: [`@azure-id/orc`](https://www.npmjs.com/package/@azure-id/orc)** — `npm i -g @azure-id/orc`
20
20
 
@@ -287,6 +287,7 @@ ORC have terminal hook to see: Context Window %, 5 Hour usage %, Weekly usage %
287
287
  | **`/orc-challenge`** | Grades a **finished** artifact — a TSD, a PRD, an ADR, an API contract, a README, a module — against a goal **you** state, then **stops and makes you fix it in a different session**. ORC judges, you fix, ORC re-judges: **it never fixes what it judged**, because a session that just wrote the fix would grade its own homework. **And it never guesses what "good" means here.** | [see it](mock-run/orc-challenge.md) |
288
288
  | **`/orc-pact`** | The promises your project makes, and which are in doubt right now. Four states, all **computed on read**: HOLDING · DRIFTED · **UNCHECKABLE** (the honest state — never a failure) · BROKEN. It never invents a promise and never retires one for you. | [see it](mock-run/orc-pact.md) |
289
289
  | **`/orc-boundary`** | What ORC should **not** try here, and exactly what would change that. EXECUTE · ESCALATE · REFUSE, per area. **A REFUSE always names what would make it a yes.** It gates ORC's own dispatch, never your instructions. | [see it](mock-run/orc-boundary.md) |
290
+ | **`/orc-test`** | **Runs** the test against a running system - yours, or one you were given permission to touch. Sends the requests, writes down what came back, and stops. **The CLI executes and measures; the model designs and interprets.** Three verdicts, and **`unknown` is the honest one**. The OWASP API Top 10 (2023) as a **closed set** where a category it could not measure keeps its slot and never becomes a pass. It never edits the system it is testing. | [see it](mock-run/orc-test.md) |
290
291
  | **`/orc-verify`** | Verifies only your git-modified changes: build, tests, diff sanity, findings on a P0–P3 ladder. Read-only. | [see it](templates/skills/orc-verify/examples/verify-mock.md) |
291
292
  | **`/orc-aftermath`** | Did what we shipped hold up? Graded from the repository's own future: churn, reverts, deleted tests, broken promises. **Churn is a signal, never a verdict**, and it never names a person. | [see it](mock-run/orc-aftermath.md) |
292
293
  | **`/orc-budget`** | What a run costs, in the unit you are billed in. A **token vector** — fresh input, cache write, cache read, output, never blended — shown four ways: tokens, dollars, percent of your 5-hour window, and context risk. Needs a plan, not a sentence. | [see it](mock-run/orc-budget.md) |
@@ -575,7 +576,7 @@ a current audit: [EVAL-REPORT.md](EVAL-REPORT.md).
575
576
  **Full history: [CHANGELOG.md](CHANGELOG.md)** — or `orc changelog`, which prints
576
577
  only what is newer than the version you have.
577
578
 
578
- ### v1.4.2 - the panel that stops reloading, and the fields you could not read back _(2026-09-05)_
579
+ ### v1.5.0 - the lane that runs the test _(2026-09-07)_
579
580
 
580
581
  **Still on the unscoped `orc` package?** Do this once first - your `orc upgrade`
581
582
  is the pre-v0.56.0 one and cannot install itself. Full detail in the CAUTION at
@@ -587,50 +588,49 @@ the top of this file.
587
588
 
588
589
  **Do not use `npm i -g -f`.** Full detail in v0.56.0 below.
589
590
 
590
- Four more defects in `orc ui` ▸ **CLI Hook Interface**. Three were the same
591
- defect wearing three faces.
592
-
593
- **Staging a change reloaded the whole panel** - every staged op re-entered the
594
- router, so four endpoints were refetched and everything was rebuilt from a
595
- skeleton. That made a staged change look like an applied one, and it left the
596
- open editor showing values from before the change you had just made: you picked
597
- a shape and nothing moved. Nothing is fetched now until something actually moves
598
- the disk; a staged op repaints from cache with **zero requests**, keeps your
599
- scroll position, and the open editor repaints with it - caret and all.
600
-
601
- **And the fields could not be read back.** `orc statusline show --json` emitted
602
- twelve of the twenty-four fields a part can carry, so `case`, `prefix`,
603
- `min_cols`, `precision` and seven more were written to disk correctly and then
604
- were invisible to the panel that wrote them. Every field ships now, plus
605
- `authored`, so a control can say **which values are yours** rather than
606
- inherited. `--json is not a summary`, found again.
607
-
608
- **Six parts per line, not five.** **The dropdown nobody could read** turned out
609
- to be a panel with no colours at all: `hookui.css` was written against four CSS tokens that do not
610
- exist, so every one of those declarations was silently dropped.
611
-
612
- **The preview is drawn as a terminal now** - a window of the stated width with a
613
- column ruler - and `orc statusline preview` takes `--theme` and `--glyphs` as a
614
- **render-only** override, so a new drawer shows the same bar under all four
615
- colour sets and all seven symbol sets. Picking a colour set from its name is a
616
- guess; picking it from its picture is a decision.
617
-
618
- **And the sixth part still reset the bar to the default**, because the cap was in
619
- three places: the hook re-checks the compiled file with a cheap shape guard of
620
- its own, and that guard held its own `5` — and counted spacers, which the
621
- validator never has. The cap now travels on the lock file and the compiler marks
622
- each structural item, so one cap and one counting rule serve all three readers.
623
-
624
- **And a name you typed sometimes went nowhere.** Seven of the thirty-five shapes
625
- draw a name; the other twenty-eight ignore it, which is the design — a bar with a
626
- word in front of it is a different shape. The Name box was offered on all
627
- thirty-five anyway. Each renderer now publishes the fields it **uses**, and the
628
- editor greys out what this shape ignores, keeping the slot and naming the shapes
629
- that do.
630
-
631
- **And it still blinked with the network tab empty:** `hkPaint` replaces every
632
- child, and the stylesheet faded each one in on a stagger. Entrance animations are
633
- off from the second paint onward.
591
+ Every other testing surface in ORC **writes** tests. `/orc-test` **runs** them.
592
+
593
+ It points at a running API - yours, on your laptop, or one you were given
594
+ permission to touch - sends real requests, writes down what came back, and
595
+ stops.
596
+
597
+ > **The CLI executes and measures. The model designs and interprets.**
598
+ > A model never sends a request. The CLI never decides what a response means.
599
+
600
+ That split is what makes the report worth reading: a number in it was measured
601
+ by a program, and a sentence in it was written by a model that only ever saw
602
+ evidence on disk.
603
+
604
+ **The free pass runs first.** `orc test surface` reads your repository and the
605
+ target's own spec document for zero model tokens, and the **code-vs-live diff**
606
+ falls out of it - a route that answers at the target and is in **no file in your
607
+ repository** is surface nobody reviews and nobody patches. With no spec at the
608
+ target it reads **NOT MEASURED, with the reason**, because an empty list there
609
+ would say "no shadow APIs", which is a claim nobody made.
610
+
611
+ **The security tier is a closed set** - the OWASP API Top 10 (2023), and all ten
612
+ rows render in every state. A category ORC could not measure says `UNCHECKABLE`,
613
+ keeps its slot, and **never becomes a pass**. It detects and never exploits.
614
+
615
+ **When your app is broken it stops.** It finds the start command, sees the
616
+ process is alive, reads the exact line in the log - and will not open that file.
617
+
618
+ **A red happy path stops the ladder**, because a 500 on every request will
619
+ "prove" a dozen vulnerabilities that are one bug. A **429 is a result** - it
620
+ means rate limiting works, so ORC backs off rather than pushing through. Every
621
+ credential is replaced **before the bytes reach disk**. A finding that cannot
622
+ point at evidence on disk is **dropped by name**. A flake is **recorded, never
623
+ retried away**.
624
+
625
+ **`orc ui` ▸ Test** renders all of it and works out none of it - and `orc test
626
+ run` is a command you **copy**, never a button: a page that can start a scan
627
+ against a live host is a page that can start one by accident.
628
+
629
+ **And one bug that was not in this lane.** Writing the tests isolated a real
630
+ one: `orc ui` compressed its API answers but not its static files, guarded by a
631
+ comment reading *"No asset is over 64 KiB today"* that had been false for two
632
+ releases. Over a Windows loopback socket a 138 KB panel script loses its tail
633
+ roughly one time in six. Both paths share one encoder now.
634
634
 
635
635
  Full detail in [CHANGELOG.md](CHANGELOG.md).
636
636