@erclx/canon 5.76.0 → 5.78.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.
- package/CHANGELOG.md +33 -0
- package/claude/.claude-plugin/plugin.json +1 -1
- package/claude/skills/auto-ship/references/ui-checklist.md +9 -1
- package/claude/skills/ci-workflow/REQUIREMENT.md +8 -2
- package/claude/skills/ci-workflow/SKILL.md +3 -0
- package/claude/skills/code-craft/REQUIREMENT.md +1 -1
- package/claude/skills/code-craft/SKILL.md +7 -0
- package/claude/skills/code-craft/references/adopted.md +8 -0
- package/claude/skills/pr-evidence/SKILL.md +6 -1
- package/claude/skills/pr-evidence/references/evidence.md +1 -0
- package/claude/skills/pr-evidence/references/reel.md +9 -1
- package/claude/skills/review-craft/references/ui.md +13 -1
- package/claude/skills/review-pr/references/body-variants.md +2 -0
- package/claude/skills/review-pr/references/close-out.md +2 -0
- package/claude/skills/review-pr/references/post.md +1 -0
- package/claude/skills/review-ui/REQUIREMENT.md +1 -0
- package/claude/skills/review-ui/SKILL.md +2 -2
- package/claude/skills/review-ui/references/driving.md +32 -4
- package/claude/skills/review-ui/references/post.md +6 -2
- package/claude/skills/role-orchestrator/SKILL.md +2 -2
- package/claude/skills/role-orchestrator/references/orchestrator-output.md +24 -1
- package/claude/skills/role-orchestrator/references/orchestrator-poll.md +3 -2
- package/claude/skills/role-orchestrator/references/orchestrator-review-dispatch.md +35 -4
- package/claude/skills/role-orchestrator/references/orchestrator-reviewer-launch.md +1 -1
- package/claude/skills/role-worker/SKILL.md +1 -0
- package/claude/skills/test-craft/SKILL.md +1 -0
- package/claude/skills/ui-checklist/REQUIREMENT.md +1 -1
- package/claude/skills/ui-checklist/SKILL.md +2 -1
- package/claude/skills/ui-craft/references/capture.md +16 -0
- package/claude/skills/ui-film/REQUIREMENT.md +2 -2
- package/claude/skills/ui-film/SKILL.md +6 -1
- package/claude/skills/ui-film/references/compose-craft.md +68 -11
- package/claude/skills/ui-film/references/config.md +2 -2
- package/claude/skills/ui-film/references/handoff.md +1 -1
- package/claude/skills/ui-film/references/harness.md +71 -0
- package/claude/skills/ui-film/references/take-craft.md +42 -17
- package/docs/agents/targets.md +3 -1
- package/docs/workflow/operating-model.md +6 -5
- package/docs/workflow/visual-design-workflow.md +2 -1
- package/governance/ledger/skills/code-craft/SKILL.md +9 -0
- package/governance/ledger/skills/test-craft/SKILL.md +1 -0
- package/governance/ledger/skills/ui-craft/capture.md +18 -5
- package/package.json +5 -4
- package/src/commands/pr.ts +117 -31
- package/src/commands/take.ts +12 -1
- package/src/commands/targets.ts +11 -1
- package/src/design/components.ts +5 -107
- package/src/design/favicon.ts +21 -17
- package/src/design/render.ts +9 -27
- package/src/design/template.ts +42 -0
- package/src/design/templates/favicon.svg +17 -0
- package/src/design/templates/hand-drawn-figure.css +54 -0
- package/src/design/templates/preview.html +27 -0
- package/src/design/templates/scrollbar.css +29 -0
- package/src/design/templates/status.css +24 -0
- package/src/gate/embedded.ts +400 -0
- package/src/gate/stages.ts +8 -0
- package/src/pr/evidence.ts +43 -4
- package/src/pr/frames.ts +1 -6
- package/src/pr/lift.ts +77 -9
- package/src/pr/rest.ts +2 -0
- package/src/pr/review-scope.ts +28 -0
- package/src/pr/review-state.ts +5 -5
- package/src/pr/waiver.ts +45 -0
- package/src/take/camera.ts +337 -208
- package/src/take/film.ts +7 -1
- package/src/take/log.ts +43 -2
- package/src/take/perform.ts +85 -13
- package/src/take/plan.ts +26 -5
- package/src/take/reel.ts +30 -5
- package/src/take/screencast.ts +110 -3
- package/src/take/stepper.ts +24 -4
- package/src/targets/registry.ts +99 -14
- package/src/targets/resolve.ts +3 -1
- package/tooling/astro/configs/card.config.mjs +4 -0
- package/tooling/astro/configs/scripts/check-card-exclusion.sh +7 -2
- package/tooling/astro/reference.md +2 -1
- package/tooling/web/configs/.github/workflows/readme-screenshot.yml +3 -1
- package/tooling/web/configs/.github/workflows/verify.yml +5 -2
- package/tooling/web/configs/scripts/install-playwright-deps.sh +52 -0
- package/tooling/web/reference.md +5 -0
- package/src/commands/fixtures/gh.sh +0 -64
- package/src/take/fixtures/busy.html +0 -107
- package/src/take/fixtures/fade.html +0 -49
- package/src/take/fixtures/fetch.html +0 -38
- package/src/take/fixtures/input.html +0 -138
- package/src/take/zoom/NOTICE.md +0 -45
- package/src/take/zoom/math-utils.ts +0 -69
- package/src/take/zoom/region-utils.ts +0 -55
- package/src/take/zoom/spring.ts +0 -133
package/CHANGELOG.md
CHANGED
|
@@ -1,5 +1,38 @@
|
|
|
1
1
|
# Changelog
|
|
2
2
|
|
|
3
|
+
## [5.78.0](https://github.com/erclx/canon/compare/v5.77.0...v5.78.0) (2026-11-04)
|
|
4
|
+
|
|
5
|
+
|
|
6
|
+
### Features
|
|
7
|
+
|
|
8
|
+
* **capture:** owe a case for every added or altered rendered state ([#2876](https://github.com/erclx/canon/issues/2876)) ([e13daa2](https://github.com/erclx/canon/commit/e13daa25182da60b0654725326fd14d07f56c69d))
|
|
9
|
+
* **gate:** keep long pages, stylesheets, and scripts out of strings ([#2883](https://github.com/erclx/canon/issues/2883)) ([44ca538](https://github.com/erclx/canon/commit/44ca538cbcb982bc10b0964807e8ea319df5dc17))
|
|
10
|
+
* **orchestrate:** check painted pull requests for proof before review ([#2877](https://github.com/erclx/canon/issues/2877)) ([403a80d](https://github.com/erclx/canon/commit/403a80dd0ada3913f4bb7dac1336fc483b53c6e1))
|
|
11
|
+
* **pr:** bind the UI review only on a drivable checklist box ([#2880](https://github.com/erclx/canon/issues/2880)) ([3027274](https://github.com/erclx/canon/commit/3027274a1d97ec0c8016157f7278fc8ff30b4916))
|
|
12
|
+
* **pr:** refuse a lift on a painted path with no capture or waiver ([#2873](https://github.com/erclx/canon/issues/2873)) ([c05036e](https://github.com/erclx/canon/commit/c05036e2929572cd680a9ddc62e4d7e408b55b3a))
|
|
13
|
+
* **take:** align screencast moves to frames and calibrate the lag ([#2882](https://github.com/erclx/canon/issues/2882)) ([5f274b8](https://github.com/erclx/canon/commit/5f274b877a84496831f3db19917b0127aca3ad94))
|
|
14
|
+
* **take:** pace each press and time every zoom to a glide ([#2875](https://github.com/erclx/canon/issues/2875)) ([6319458](https://github.com/erclx/canon/commit/63194586f6e8e0a5566df872a5fbe4197ef7c09a))
|
|
15
|
+
* **ui-film:** add the film craft a launch film reshoot needed ([#2878](https://github.com/erclx/canon/issues/2878)) ([94ac7fc](https://github.com/erclx/canon/commit/94ac7fc2b8e6a3cdf2da67d13dc7d76fb850bc1d))
|
|
16
|
+
|
|
17
|
+
|
|
18
|
+
### Bug Fixes
|
|
19
|
+
|
|
20
|
+
* **take:** clear the cap timers so the command exits with filming ([#2879](https://github.com/erclx/canon/issues/2879)) ([8fefa21](https://github.com/erclx/canon/commit/8fefa21dbf357ab32c688a4dcc2e1c688c25cab2))
|
|
21
|
+
* **take:** encode the reel lossless so a fade leaves no ghost ([#2881](https://github.com/erclx/canon/issues/2881)) ([5cede29](https://github.com/erclx/canon/commit/5cede2913953c3dd041f2fe505565a036c0bb15b))
|
|
22
|
+
|
|
23
|
+
## [5.77.0](https://github.com/erclx/canon/compare/v5.76.0...v5.77.0) (2026-10-31)
|
|
24
|
+
|
|
25
|
+
|
|
26
|
+
### Features
|
|
27
|
+
|
|
28
|
+
* **targets:** keep only real projects in the target index ([#2867](https://github.com/erclx/canon/issues/2867)) ([340cbff](https://github.com/erclx/canon/commit/340cbff8edda3987af6d4933aa27391e07b312a2))
|
|
29
|
+
* **tooling:** bound and retry the shipped playwright installs ([#2865](https://github.com/erclx/canon/issues/2865)) ([842d5f9](https://github.com/erclx/canon/commit/842d5f957602136d8bbbdfba524fbba1340df76a))
|
|
30
|
+
|
|
31
|
+
|
|
32
|
+
### Bug Fixes
|
|
33
|
+
|
|
34
|
+
* **tooling:** turn off the card toolbar and narrow the exclusion check ([#2864](https://github.com/erclx/canon/issues/2864)) ([188c1e9](https://github.com/erclx/canon/commit/188c1e950c83cd00ad22e07c43d5232bf01e6ad8))
|
|
35
|
+
|
|
3
36
|
## [5.76.0](https://github.com/erclx/canon/compare/v5.75.0...v5.76.0) (2026-10-31)
|
|
4
37
|
|
|
5
38
|
|
|
@@ -14,10 +14,18 @@ The chain continues to Step 6 here in every run, dispatched or hand-run, since t
|
|
|
14
14
|
Count two things in `.canon/tmp/handoff/ui-checklist/<slug>.md` at the main worktree root:
|
|
15
15
|
|
|
16
16
|
- `<N>`, the `- [ ]` lines
|
|
17
|
-
- `<M>`, how many of those
|
|
17
|
+
- `<M>`, how many of those carry `(taste)` among their trailing markers
|
|
18
18
|
|
|
19
19
|
Hold both until the Output block. `pr-evidence` removes the file once it posts the evidence comment, so a count taken after Step 6 reads nothing.
|
|
20
20
|
|
|
21
|
+
## Owed fixture states
|
|
22
|
+
|
|
23
|
+
Settle each state the checklist names before Step 6, since a box the driver cannot reach opens the UI review.
|
|
24
|
+
|
|
25
|
+
- Add the state to the drive fixture for each box ending in `(needs fixture)`, then drop the marker from the box
|
|
26
|
+
- Confirm every state the checklist names has a capture case, per the `canon:ui-craft` capture reference, and add the missing ones
|
|
27
|
+
- A project with no `canon/config/app-drive.toml` takes the setup inline on the box instead of a fixture file
|
|
28
|
+
|
|
21
29
|
## Reading the counts into the closing block
|
|
22
30
|
|
|
23
31
|
The Output block's second line takes both counts. When every box is a taste box, `<N>` and `<M>` match and the boxes are owed to the operator alone, so say the operator and drop the UI reviewer clause.
|
|
@@ -9,12 +9,18 @@ description: Scope boundary for pipeline structure against job contents, and the
|
|
|
9
9
|
|
|
10
10
|
Without this skill, a session chains jobs with `needs` to express reading order rather than a data dependency, so the pipeline costs the sum of its jobs. The same session splits a one-minute gate into parallel jobs, each repaying checkout, install, and toolchain setup, so the gate gets slower while reporting no earlier.
|
|
11
11
|
|
|
12
|
-
The rest surface as flakes
|
|
12
|
+
The rest surface as flakes or stalls:
|
|
13
|
+
|
|
14
|
+
- A moving action ref changes under the project, and a static cache key serves a stale toolchain
|
|
15
|
+
- Artifacts never expire, and a broad default token grants unneeded writes
|
|
16
|
+
- A missing manual trigger leaves a run reproducible only by pushing a commit
|
|
17
|
+
- A Linux-only pin flags a supported macOS job as a departure
|
|
18
|
+
- A Playwright install calling apt directly hangs on a stalled mirror and, with no step bound, holds the runner until the six-hour job default
|
|
13
19
|
|
|
14
20
|
## Must
|
|
15
21
|
|
|
16
22
|
- A job is gated only on a data dependency or a cost that justifies the wait, and checks sharing setup stay in one job until a run log puts the gate past roughly two minutes
|
|
17
|
-
- Every action is pinned to a tag that cannot cross a major version,
|
|
23
|
+
- Every action is pinned to a tag that cannot cross a major version, every cache is keyed on the version of what it caches, and every Playwright install is bounded and retried
|
|
18
24
|
- Every workflow carries a manual trigger beside its primary one, except one that commits back
|
|
19
25
|
- The token defaults to read-only, with a write scope granted only on the job that needs it, and artifact upload is bounded to failures and expires
|
|
20
26
|
- A job runs on Linux unless the project states a platform for a layer that differs by platform
|
|
@@ -60,6 +60,8 @@ Linux stays the default. A job leaves it only for a layer whose result differs b
|
|
|
60
60
|
- Use `oven-sh/setup-bun@v2` with `bun-version: latest`.
|
|
61
61
|
- Install with `bun install --frozen-lockfile`.
|
|
62
62
|
- Cache Playwright browsers keyed on the Playwright version string, never a static key.
|
|
63
|
+
- Bound each Playwright install step, 10 minutes on the system packages and 5 on the browser. A stalled apt mirror hangs rather than fails, and an unbounded job waits out the six-hour default.
|
|
64
|
+
- Install the system packages through a script that kills and retries a stalled attempt, never a direct `install-deps` or `--with-deps`, since a bound alone turns the hang red.
|
|
63
65
|
|
|
64
66
|
## Commit-back
|
|
65
67
|
|
|
@@ -106,3 +108,4 @@ Before responding, also verify:
|
|
|
106
108
|
Before responding, also verify:
|
|
107
109
|
|
|
108
110
|
- No `run:` step passes five lines or carries more than one exit-or-output guard, a loop, a trap, or a function. A step that does calls a script, with its inputs as arguments or `env`.
|
|
111
|
+
- Every Playwright install step carries `timeout-minutes`, and the system packages install through a retried script.
|
|
@@ -16,7 +16,7 @@ Agents fail there in recorded ways. They copy where reuse belonged, spread one c
|
|
|
16
16
|
- Open with the change test, naming the change most likely to come next and counting what it would touch before choosing a shape
|
|
17
17
|
- State depth as rules a session can act on, covering a unit's interface being simpler than its work, inlined pass-throughs, and splitting by the decision hidden
|
|
18
18
|
- State each tension as when one side wins, such as one place for knowledge against coupling two things that only look alike
|
|
19
|
-
- State
|
|
19
|
+
- State what a unit keeps out of itself, being the clock, environment, and randomness, transport and storage code in a business rule, and a long page, stylesheet, or script held in a string
|
|
20
20
|
- Close with the agent failure modes as checks on the session's own diff, with excuses, red flags, a checklist, and the external sources adopted and declined with the reason for each
|
|
21
21
|
|
|
22
22
|
## Must not
|
|
@@ -55,6 +55,13 @@ A pattern earns its indirection only when the problem it solves is present now.
|
|
|
55
55
|
- Keep business rules free of transport and storage code, so a rule can be read and tested without a request or a database.
|
|
56
56
|
- Skip ports and adapters for an application that only reads and writes records. The layers cost more than the change they protect against.
|
|
57
57
|
|
|
58
|
+
## Give another language its own file
|
|
59
|
+
|
|
60
|
+
- Put a page, a stylesheet, or a script past five lines in its own file with its language's extension. A string reaches no formatter or linter, and the next session copies it from its neighbor.
|
|
61
|
+
- Put a script that branches in its own file at any length, since a branch is logic no test reads as its own input.
|
|
62
|
+
- Keep a template that interpolates data in code, since it is code generating output. Count only its static lines, so one interpolation cannot exempt a long page.
|
|
63
|
+
- Keep a short string inline when it is the input under test, so a reader sees it beside the assertion that reads it.
|
|
64
|
+
|
|
58
65
|
## Check your own diff
|
|
59
66
|
|
|
60
67
|
Agents fail at writing time in recorded ways. Read the diff for each before calling it done.
|
|
@@ -67,6 +67,14 @@ Martin Fowler, [Beck Design Rules](https://martinfowler.com/bliki/BeckDesignRule
|
|
|
67
67
|
|
|
68
68
|
Martin Fowler, Inversion of Control Containers and the Dependency Injection pattern, hands a component what it depends on rather than letting it find it. Adopted as the hidden-inputs rule for the clock, the environment, randomness, and globals, without any container.
|
|
69
69
|
|
|
70
|
+
## Adopted for embedded languages
|
|
71
|
+
|
|
72
|
+
### Inline resource
|
|
73
|
+
|
|
74
|
+
Gerard Meszaros, xUnit Test Patterns, names putting a file's contents into a string in the test as Inline Resource and recommends it over the Mystery Guest a separate file creates. The same page warns that a large resource signals an Eager Test.
|
|
75
|
+
|
|
76
|
+
Adopted as both sides of the embedded-file rule. A short input under test stays inline, and a long page, stylesheet, or script leaves for its own file. The five-line threshold mirrors the limit the `ci-workflow` skill sets on an inline `run:` step, so one number covers both.
|
|
77
|
+
|
|
70
78
|
## Adopted for agent failure modes
|
|
71
79
|
|
|
72
80
|
Birgitta Böckeler, The role of developer skills in agentic coding, 2025, and How far can we push AI autonomy in code generation?, 2025.
|
|
@@ -52,7 +52,12 @@ The no-local-preview and no-reel lines also land on the evidence comment, throug
|
|
|
52
52
|
|
|
53
53
|
### The uncaptured line
|
|
54
54
|
|
|
55
|
-
Collect `📸 <N> painted paths changed with no evidence capture. Recapture and push.` when the evidence record lists `uncaptured` paths, with `<N>` its count.
|
|
55
|
+
Collect `📸 <N> painted paths changed with no evidence capture. Recapture and push.` when the evidence record lists `uncaptured` paths, with `<N>` its count. It never stops the run. No step here can take a capture, so the gap reaches the thread and the lift by other routes:
|
|
56
|
+
|
|
57
|
+
- The evidence call writes an `**Uncaptured:**` line naming each path on the marked comment, posting it even on a head with no other news
|
|
58
|
+
- The line drops on the first render after a capture lands or a reel filmed at the head renders beside it
|
|
59
|
+
- `canon pr lift` refuses `painted-uncaptured` until a capture, a reel at the head, or a waiver in the newest review pass covers every listed path
|
|
60
|
+
- A worker never writes the waiver, since a review is the one surface a worker never posts
|
|
56
61
|
|
|
57
62
|
### The no-local-preview line
|
|
58
63
|
|
|
@@ -150,6 +150,7 @@ rmdir <main-root>/.canon/tmp/handoff/ui-checklist 2>/dev/null || true
|
|
|
150
150
|
|
|
151
151
|
- The `rmdir` is a no-op while another branch's pending checklist sits in the folder, so this step never deletes a handoff not its own
|
|
152
152
|
- `git-followup` re-runs `canon pr evidence` with no `--checklist`, and the verb carries the checklist forward out of the comment it edits
|
|
153
|
+
- Drop a carried checklist with `canon pr evidence <number> --no-checklist --json` and post its `ok` body, never a hand edit, which the next render undoes
|
|
153
154
|
- A tick survives a render at the head its stamp names and is cleared by one at a newer head, so the next UI pass earns it again
|
|
154
155
|
|
|
155
156
|
## Post the preview address
|
|
@@ -36,7 +36,7 @@ Film where motion is the claim. Filter the boxes first, then spend the three bea
|
|
|
36
36
|
|
|
37
37
|
A box is filmable when it asks the reviewer to click, fill, or scroll something and its result is a visible change.
|
|
38
38
|
|
|
39
|
-
- Skip a box
|
|
39
|
+
- Skip a box whose trailing markers hold `(taste)`, in any order, since no driver judges it
|
|
40
40
|
- Skip a box that asks only to look at a state the page opens on, since a screenshot already shows it
|
|
41
41
|
- Skip a negative box, one asserting that something does not happen, such as "no drop line draws", since footage of nothing shows nothing
|
|
42
42
|
|
|
@@ -80,6 +80,14 @@ Branch on the record's `reason`, never on the exit code.
|
|
|
80
80
|
| `over-cap` | Drop `beat` and each beat after it, then film once more. Skip as `over-cap` if `beat` is first or it refuses again |
|
|
81
81
|
| Any other value | Skip under that `reason`, such as `target-missing` with its `beat` |
|
|
82
82
|
|
|
83
|
+
### A skip for a state the fixture lacks
|
|
84
|
+
|
|
85
|
+
A skip whose cause is a state the drive fixture lacks, such as `target-missing` on a control only that state renders, is work the building session owes.
|
|
86
|
+
|
|
87
|
+
- Film a beat from a box carrying `(needs fixture)` only if the state answers, and otherwise skip it as owed
|
|
88
|
+
- Report the owed skip on the evidence comment's `--reel-skip` line and in the closing report, naming the state, the selector, or the setup step the beat needed
|
|
89
|
+
- Never report it as a plain skip, since the next pull request meets the same fixture and skips again
|
|
90
|
+
|
|
83
91
|
## Check each still
|
|
84
92
|
|
|
85
93
|
Open each beat's `still.jpg`, the closing frame the record names in its `still` field, and confirm it shows the state the beat's box describes. This check replaces the operator's approval, so it runs on every reel.
|
|
@@ -36,12 +36,24 @@ canon pr evidence <number> --check --json
|
|
|
36
36
|
|
|
37
37
|
Read the record's `uncaptured` field, never the exit code.
|
|
38
38
|
|
|
39
|
-
- It lists paths: the project keeps captures and this change skipped them. File a
|
|
39
|
+
- It lists paths: the project keeps captures and this change skipped them. File a should-fix naming each path, since `canon pr lift` refuses `painted-uncaptured` until each one is covered.
|
|
40
40
|
- An empty list beside a changed `evidence/` image means the capture exists and the comment fails to show it. File that as a finding too.
|
|
41
41
|
- An empty list with no changed `evidence/` image means the painting file sits outside the painted set, such as a token file. Raise a question naming the path.
|
|
42
42
|
- It is absent: the base keeps no capture, or its tree went unread. Raise a question with no severity, since a project with no capture harness would otherwise take the flag on every styling change.
|
|
43
43
|
- The record refuses: it decides nothing, so take the tree test under the last section instead
|
|
44
44
|
|
|
45
|
+
### Waiving a capture
|
|
46
|
+
|
|
47
|
+
A worker may state why a listed path needs no capture, such as a change to keyboard focus order that no reachable state shows. Accept the exemption only when the diff bears it out, and leave the should-fix standing otherwise.
|
|
48
|
+
|
|
49
|
+
- Write the waiver line in this pass's body, in the form `${CLAUDE_SKILL_DIR}/../review-pr/references/post.md` gives, one line per path
|
|
50
|
+
- Keep it outside any code fence, since the lift skips a fenced line as a quoted sample
|
|
51
|
+
- Copy the path from the record, since the lift matches it only as `uncaptured` spells it
|
|
52
|
+
- Write the reason after the colon, since a line with none waives nothing
|
|
53
|
+
- Restate it in every later pass, a close-out included, since the lift reads only the newest marked pass of each family and never a reply
|
|
54
|
+
|
|
55
|
+
### A recapture of the design
|
|
56
|
+
|
|
45
57
|
A recapture under `canon/design/` redraws the accepted design rather than the built app, so it never stands in for an evidence capture. The verb leaves those paths out of `uncaptured`, and a pass clears a painted change on the evidence comment alone, however many design references beside it were redrawn.
|
|
46
58
|
|
|
47
59
|
Stop reading this reference once the flag is raised, since there is nothing to open. Otherwise continue with the comment in hand.
|
|
@@ -63,6 +63,8 @@ A pass carrying nothing at all takes `## Review closed` and a short body, with t
|
|
|
63
63
|
- A prior finding this pass withdrew leaves the count, and its line names the fact that settled it rather than a fix, per the withdrawal rule below
|
|
64
64
|
- A closing remark that fits no prior finding, such as a ticked Testing box, takes one line of its own after them
|
|
65
65
|
|
|
66
|
+
Each capture waiver this pass still accepts takes its `- **Waived capture:**` line last, unfenced. The lift reads waivers from the newest pass alone, so a close-out that drops one withdraws it.
|
|
67
|
+
|
|
66
68
|
### Only minors
|
|
67
69
|
|
|
68
70
|
A pass carrying only minors is an ordinary finding-carrying pass, so it takes the open heading and the full shape, since neither short line reports the minors. A pass carrying only Testing questions or only an unanswered reviewer request takes the same route. Keep whichever scope sentence the pass owes on the summary line:
|
|
@@ -19,6 +19,8 @@ gh api --paginate 'repos/{owner}/{repo}/pulls/<number>/reviews?per_page=100' --j
|
|
|
19
19
|
|
|
20
20
|
Write the replacement body to `<body-file>`, the name `post.md` already derived at the top of Step 4. Keep the heading and the footer, and name what this pass covered on the scope line in place of what the old one covered.
|
|
21
21
|
|
|
22
|
+
Carry every `- **Waived capture:**` line the standing close-out holds into the replacement when this pass still accepts it. The lift reads waivers from the newest pass alone, so a rewrite that drops one withdraws it and the lift refuses `painted-uncaptured` again.
|
|
23
|
+
|
|
22
24
|
- Derive that name the same way whichever path reached here, since the guard reads `<prior-heading>` alone and a repeated head resolves the third segment as usual
|
|
23
25
|
- The folder then gains a record of every covered head rather than losing the one the standing comment named
|
|
24
26
|
|
|
@@ -65,6 +65,7 @@ X critical, Y should-fix, Z minor. Reviewed against project docs and the board.
|
|
|
65
65
|
- Fix: the change
|
|
66
66
|
- **minor** ([lines 30-34](<repo-url>/blob/<headRefOid>/path/to/file.ext#L30-L34)): what breaks, in one sentence.
|
|
67
67
|
- Fix: the change
|
|
68
|
+
- **Waived capture:** `src/client/board/overlay.tsx`: keyboard focus order only, no visible change in any reachable state
|
|
68
69
|
|
|
69
70
|
<details>
|
|
70
71
|
<summary>Review focus, N checked</summary>
|
|
@@ -16,6 +16,7 @@ A model asked to drive a checklist also drifts. It judges a taste box the operat
|
|
|
16
16
|
- Every checklist box is driven in the running app and gets one verdict, pass or fail with the value quoted, needs eyes for a taste box, or not driven with the reason
|
|
17
17
|
- The checklist and address come from the evidence record rather than the diff, and only a build of the head the verdict names is driven
|
|
18
18
|
- An unreachable address reports not driven rather than fail, a box no commit can settle leaves the review closed, and a pass that drove no box never reads as closed
|
|
19
|
+
- A box not driven for a state the drive fixture lacks is the exception, since the building session can add that state, so it opens the review. A state no fixture file can hold stays closed.
|
|
19
20
|
- The review posts as its own pull request review under `## UI review` while anything is owed and `## UI review closed` once nothing is, ending on a marker naming the head it drove
|
|
20
21
|
- The pass drives a pinned browser under its own named session and sweeps only console errors, overflow, and the focus, details, and axe probes, opening on an axe finding the CLI marks as gating
|
|
21
22
|
|
|
@@ -84,7 +84,7 @@ Take the first rung that answers, testing each with `curl -s -o /dev/null -w '%{
|
|
|
84
84
|
2. The `local` address off the record.
|
|
85
85
|
3. An address the launch names.
|
|
86
86
|
|
|
87
|
-
When the hosted rung answers, read `${CLAUDE_SKILL_DIR}/references/hosted-preview.md` to check it was built from the head before driving. A pass on the local rung or a launch-named address skips
|
|
87
|
+
When the hosted rung answers, read `${CLAUDE_SKILL_DIR}/references/hosted-preview.md` to check it was built from the head before driving. A pass on the local rung or a launch-named address skips that check, and every rung then takes the config's `access` per `## The access join` in `${CLAUDE_SKILL_DIR}/references/driving.md`.
|
|
88
88
|
|
|
89
89
|
### Unverified and unanswered addresses
|
|
90
90
|
|
|
@@ -112,7 +112,7 @@ Read `${CLAUDE_SKILL_DIR}/references/driving.md` on reaching this step for how a
|
|
|
112
112
|
- Make each box its own item on the session's task list, and tick it as its verdict lands. Skip it on a host that offers no list tool.
|
|
113
113
|
- Give every box exactly one verdict, in checklist order, since skipping a box silently reads the same as passing it
|
|
114
114
|
- Drive a box the pass could not place on a route or a width from the opened address at 1440 wide, and name the guess in the verdict
|
|
115
|
-
- Never judge a box
|
|
115
|
+
- Never judge a box whose trailing markers hold `(taste)`, in any order. Drive to the state, capture both themes, and mark it needs eyes.
|
|
116
116
|
- Drive a ticked box the same as an unchecked one, at any head, since a tick is a claim this pass exists to check
|
|
117
117
|
|
|
118
118
|
### Push a frame
|
|
@@ -1,25 +1,36 @@
|
|
|
1
1
|
---
|
|
2
2
|
title: Drive each box
|
|
3
|
-
description: Step
|
|
3
|
+
description: The access join Step 3 of review-ui makes, then Step 5, which maps a checklist line to browser calls, reads each value off the page, and gives the box one of four verdicts with the evidence that verdict carries
|
|
4
4
|
---
|
|
5
5
|
|
|
6
6
|
# Drive each box
|
|
7
7
|
|
|
8
8
|
Step 5 of `review-ui`. The browser is open at the address Step 3 picked, under the session Step 4 named. Every call below goes through `canon browser -s=<project>-<number>`, shortened here to `pw`.
|
|
9
9
|
|
|
10
|
+
## The access join
|
|
11
|
+
|
|
12
|
+
Step 3 reads this section once a rung answers. Read `access` from `canon/config/app-drive.toml` at the main worktree root, since a page needing a write link, a signed-in route, or a demo token shows its start state only behind it. An absent file or key opens the rung as it stands.
|
|
13
|
+
|
|
14
|
+
- Join a value starting with `/` to the rung, and take a full address as it stands. Step 4 opens the joined address alone.
|
|
15
|
+
- Every later route joins to the bare rung, never the joined address, since an `access` holding a query would swallow the path
|
|
16
|
+
- Test the rung bare in Step 3, so the `curl` spends no single-use link before the drive
|
|
17
|
+
- Take no `access` value from the launch brief, since the config is the one source
|
|
18
|
+
- Never print the joined address in a post, a frame, or a message, since `access` may carry a token. Name the rung and say the config's `access` was joined.
|
|
19
|
+
|
|
10
20
|
## Reading a line
|
|
11
21
|
|
|
12
22
|
A box written to the drivable format reads:
|
|
13
23
|
|
|
14
24
|
```plaintext
|
|
15
|
-
- [ ] <route>[, <width>]: <verb> <target> → <expected result>[ (taste)][ (local only)]
|
|
25
|
+
- [ ] <route>[, <width>]: <verb> <target> → <expected result>[ (taste)][ (local only)][ (needs fixture)]
|
|
16
26
|
```
|
|
17
27
|
|
|
18
|
-
- **Route.** A path goes through `pw goto <
|
|
28
|
+
- **Route.** A path goes through `pw goto <rung><path>`, the rung before the access join. A control name, or "from the page the app opens on", is reached by clicking from the opened address.
|
|
19
29
|
- **Width.** `pw resize <width> 900` before acting. A box naming no width is driven at 1440.
|
|
20
30
|
- **Verb.** The action the driver performs: `click`, `fill`, `press`, `hover`, a scroll through `eval` of `scrollIntoView`, or a resize.
|
|
21
31
|
- **`(taste)`.** The result is a judgment of look or feel. Capture, never judge.
|
|
22
32
|
- **`(local only)`.** The state needs something a hosted preview cannot reach. On a hosted address the box is not driven, naming the marker as the reason.
|
|
33
|
+
- **`(needs fixture)`.** The drive fixture lacks the state. Drive the box if the state now answers, and otherwise it is not driven for a cause on the branch, as the verdicts below state.
|
|
23
34
|
|
|
24
35
|
A box written before that format may carry no route, no width, and a verb such as "read" or "look at". Drive it anyway: take the opened address as the route and 1440 as the width, turn the verb into the nearest action, and name each guess in the verdict's evidence.
|
|
25
36
|
|
|
@@ -51,13 +62,30 @@ Each box takes exactly one, keyed here by the state it answers.
|
|
|
51
62
|
- The evidence is the value read, quoted, such as `scrollWidth 436 against clientWidth 320`.
|
|
52
63
|
- **pass or fail, frame.** The result has a stated criterion only an image settles.
|
|
53
64
|
- The evidence is the matching evidence stem or the pushed frame's link, inline under the failed box's heading, and what the frame shows, in words.
|
|
54
|
-
- **needs eyes.** The box
|
|
65
|
+
- **needs eyes.** The box's trailing markers hold `(taste)`, in any order.
|
|
55
66
|
- The evidence is the dark and the light shot as a pair, each the matching evidence stem or a pushed frame's link, and what the frames showed, with nothing about whether it looks right.
|
|
56
67
|
- **not driven.** The state could not be reached.
|
|
57
68
|
- The evidence is the reason, such as an unreachable address, a `(local only)` box on a hosted preview, or a target the snapshot does not hold.
|
|
58
69
|
|
|
59
70
|
A fail names what was expected beside what was read. A not driven never reads as a fail, since it says the pass could not look rather than that the page is wrong. Its reason says whether the cause sits on the page or off it, since only a cause on the page opens the heading Step 7 picks.
|
|
60
71
|
|
|
72
|
+
### A state the fixture lacks
|
|
73
|
+
|
|
74
|
+
A box the pass could not drive because the drive fixture holds no such state is a cause on the branch, never a skip. The building session owes the state, and no other session can add it.
|
|
75
|
+
|
|
76
|
+
- Name the cause as a missing fixture state, with the state to add and the selector or setup step the box needs
|
|
77
|
+
- Count it as not driven, and never as a fail, since the page may be right
|
|
78
|
+
- An address that did not answer stays a cause off the branch, and a `(local only)` box on a hosted address does too
|
|
79
|
+
- A state no fixture file can hold is the exit, such as one a project with no `canon/config/app-drive.toml` cannot reach inline. Name it a cause off the branch, so the review stays closed.
|
|
80
|
+
|
|
81
|
+
### A refused address
|
|
82
|
+
|
|
83
|
+
A permission rule or a classifier that denies the call opening or driving an address leaves the box not driven, for a cause off the branch. Name the refusal as the host worded it and the call it denied.
|
|
84
|
+
|
|
85
|
+
- Never retry through another route, being a second address, a different browser call, or a direct fetch, since the refusal is a decision about this pass rather than a fault to work around
|
|
86
|
+
- A refused opening call drives no box, so the pass posts open with the refusal as its cause line, per `${CLAUDE_SKILL_DIR}/references/post.md`
|
|
87
|
+
- Name the address by its rung and never print the joined `access`, which may carry a token
|
|
88
|
+
|
|
61
89
|
### Which image a verdict carries
|
|
62
90
|
|
|
63
91
|
A pass or fail resting on a frame carries one image at most, and never one the worker's evidence already shows. A needs-eyes box carries the pair, dark and light, since a taste call is made by comparing them.
|
|
@@ -11,7 +11,10 @@ Step 7 of `review-ui`.
|
|
|
11
11
|
|
|
12
12
|
The heading reports whether the branch owes anything, the way the code review's does.
|
|
13
13
|
|
|
14
|
-
- `## UI review` when a box failed, the sweep raised a finding Step 6 names, the worktree check read `changed`, a box was not driven for a cause
|
|
14
|
+
- `## UI review` when a box failed, the sweep raised a finding Step 6 names, the worktree check read `changed`, a box was not driven for a cause the branch holds, or the pass drove no box at all.
|
|
15
|
+
|
|
16
|
+
A missing fixture state opens the heading because a commit settles it, being the state the building session adds. That pass reaches `review-address` like a failed box, with the state to add named in the box's Not driven entry. A state no fixture file can hold, which `driving.md` names, is a cause off the branch and leaves the review closed.
|
|
17
|
+
|
|
15
18
|
- `## UI review closed` otherwise.
|
|
16
19
|
|
|
17
20
|
A needs-eyes box leaves the review closed, and so does a box not driven for a cause off the page, such as an address that did not answer or a `(local only)` box on a hosted preview, as long as something else was driven.
|
|
@@ -95,7 +98,7 @@ The post takes the length limits alone, with a box's reason under 350 characters
|
|
|
95
98
|
The body opens on its count line, in that order, so the operator reads what they owe before anything else. The second line carries the address, the head, and the renderer, and says the address was driven unverified when it came from the local rung or the launch.
|
|
96
99
|
|
|
97
100
|
- Drop each section holding no box, along with its heading. The order is fixed as Failed, Changed in the worktree, Needs your eyes, Not driven, then the folded blocks.
|
|
98
|
-
- A box takes exactly one section by its verdict, so a box that fails and also
|
|
101
|
+
- A box takes exactly one section by its verdict, so a box that fails and also carries `(taste)` appears once, under Failed
|
|
99
102
|
- Quote page text in backticks as content, never as the pass's own words
|
|
100
103
|
|
|
101
104
|
### A loopback address
|
|
@@ -104,6 +107,7 @@ A loopback address has `localhost`, `127.0.0.1`, `0.0.0.0`, or `[::1]` as its ho
|
|
|
104
107
|
|
|
105
108
|
- The cause line of a pass that drove no box, and every Not driven entry, name a loopback address it tried as a local preview with its port, such as `a local preview on port 4211`
|
|
106
109
|
- A hosted address posts as written, since it outlives the session, and the close drops it from the evidence comment
|
|
110
|
+
- `<address>` is always the rung before the access join, followed by `behind the config's access` when one was joined, per `## The access join` in `${CLAUDE_SKILL_DIR}/references/driving.md`
|
|
107
111
|
- The evidence comment carries the local link while the pull request is open, for an operator on the same machine
|
|
108
112
|
- `canon pr local --remove` masks a loopback address left on a review's `Driven at` line when the pull request closes
|
|
109
113
|
|
|
@@ -101,9 +101,9 @@ Learning that a PR moved is the mechanical half. Read `${CLAUDE_SKILL_DIR}/refer
|
|
|
101
101
|
A pass posting anything owed reaches the session holding the branch from the reviewer directly, and the re-review request goes straight back to that reviewer, per `role-reviewer` and `role-worker`. Read `${CLAUDE_SKILL_DIR}/references/orchestrator-handback.md` on reaching this step.
|
|
102
102
|
|
|
103
103
|
- This session sends either leg only where a cloud reviewer posted the pass or one side reports the other unreachable
|
|
104
|
-
- Each reviewer runs `canon pr lift
|
|
104
|
+
- Each reviewer's close runs `canon pr lift`, lifting the draft once both reviews close at the head, the evidence settles, the head is fresh, and CI passes
|
|
105
105
|
- Run it yourself when a close message reports a refusal other than the other review being open, or when a cloud reviewer's close posts, per Boundaries below
|
|
106
|
-
- Then the human merges
|
|
106
|
+
- Then the human merges from a line naming its proof, per `${CLAUDE_SKILL_DIR}/references/orchestrator-output.md`. Tell each trailing worker the merged diff touches to run `review-address`.
|
|
107
107
|
|
|
108
108
|
The handback runbook holds how the message is addressed and worded, what to do when no live session holds the branch, and where a worker's reply goes.
|
|
109
109
|
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
---
|
|
2
2
|
title: Orchestrator output formats
|
|
3
|
-
description: The invocation block with its four sections, the three-slot shape every later report opens with, and the rule against a shape for a correction
|
|
3
|
+
description: The invocation block with its four sections, the three-slot shape every later report opens with, the proof a merge line names, and the rule against a shape for a correction
|
|
4
4
|
---
|
|
5
5
|
|
|
6
6
|
Read this on invocation, before reporting the state of play, and again before any later report.
|
|
@@ -70,4 +70,27 @@ Keep the detail below the block and keep it skippable. A decision reached at the
|
|
|
70
70
|
- A rename leaves the launch name matching nothing, so read the current name off `canon sessions list --json` when the line is written
|
|
71
71
|
- `claude rm` takes the id alone, so that line carries the id
|
|
72
72
|
|
|
73
|
+
## The merge line
|
|
74
|
+
|
|
75
|
+
A pull request recommended for merge names the proof its evidence comment carries, beside the merge command, since a lift's `ok` says the gates held and nothing about what anyone could look at.
|
|
76
|
+
|
|
77
|
+
```plaintext
|
|
78
|
+
PR #<n> <title> proof: <screenshots|reel|screenshots and reel|waived|none>
|
|
79
|
+
→ canon pr merge <n>
|
|
80
|
+
```
|
|
81
|
+
|
|
82
|
+
Read the slot off `canon pr evidence <number> --json` at the moment the line is written, branching on the record rather than the exit code.
|
|
83
|
+
|
|
84
|
+
- `screenshots` when the record carries `states`, and `reel` when it carries `reel`
|
|
85
|
+
- `waived` when neither is carried and `canon pr lift <number> --check --json` names every listed path under `waived`, quoting no token from the reason
|
|
86
|
+
- `none` otherwise, and a pull request with no painted path takes no slot at all
|
|
87
|
+
|
|
88
|
+
### An unproven painted pull request
|
|
89
|
+
|
|
90
|
+
A painted pull request whose slot reads `none` is unproven. Report it as unproven, never as ready, whatever the lift returned, and put the missing proof to the operator as a decision.
|
|
91
|
+
|
|
92
|
+
- Painted means the record carries a `checklist`, or the check record lists `uncaptured` paths
|
|
93
|
+
- A project whose base keeps no captures reads `uncaptured` absent, so a checklist with no stills and no reel is still unproven there
|
|
94
|
+
- Send the branch's session back to run `pr-evidence` under the proof check in `orchestrator-review-dispatch.md`, rather than recommending the merge
|
|
95
|
+
|
|
73
96
|
Write no shape for a correction. A correction is a sentence, and a format for admitting error invites ceremony where plainness is the whole value.
|
|
@@ -47,8 +47,9 @@ bun <POLL_SCRIPT> --wait 1200
|
|
|
47
47
|
Act on what the poll printed when it exited, then start it again.
|
|
48
48
|
|
|
49
49
|
- A release pull request, whatever state follows it: report it and stop. Its sweep carries no findings, so no pass is owed. Test this before any rule below, since a release pull request is reported OPENED like any other and would otherwise match that rule first.
|
|
50
|
+
- MOVED, before the rule below: run the review dispatch runbook's proof check on the new head. A head first carrying an uncaptured path, or owing evidence, goes back to its worker and holds the re-review. One first carrying a `drivable` box with no UI reviewer launched takes one now.
|
|
50
51
|
- MOVED or RESPONSE on a pull request already reviewed: when a live local reviewer holds it, report it and stop, since the worker asks that reviewer for the re-review directly. When none does, which a cloud reviewer always leaves, launch a fresh reviewer under the review dispatch runbook of the canon:role-orchestrator skill. Never run the canon:review-pr skill here. Re-reviews read prior..head and gain nothing from waiting.
|
|
51
|
-
- OPENED, or a pull request with no prior review pass: launch its reviewer under the review dispatch runbook of the canon:role-orchestrator skill, and its UI reviewer beside it when the evidence record
|
|
52
|
+
- OPENED, or a pull request with no prior review pass: once that runbook's proof check reads proof, launch its reviewer under the review dispatch runbook of the canon:role-orchestrator skill, and its UI reviewer beside it when the evidence record counts a `drivable` box. Never run the first pass here. A draft counts, since every pull request here opens as one and skipping drafts skips everything.
|
|
52
53
|
- SEEN: report it and stop. A pass already covers that head, whether it arrived out of band or before the poll first saw the pull request, so no review follows.
|
|
53
54
|
- STALLED: read the last pass and report what it carried. The pass has sat open for hours with nothing following it, so a worker mid-task is already ruled out and the dispatch either never went out or the session holding it is gone. Confirm and re-send it under the dispatch rule below, whatever grades the pass carried. Do not re-run a review to correct the heading, since a pass on an unchanged head with no response behind it stops by design.
|
|
54
55
|
- CONFLICT or STALE: send the session holding that branch the rebase handback in the canon:role-orchestrator skill's handback runbook, resolving it the way the handback rule below does. The branch owner rebases, not this session. The poll prints one of the two for a pull request, never both, so it earns one message. The canon pr lift verb refuses on either standing itself, since the green run tested a main that no longer exists, so nothing here lifts the mark.
|
|
@@ -80,7 +81,7 @@ The eight headings the script knows are written by `review-pr`, `review-address`
|
|
|
80
81
|
- The reply family matches by a filter in `poll.ts`, so a project posting it under different headings edits that
|
|
81
82
|
- The review and UI families match inside `canon pr review-state`, which the script and `review-pr` both read, so renaming one changes the verb
|
|
82
83
|
- The `UI-` states report the newest UI pass on its transition, and `UI-STALE` fires beside the `MOVED` of a push that left its marker behind
|
|
83
|
-
- A first sighting reports no `UI-` state at no cost to the mark, since `canon pr lift` reads the UI review itself and holds the mark on a
|
|
84
|
+
- A first sighting reports no `UI-` state at no cost to the mark, since `canon pr lift` reads the UI review itself and holds the mark on a drivable checklist until a UI close names the head
|
|
84
85
|
|
|
85
86
|
### UNMATCHED and RESPONSE
|
|
86
87
|
|
|
@@ -1,10 +1,39 @@
|
|
|
1
1
|
---
|
|
2
2
|
title: Orchestrator review dispatch runbook
|
|
3
|
-
description:
|
|
3
|
+
description: The painted-proof check every pull request clears before a reviewer launches, which pull requests take a reviewer dispatched under role-reviewer, the model it runs on, when a UI reviewer goes beside it, when small pull requests share one reviewer pair, and how the cross-branch pass per wave reaches each brief
|
|
4
4
|
---
|
|
5
5
|
|
|
6
6
|
Run this on every first pass, from `### The review dispatch` in the skill body. Review splits by what each side can see rather than by pass number. A dispatched reviewer holds one pull request and reads it deeper than this session can while holding a wave, and this session holds the wave and reads what no single pull request shows.
|
|
7
7
|
|
|
8
|
+
## Proof before any reviewer
|
|
9
|
+
|
|
10
|
+
A painted pull request missing proof goes back to its worker before any reviewer launches. Read it on every first pass, ahead of every launch below, and on every `MOVED` the poll routes here:
|
|
11
|
+
|
|
12
|
+
```bash
|
|
13
|
+
canon pr evidence <number> --check --json
|
|
14
|
+
```
|
|
15
|
+
|
|
16
|
+
Branch on the record's fields rather than on the exit code, and never derive the painted set from `gh pr diff` against a test written here, since the verb already reads it.
|
|
17
|
+
|
|
18
|
+
| Record | Route |
|
|
19
|
+
| ------------------------------ | ------------------------------------------------------------------------------------------ |
|
|
20
|
+
| `uncaptured` lists paths | Send it back for a capture and `pr-evidence`, naming each path as the record spells it |
|
|
21
|
+
| `owed` holds `evidence` | Send it back to run `pr-evidence`, since an evidence image changed and no comment shows it |
|
|
22
|
+
| `settled`, `uncaptured` empty | Proof stands, so launch the reviewers below |
|
|
23
|
+
| `uncaptured` absent | The base keeps no captures, so route on `owed` alone and never send it back for a capture |
|
|
24
|
+
| A refusal, such as `gh-failed` | Report the `reason`, launch the reviewers, and name the check unread in each brief |
|
|
25
|
+
|
|
26
|
+
`owed` holding only `preview` is the ship chain's deploy wait rather than missing proof, so it holds no reviewer.
|
|
27
|
+
|
|
28
|
+
### Sending it back
|
|
29
|
+
|
|
30
|
+
Message the session holding the branch, resolved the way `## Sending the handback` in `orchestrator-handback.md` resolves it, with the paths and the skill to run. Hold both reviewers until a re-read reads proof, since a code review on a head about to gain captures runs twice.
|
|
31
|
+
|
|
32
|
+
- A worker reporting that no capture can be taken, such as a state no fixture reaches, releases the hold, so launch the reviewers
|
|
33
|
+
- Carry the uncaptured paths as a fact in the code reviewer's brief then, since only a review pass may write the waiver `canon pr lift` reads
|
|
34
|
+
- Re-read the check on the worker's reply or the next `MOVED`, never on a timer
|
|
35
|
+
- A refusal never reads as proof. `canon pr lift` reads the same record and holds the mark on its own gate, so a launch past an unread check costs no merge.
|
|
36
|
+
|
|
8
37
|
## Every pull request takes a reviewer
|
|
9
38
|
|
|
10
39
|
Dispatch every pull request's review to a reviewer under `role-reviewer`, first pass included, whatever its size or its paths. A release pull request is the one exception, since its sweep carries no findings and owes no pass.
|
|
@@ -16,9 +45,11 @@ Dispatch every pull request's review to a reviewer under `role-reviewer`, first
|
|
|
16
45
|
|
|
17
46
|
## The UI reviewer
|
|
18
47
|
|
|
19
|
-
A pull request whose evidence record
|
|
48
|
+
A pull request whose evidence record counts a drivable box takes a second reviewer, a UI reviewer under `review-ui`, dispatched beside the code reviewer so the two passes run at once. Read the record with `canon pr evidence <number> --json` and branch on `drivable` above zero rather than on the exit code.
|
|
20
49
|
|
|
21
50
|
- A record carrying no checklist dispatches no UI reviewer, since the pass would stop on arrival
|
|
51
|
+
- A record whose `drivable` reads zero, every box being `(taste)`, dispatches none either, while a `checklist` with no readable `drivable` dispatches one, as the lift binds on it
|
|
52
|
+
- A pull request that gains a drivable box in review takes its UI reviewer then, on the `MOVED` that brought it, since a first pass that read none launched nobody
|
|
22
53
|
- The UI reviewer reads no diff and never hears the code verdict, so neither brief carries the other's result
|
|
23
54
|
- Each posts its own family and runs `canon pr lift` on its close, and the verb lifts the draft mark only once both read closed at the head
|
|
24
55
|
|
|
@@ -38,7 +69,7 @@ A pull request failing any condition takes its own reviewer pair, as above. A ro
|
|
|
38
69
|
|
|
39
70
|
### One pair per batch
|
|
40
71
|
|
|
41
|
-
Launch one code reviewer for the whole batch, and one UI reviewer beside it when any batched evidence record carries a
|
|
72
|
+
Launch one code reviewer for the whole batch, and one UI reviewer beside it when any batched evidence record carries a `drivable` count above zero. `orchestrator-reviewer-launch.md` carries both batch shapes.
|
|
42
73
|
|
|
43
74
|
- Each pull request still takes its own pass, its own verdict comment, and its own `canon pr lift`, since the poll routes on each comment's heading
|
|
44
75
|
- Never ask for one summary comment across the set, since a second comment is a second verdict the poll cannot route
|
|
@@ -64,7 +95,7 @@ A pull request whose Testing section names a billed run waits on the operator's
|
|
|
64
95
|
|
|
65
96
|
## Launching the reviewer
|
|
66
97
|
|
|
67
|
-
Take the reviewer shape in `orchestrator-reviewer-launch.md`, or its UI reviewer shape for a pull request
|
|
98
|
+
Take the reviewer shape in `orchestrator-reviewer-launch.md`, or its UI reviewer shape for a pull request whose `drivable` count is above zero.
|
|
68
99
|
|
|
69
100
|
- Check `canon sessions list --json` first for a live `reviewer-<project>-` or `reviewer-ui-<project>-` session whose trailing numbers include `<number>`, and message it instead of launching
|
|
70
101
|
- Match a number among the trailing ones rather than the whole name, since a batch reviewer's name lists every pull request it holds
|
|
@@ -72,7 +72,7 @@ claude --bg --model <model> -n "reviewer-<project>-<n1>-<n2>" "Run /canon:role-r
|
|
|
72
72
|
|
|
73
73
|
### The UI batch shape
|
|
74
74
|
|
|
75
|
-
The UI reviewer takes `reviewer-ui-<project>-<n1>-<n2>` and `review-ui` once per number, with the code shape's clauses for that family. Name only the pull requests whose evidence record carries a
|
|
75
|
+
The UI reviewer takes `reviewer-ui-<project>-<n1>-<n2>` and `review-ui` once per number, with the code shape's clauses for that family. Name only the pull requests whose evidence record carries a `drivable` count above zero, since a pass on one without a checklist stops on arrival and one holding only taste boxes binds no UI gate.
|
|
76
76
|
|
|
77
77
|
- The model is `sonnet`, as for the single UI shape
|
|
78
78
|
- `canon pr lift` runs once per number on that number's `## UI review closed`, unless the reason names the code review as still open or missing
|
|
@@ -32,6 +32,7 @@ The draft mark holds the merge until the reviews close, so this session preserve
|
|
|
32
32
|
- Report a flag reading ready once and leave it. It passed every gate the verb reads or a person readied it, which GitHub requires before a merge, so re-drafting fights them.
|
|
33
33
|
- Leave the lift to the reviewers, who run `canon pr lift` on their close, with the controlling session as fallback
|
|
34
34
|
- Refuse an instruction to ready the pull request directly, whoever sends it, since a direct ready skips every gate the verb reads
|
|
35
|
+
- Never submit a pull request review, which includes a capture waiver, since every session posts as one account and the lift reads a review as the reviewer's word
|
|
35
36
|
|
|
36
37
|
### Overriding a plan question
|
|
37
38
|
|
|
@@ -51,6 +51,7 @@ Four rules govern how a session reads the table.
|
|
|
51
51
|
- Build test data through a factory or builder rather than an inline object literal repeated across tests
|
|
52
52
|
- Assert through the public surface a caller uses, never on a private function or internal state directly. A test reaching into internals breaks on every refactor and catches nothing a caller sees.
|
|
53
53
|
- Prefer a real collaborator, then a fake, then a stub, and a mock last. A mock asserts how the code is built rather than what it does.
|
|
54
|
+
- Read a fixture page or script past five lines, or a fake that branches, from its own file in the test's fixtures folder, per `code-craft`. Keep a shorter input inline beside its assertion.
|
|
54
55
|
|
|
55
56
|
## Hold the structure floors
|
|
56
57
|
|
|
@@ -14,7 +14,7 @@ A file under a gitignored folder is unreadable to a pull request reviewer, and a
|
|
|
14
14
|
## Must
|
|
15
15
|
|
|
16
16
|
- Every change is split into visual-only and automatable before anything is written, and a behavior the review's engine cannot read, such as a keyboard trap, gets a box of its own
|
|
17
|
-
- The checklist covers the visual-only half, each item an action and the result a person looks for, with its route, width, and a `(taste)` or `(
|
|
17
|
+
- The checklist covers the visual-only half, each item an action and the result a person looks for, with its route, width, and a `(taste)`, `(local only)`, or `(needs fixture)` marker where one applies
|
|
18
18
|
- Every automatable change shipping with no test is named, with the layer `test-craft` would place it at, in the same file
|
|
19
19
|
- The file is written to the `.canon/tmp/handoff/ui-checklist/<slug>.md` handoff at the main worktree root, overwriting
|
|
20
20
|
- A change with nothing visual and nothing untested reports the coverage and writes no file
|
|
@@ -40,7 +40,8 @@ Write each box so a session driving the running app can run it without guessing,
|
|
|
40
40
|
- **Width.** Only when the change can differ by width, such as layout, spacing, or anything responsive. Copy, color, or a state rendering the same everywhere leaves it off.
|
|
41
41
|
- **Verb.** An action a driver performs, such as "scroll to", "click", "resize to", or "tab to". Never "read" or "look at", which name no action.
|
|
42
42
|
- **Taste.** End the line with `(taste)` when the result is a judgment of look or feel. A driver reports such a box as needing a person's eyes rather than passing it.
|
|
43
|
-
- **Setup.** State inline
|
|
43
|
+
- **Setup.** State inline the setup the page does not open in and the fixture state it needs. End with `(local only)` when a hosted preview cannot reach it, such as a stopped service.
|
|
44
|
+
- **Fixture.** End with `(needs fixture)` when the drive fixture lacks the state. The builder adds it, or with no `canon/config/app-drive.toml` writes the setup inline and drops the marker.
|
|
44
45
|
|
|
45
46
|
When the plan cites `canon/design/<surface>/` under `**Design references:**`, name the reference as the comparison on each box for that surface, such as "→ matches `canon/design/<surface>/` in light and dark". The reviewer then judges the build against the accepted design instead of against taste.
|
|
46
47
|
|