@vintasoftware/pr-review-canvas 0.3.0 → 0.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 (137) hide show
  1. package/README.md +79 -31
  2. package/docs/reference.md +396 -101
  3. package/package.json +9 -4
  4. package/pr-review.config.example.yml +44 -4
  5. package/prompts/chat-seed.md +3 -0
  6. package/prompts/generation-format.md +123 -26
  7. package/prompts/generation-strict-incremental.md +53 -0
  8. package/prompts/generation-strict.md +1 -27
  9. package/prompts/generation-surfacing-incremental.md +56 -0
  10. package/prompts/generation-surfacing.md +1 -58
  11. package/prompts/judging-strict.md +27 -0
  12. package/prompts/judging-surfacing.md +58 -0
  13. package/skills/pr-review-canvas/SKILL.md +81 -42
  14. package/src/acpx/acpx.ts +98 -5
  15. package/src/acpx/models.ts +43 -0
  16. package/src/canvas/comment.ts +24 -0
  17. package/src/canvas/import.ts +30 -9
  18. package/src/canvas/name.ts +1 -0
  19. package/src/canvas/zip.ts +21 -1
  20. package/src/chat/chat-manager.ts +67 -40
  21. package/src/chat/threads.ts +27 -26
  22. package/src/cli.ts +70 -8
  23. package/src/commands.ts +50 -17
  24. package/src/config.ts +14 -26
  25. package/src/contract/api.ts +58 -2
  26. package/src/contract/canvas-manifest.ts +7 -0
  27. package/src/contract/comments.ts +5 -0
  28. package/src/contract/discovery.ts +5 -2
  29. package/src/contract/generation-context.ts +76 -2
  30. package/src/contract/keys.ts +1 -0
  31. package/src/contract/pending.ts +49 -0
  32. package/src/contract/review-artifact.ts +50 -7
  33. package/src/contract/review-key.ts +51 -0
  34. package/src/contract/reviews.ts +26 -0
  35. package/src/contract/settings.ts +7 -0
  36. package/src/contract/state.ts +53 -22
  37. package/src/contract/validation.ts +1 -0
  38. package/src/git/environment.mjs +27 -0
  39. package/src/git/git.ts +109 -9
  40. package/src/git/local-target.ts +138 -0
  41. package/src/git/patch-lines.ts +34 -2
  42. package/src/git/pr-refs.ts +36 -0
  43. package/src/github/attachments.ts +9 -257
  44. package/src/github/canvas-comment.ts +22 -0
  45. package/src/github/capabilities.ts +3 -41
  46. package/src/github/comments.ts +3 -24
  47. package/src/github/post-comment.ts +3 -36
  48. package/src/github/post-review.ts +64 -23
  49. package/src/github/pr.ts +6 -87
  50. package/src/github/threads.ts +2 -2
  51. package/src/gitlab/attachments.ts +40 -0
  52. package/src/gitlab/canvas-comment.ts +26 -0
  53. package/src/gitlab/capabilities.ts +64 -0
  54. package/src/gitlab/comments.ts +164 -0
  55. package/src/gitlab/mr.ts +115 -0
  56. package/src/gitlab/post-comment.ts +111 -0
  57. package/src/gitlab/post-review.ts +93 -0
  58. package/src/gitlab/project.ts +13 -0
  59. package/src/gitlab/publish-drafts.ts +69 -0
  60. package/src/host/attachments.ts +293 -0
  61. package/src/host/capabilities.ts +38 -0
  62. package/src/host/client.ts +246 -0
  63. package/src/host/host.ts +154 -0
  64. package/src/host/pr.ts +51 -0
  65. package/src/host/remote.ts +42 -0
  66. package/src/project-config.ts +26 -0
  67. package/src/review/carry-marks.ts +131 -0
  68. package/src/review/carry-over.ts +79 -0
  69. package/src/review/doctor.ts +82 -38
  70. package/src/review/incremental.ts +107 -0
  71. package/src/review/normalize.ts +14 -4
  72. package/src/review/prepare.ts +111 -10
  73. package/src/review/prompt.ts +112 -5
  74. package/src/review/publish.ts +62 -10
  75. package/src/{github → review}/review-body.ts +17 -5
  76. package/src/review/skill-command.ts +5 -3
  77. package/src/review/test-paths.ts +44 -4
  78. package/src/review/validate-folds.ts +349 -24
  79. package/src/review/validate.ts +14 -5
  80. package/src/server/bundle.ts +324 -111
  81. package/src/server/context.ts +10 -8
  82. package/src/server/errors.ts +30 -8
  83. package/src/server/html.ts +35 -11
  84. package/src/server/routes/api.ts +63 -26
  85. package/src/server/routes/chat-routes.ts +91 -44
  86. package/src/server/routes/pages.ts +26 -9
  87. package/src/server/routes/review-routes.ts +278 -67
  88. package/src/store/canvas-store.ts +93 -55
  89. package/src/store/data-dir.ts +2 -1
  90. package/src/store/derived-store.ts +41 -27
  91. package/src/store/pr-store.ts +23 -14
  92. package/src/store/settings-store.ts +9 -1
  93. package/src/store/state-store.ts +105 -36
  94. package/src/upgrade.ts +338 -0
  95. package/static/js/api.js +87 -25
  96. package/static/js/app.js +50 -15
  97. package/static/js/chat-panel.js +32 -9
  98. package/static/js/chat.js +30 -6
  99. package/static/js/code-folds.js +171 -44
  100. package/static/js/composer.js +132 -17
  101. package/static/js/contract-types.d.ts +7 -0
  102. package/static/js/diff-decorations.js +67 -1
  103. package/static/js/diff-renderer.js +1 -1
  104. package/static/js/download.js +1 -1
  105. package/static/js/empty-state.js +102 -18
  106. package/static/js/errors.js +22 -6
  107. package/static/js/fold-levels.js +176 -0
  108. package/static/js/header.js +65 -15
  109. package/static/js/host.js +40 -0
  110. package/static/js/import-zone.js +1 -1
  111. package/static/js/interactions.js +274 -46
  112. package/static/js/keyboard.js +4 -1
  113. package/static/js/keys.js +12 -0
  114. package/static/js/layers.js +295 -32
  115. package/static/js/links.js +3 -3
  116. package/static/js/markdown.js +28 -1
  117. package/static/js/nav.js +22 -4
  118. package/static/js/pending.js +161 -0
  119. package/static/js/points.js +70 -9
  120. package/static/js/progress.js +4 -5
  121. package/static/js/quick-questions.js +15 -2
  122. package/static/js/reading-level.js +97 -0
  123. package/static/js/review-session.js +113 -29
  124. package/static/js/settings.js +55 -24
  125. package/static/js/signoff.js +79 -10
  126. package/static/js/skin.js +2 -2
  127. package/static/styles/chat-panel.css +22 -24
  128. package/static/styles/chat.css +4 -0
  129. package/static/styles/commands.css +6 -0
  130. package/static/styles/header.css +21 -0
  131. package/static/styles/panels.css +4 -0
  132. package/static/styles/pending.css +102 -0
  133. package/static/styles/review-actions.css +1 -0
  134. package/static/styles/review.css +4 -0
  135. package/static/styles/skin-github.css +7 -1
  136. package/static/styles.css +1 -0
  137. package/src/github/gh.ts +0 -211
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "name": "@vintasoftware/pr-review-canvas",
3
- "version": "0.3.0",
4
- "description": "Localhost PR review canvas: layered diffs, attention points, and GitHub comments for one PR",
3
+ "version": "0.5.0",
4
+ "description": "Localhost PR review canvas: layered diffs, attention points, and GitHub or GitLab comments for one PR",
5
5
  "type": "module",
6
6
  "bin": {
7
7
  "pr-review": "./bin/pr-review.mjs"
@@ -10,7 +10,7 @@
10
10
  "dev": "tsx watch --clear-screen=false --ignore '**/.pr-review/**' src/cli.ts serve",
11
11
  "start": "tsx src/cli.ts serve",
12
12
  "test": "vitest run",
13
- "hooks:install": "git config core.hooksPath .githooks",
13
+ "hooks:install": "git config core.hooksPath \"$(git rev-parse --show-toplevel)/.githooks\"",
14
14
  "test:watch": "vitest",
15
15
  "test:browser": "playwright test",
16
16
  "coverage": "vitest run --coverage",
@@ -23,7 +23,12 @@
23
23
  "format": "oxfmt --write",
24
24
  "format:check": "oxfmt --check",
25
25
  "check": "pnpm lint && pnpm format:check && pnpm typecheck",
26
- "precommit": "pnpm check && pnpm test"
26
+ "precommit": "pnpm check && pnpm test",
27
+ "site:dev": "vite --config site/vite.config.js",
28
+ "site:image": "node scripts/render-social-preview.mjs",
29
+ "site:build": "vite build --config site/vite.config.js",
30
+ "site:preview": "vite preview --config site/vite.config.js",
31
+ "site:test": "playwright test --config site/playwright.config.js"
27
32
  },
28
33
  "dependencies": {
29
34
  "@highlightjs/cdn-assets": "^11.12.0",
@@ -39,11 +39,51 @@ generation:
39
39
  # rationale: 300
40
40
  # diagram: 1500 # mermaid source, counted raw
41
41
 
42
- # Which paths count as tests, for the layering rules and the `test` pill on a file card.
43
- # Defaults to the JavaScript and TypeScript conventions below; name your own for other languages
44
- # (Python: '**/test_*.py', '**/tests/**'; Go: '**/*_test.go').
42
+ # Which paths count as tests, for the layering rules, the `test` pill on a file card, and the
43
+ # light reading level, which keeps test titles on screen. The defaults below match test
44
+ # directories and file-name shapes across stacks (JS/TS, Python, Go, Ruby, Java, Kotlin, PHP,
45
+ # C#, Swift, Elixir, Dart, Rust). A list here replaces them; add `'**/spec/**'` when that
46
+ # directory holds tests in your repository. Snapshots and fixtures inside test paths may still
47
+ # hide at light, since they are generated.
45
48
  tests:
46
- patterns: ['**/*.test.*', '**/*.spec.*', '**/__tests__/**']
49
+ patterns:
50
+ - '**/__tests__/**'
51
+ - '**/tests/**'
52
+ - '**/test/**'
53
+ - '**/*.test.*'
54
+ - '**/*.spec.*'
55
+ - '**/*_test.*'
56
+ - '**/*_spec.*'
57
+ - '**/test_*.py'
58
+ - '**/conftest.py'
59
+ - '**/*Test.java'
60
+ - '**/*Tests.java'
61
+ - '**/*Test.kt'
62
+ - '**/*Tests.kt'
63
+ - '**/*Test.scala'
64
+ - '**/*Tests.scala'
65
+ - '**/*Test.groovy'
66
+ - '**/*Tests.groovy'
67
+ - '**/*Test.cs'
68
+ - '**/*Tests.cs'
69
+ - '**/*Test.fs'
70
+ - '**/*Tests.fs'
71
+ - '**/*Test.vb'
72
+ - '**/*Tests.vb'
73
+ - '**/*Test.swift'
74
+ - '**/*Tests.swift'
75
+ - '**/*Test.php'
76
+ - '**/*Tests.php'
47
77
 
48
78
  chat:
49
79
  enabled: true # false removes the chat pane and its routes
80
+
81
+ canvas:
82
+ # A canvas stays current for a later head whose diff is identical to the one it was generated
83
+ # from, as after merging the base branch in. Set false to mark the canvas outdated on every new
84
+ # commit.
85
+ keepForIdenticalDiff: true
86
+ # Regenerating a canvas for a new head starts from the newest canvas of a commit the head was
87
+ # built on, keeping the layers, folds, notes and attention points its diff leaves untouched.
88
+ # Set false to generate every canvas from a blank page, as `--force` always does.
89
+ incremental: true
@@ -11,6 +11,9 @@ At most six sentences. No headings unless the reader asks for more. Markdown is
11
11
  short lists, `path:line` references. Do not restate the question. Do not summarize the whole PR
12
12
  when the reader asked about one file.
13
13
 
14
+ Call diff sections **chunks** in answers and proposed comments. Keep code identifiers and
15
+ `#hunk:` link targets unchanged.
16
+
14
17
  ## Answer protocol
15
18
 
16
19
  For any "is this fine / covered / needed / safe?" question, the verdict comes first, in one of
@@ -39,6 +39,9 @@ hunk in that file's patch.
39
39
 
40
40
  ## Layering rules
41
41
 
42
+ In reader-facing prose, call diff sections **chunks**. Keep the schema field `hunks` and
43
+ `#hunk:` link targets exactly as specified.
44
+
42
45
  Project-configured layers (optional guidance):
43
46
 
44
47
  {{CONFIGURED_LAYERS}}
@@ -71,35 +74,129 @@ Project-configured layers (optional guidance):
71
74
 
72
75
  ## Selective expansion
73
76
 
74
- Keep the reading path focused by collapsing code that is already well understood and supported
75
- by evidence you read. This changes its initial presentation only: every hunk stays assigned and
76
- the reviewer can expand the full diff. Collapsing never marks code as reviewed.
77
-
78
- - For a test case with meaningful assertions that cover its behavior, show the test title and
79
- collapse its body. Keep weak assertions, important omissions, and tests that explain a decision open.
80
- - Collapse straightforward, well-tested helpers, adapters, and conventional boilerplate when
81
- there is no unresolved design choice, performance concern, or other non-functional requirement
82
- to examine. A familiar pattern or a passing test name alone is insufficient evidence.
83
- - Repeated mappings, wiring, fixtures, and generated sections can collapse when their behavior
84
- and relevant checks are understood. Keep the representative example open if it teaches the
85
- pattern; collapse repetitions that add no new decision.
86
- - Keep security boundaries, destructive operations, ordering and concurrency rules, performance
87
- assumptions, and other consequential behavior visible when they need the reviewer's attention.
88
- Keep annotations, attention points, unresolved test gaps, and discussion visible.
89
- - For an entire routine file, set its `collapsed` field to `true`. Its file header remains visible.
90
- Keep tests with the feature they cover even when their bodies are collapsed; confidence is not
91
- a reason to move meaningful behavior into Other.
92
- - Within a file, use `folds`: `{ "title": "test or function/class title", "side": "new",
93
- "startLine": 12, "endLine": 28 }`. Each range is inclusive and inside one assigned hunk.
94
- The page shows only the title until expanded. Use `old` for a deletion; use one coordinate side
95
- for all folds in a hunk, and keep ranges separate. Rows between the two anchors, including
96
- interleaved deletions, are part of the fold. Pick boundaries that keep the whole change together.
97
- Leave partial or ambiguous ranges open. A function spanning several hunks can use a separate
98
- titled range in each hunk, or the whole file can start collapsed when appropriate.
77
+ The reader chooses how much of the diff is on screen, with one control over the whole page. This
78
+ changes the initial presentation only: every hunk stays assigned and the reviewer can expand
79
+ anything. Hiding code never marks it reviewed.
80
+
81
+ Give every fold and every collapsed file the lowest of the three levels at which it should hide.
82
+ The levels nest, so a `light` fold is also hidden at `moderate` and `aggressive`; write each one
83
+ once, at its own level. The three levels answer three different questions, and each one hides
84
+ much more than the one below it:
85
+
86
+ - **light the diff as a reviewer has always seen it.** Nothing hand-written hides. The page
87
+ already folds imports, whitespace-only rewrites, and moved blocks by itself; `light` adds only
88
+ wholly generated content lock files, snapshots, migrations, generated clients and fixtures —
89
+ as `collapsed: "light"` or a `light` fold over the generated block. Snapshots and fixtures
90
+ count as generated even inside a test directory. Tests are untouched at `light`: no fold and no
91
+ collapse in any other test file carries this level.
92
+ - **moderate what would a reviewer skip once they trust the layer's rationale?** Each test
93
+ body, folded under its own title so the list of titles reads as the spec of the change: one
94
+ fold per test, starting on the line after its title; a range that spans several tests hides the
95
+ titles and is not what this level means. Then everything whose contract its signature, its
96
+ name, or the layer rationale already states: helpers and adapters, data-transfer and
97
+ serialization types, request handlers and views that follow the project's pattern, templates
98
+ and markup, dependency wiring and registration, repeated mappings, configuration. Keep the one
99
+ representative example open if it teaches a pattern the rest repeats.
100
+ - **aggressive what must the reviewer judge to decide on this change?** Only that stays open:
101
+ the code an attention point or annotation names, and the few lines that carry the layer's core
102
+ mechanism. Everything else in the layer hides behind a title. The reader follows the change as
103
+ pseudo-code and expands what they want to see. This is the only level that may hide an
104
+ annotation. Such a fold covers one whole annotation and no other, and the page then shows the
105
+ annotation's text in place of the fold title.
106
+
107
+ Aggressive is a strong instruction, not a slight increase over moderate. On a typical layer it
108
+ leaves a small fraction of the changed lines on screen. Check your output before you finish: a
109
+ layer where `moderate` and `aggressive` hide about the same amount has not applied `aggressive`.
110
+
111
+ Decide first what the layer's **core** is, because the core never collapses at any level. The
112
+ core is the file or two the reviewer must read to own the change: the file your rationale sends
113
+ them to first, the file that defines the layer's new concepts (a schema, a type, a contract, a
114
+ state machine), and every file you annotated. An annotation marks code worth reading; collapsing
115
+ its file would hide the code and the explanation together, with only a path left to say so. Not
116
+ having an attention point does not make a file routine: a new schema with no open question is
117
+ still what everything else in the layer is built on.
118
+
119
+ Then the two mechanisms split the work:
120
+
121
+ - `folds` are for the core. The file stays open, and folds hide its routine parts behind titles.
122
+ At `aggressive` the core file shows its defining lines and its annotations, and nothing else:
123
+ expect more than half of it to sit inside folds. In a data type the field or column
124
+ declarations and the constraints stay; the framework's ceremony folds, whatever the stack calls
125
+ it — string conversion and equality, accessors and builders, type-checker-only blocks, query
126
+ helpers and repositories, derived-property boilerplate. In a function the signature and the
127
+ annotated lines stay; argument parsing, presenters, formatting, and error-to-response mapping
128
+ fold. Inside a core file, folds are `aggressive` by default: at `moderate` the reviewer still
129
+ reads the core in full and trusts only the other files to the rationale, so the two levels
130
+ differ by exactly this. Give a core-file range `moderate` only when it is pure ceremony — a
131
+ repeated import pattern, generated accessors, a type-checker-only block, string conversion.
132
+ Check the core files before you finish: mostly open at `moderate`, mostly folded at
133
+ `aggressive`. One fold per contiguous routine block; several small folds are better than one
134
+ wide title that overstates what it covers.
135
+ - `collapsed` is for everything that is not the core. It hides a file's whole body behind its
136
+ header. At `moderate` and `aggressive` that is most files of a layer.
137
+
138
+ A file that carries more than about twenty changed lines and no attention point should hide
139
+ something at `aggressive`: the whole file when it is not the core, its routine ranges when it is.
140
+
141
+ The validator enforces the shape of this: `collapsed` must name a level (`true` is refused); no
142
+ fold or collapse in a test file may be `light`; a `light` fold covers at most forty lines; a file
143
+ with more than twenty changed lines outside its annotations, no attention point, and neither
144
+ `collapsed` nor a fold fails with `FOLD_MISSING`; a file of more than sixty changed lines that
145
+ stays open must fold at least half of the lines outside its attention points, annotated lines
146
+ included, or fails the same way; and a layer of more than a hundred changed lines that leaves more
147
+ than twenty lines open at `moderate` outside its attention points and hides nothing more at
148
+ `aggressive` fails the same way. A smaller layer reads whole, and only the file rules apply to it.
149
+ An annotation is not a way past these: it marks the lines to read, and the rows around it still
150
+ fold.
151
+
152
+ Keep visible at every level: security boundaries, destructive operations, ordering and
153
+ concurrency rules, performance assumptions, and other consequential behavior that needs the
154
+ reviewer's attention. Attention points, unresolved test gaps, and discussion are never folded.
155
+ Leaving such a file fully open at every level is the failure this control exists to prevent.
156
+
157
+ An example of the two together, for a file whose new `settle()` matters and whose rest does not:
158
+
159
+ ```json
160
+ {
161
+ "path": "domain/billing/actions.py",
162
+ "hunks": ["domain_billing_actions_py#1"],
163
+ "annotations": [{ "side": "new", "startLine": 61, "endLine": 66, "text": "Refunds settle before the ledger write, so a failed write leaves no money moved." }],
164
+ "folds": [
165
+ { "title": "the retry helper, unchanged in behavior", "side": "new", "startLine": 12, "endLine": 28, "level": "moderate" },
166
+ { "title": "settle() moves the money, then writes the ledger", "side": "new", "startLine": 55, "endLine": 80, "level": "aggressive" }
167
+ ]
168
+ }
169
+ ```
170
+
171
+ At `light` the file reads in full. At `moderate` the helper hides. At `aggressive` `settle()`
172
+ hides too, behind the annotation's text.
173
+
174
+ - A fold is `{ "title": "what the block does", "side": "new", "startLine": 12, "endLine": 28,
175
+ "level": "light" }`. Each range is inclusive and inside one assigned hunk. The page shows only
176
+ the title until expanded. Use `old` for a deletion; use one coordinate side for all folds in a
177
+ hunk. Rows between the two anchors, including interleaved deletions, are part of the fold. Pick
178
+ boundaries that keep the whole change together. Leave a range open when you cannot place both
179
+ of its ends. A function spanning several hunks can use a separate titled range in each hunk,
180
+ or the whole file can collapse instead.
181
+ - Two folds are either separate, or one sits wholly inside the other with the lower level inside.
182
+ A test body at `moderate` inside its whole test class at `aggressive` is valid; two ranges that
183
+ cross each other are not.
184
+ - When the declaration line is in the diff, start the fold on the line after it, so the reader
185
+ keeps the signature and can still find where the symbol is defined. The title then states what
186
+ the body does rather than repeating the name. When the declaration is outside the diff, the
187
+ title names the symbol.
188
+ - Set a file's `collapsed` field to the level at which its whole body hides; its header stays
189
+ visible. `light` is for wholly generated files, such as lock files, snapshots, and migrations,
190
+ never for a test file, a template, or anything hand-written.
191
+ At `moderate`, collapse every file the layer rationale already accounts for. At `aggressive`,
192
+ collapse every file outside the layer's core, which is most of them. A file with an annotation
193
+ or an attention point never collapses, at any level: it is core, and it uses folds. Keep tests
194
+ with the feature they cover even when their bodies are collapsed; confidence is not a reason to
195
+ move meaningful behavior into Other.
99
196
  - Generate no explanation or confidence score for a fold. The title is plain text. Use the actual test title or symbol
100
197
  name when it fits. For a longer name, use a faithful excerpt with an ellipsis within the fold-title
101
198
  cap, preserving the behavior and distinguishing condition. The full name remains in the expanded
102
- code. Omit `collapsed` and `folds` where the code should start open.
199
+ code. Omit `collapsed` and `folds` where the code should start open at every level.
103
200
 
104
201
  ## Length rules
105
202
 
@@ -0,0 +1,53 @@
1
+ # Update the review canvas for a {{TARGET_WORD}}
2
+
3
+ This {{TARGET_WORD}} already has a canvas, generated for a commit this head was built on. Your task
4
+ is to bring that canvas to the current head: keep what the new commits leave untouched, decide anew
5
+ what they changed, and write the result as one JSON file.
6
+
7
+ A canvas earns a reviewer's trust by being stable. A layer they already read should come back with
8
+ the same key, the same title, and the same words; a fold they opened should still be there; a
9
+ concern they dismissed should not reappear under a new name. Rewriting a paragraph that describes
10
+ code nobody touched costs the reviewer a second reading for nothing.
11
+
12
+ ## The basis canvas
13
+
14
+ {{BASIS}}
15
+
16
+ Read the basis canvas file for the exact wording of anything you carry. Its hunk ids belong to its
17
+ own diff and mean nothing here: use the hunk ids of the manifest below.
18
+
19
+ ### What the head changed
20
+
21
+ {{FILE_DELTA}}
22
+
23
+ ### Carry these as they stand
24
+
25
+ {{CARRIED}}
26
+
27
+ ### Decide these again
28
+
29
+ {{RE_JUDGED}}
30
+
31
+ ## How to update
32
+
33
+ - Start from the carried content and change it only where this list says to. Where you do depart
34
+ from the basis canvas on an untouched file, you must have read the new code and have a reason.
35
+ - A carried layer keeps its `key`. The key is how a reviewer's progress finds the layer again, so
36
+ never rename a key to tidy it up, and never reuse a key for a different concern.
37
+ - A new or changed file belongs wherever it fits best, which may be a carried layer. Adding a file
38
+ to a layer is a change to that layer: its rationale must still describe what it now holds.
39
+ - A re-judged concern may come back with the same kind, path, and title, but only if you read the
40
+ new code and it still holds. A concern the change fixed is gone, not softened.
41
+ - Write the summary and the risk tags again, from the whole change set as it is now.
42
+ - Everything below applies as it would to a canvas written from nothing: the layering rules, the
43
+ caps, the hunk coverage, and the validator.
44
+
45
+ ## Judging the change
46
+
47
+ Produce a code-quality review that a human can navigate. Read the changed behavior, its tests,
48
+ and the surrounding boundaries. Apply the project rulebook and bundled quality standards to
49
+ identify consequential structural problems, risks, and decisions that need the reviewer's judgment.
50
+ The basis canvas is the record of the structural review already done; extend it rather than
51
+ repeating it.
52
+
53
+ {{JUDGING}}
@@ -5,30 +5,4 @@ and the surrounding boundaries. Apply the project rulebook and bundled quality s
5
5
  identify consequential structural problems, risks, and decisions that need the reviewer's judgment.
6
6
  Assume no prior structural review unless evidence of one is supplied.
7
7
 
8
- Explain how the change works before asking the reviewer to assess it. Prioritize a small number
9
- of well-supported concerns; an empty attention-point list is valid. Tie each concern to concrete
10
- code, its consequence, and the condition under which the design is acceptable. Keep proposed
11
- changes within the PR's scope. Do not repeat automated lint findings or turn style preferences
12
- into merge requirements.
13
-
14
- Use `decide` for a choice requiring agreement or a substantiated structural concern that needs
15
- resolution, `check` for a concrete verification, and `fyi` for useful context. Read relevant test
16
- assertions before classifying behavior as covered or missing. The canvas itself runs no tests and
17
- provides no approval on the reviewer's behalf.
18
-
19
- Write one JSON file grouping the diff into semantic layers, linked explanations, and attention
20
- points. A deterministic validator checks the file; a web page renders it. Write no prose outside
21
- the JSON file.
22
-
23
- ## Project rulebook
24
-
25
- Use these code standards to assess consequential drift and debt. Read them as reference material;
26
- follow this prompt's workflow and output format.
27
-
28
- {{RULEBOOK}}
29
-
30
- ### Bundled standards
31
-
32
- {{QUALITY_STANDARDS}}
33
-
34
- {{FORMAT}}
8
+ {{JUDGING}}
@@ -0,0 +1,56 @@
1
+ # Update the review canvas for a {{TARGET_WORD}}
2
+
3
+ This {{TARGET_WORD}} already has a canvas, generated for a commit this head was built on. Your task
4
+ is to bring that walkthrough to the current head: keep the reading path the new commits leave
5
+ untouched, rebuild the parts they changed, and write the result as one JSON file.
6
+
7
+ A walkthrough earns a reviewer's trust by being stable. A layer they already read should come back
8
+ with the same key, the same title, and the same words; a fold they opened should still be there; a
9
+ concern they dismissed should not reappear under a new name. Rewriting an explanation of code
10
+ nobody touched costs the reviewer a second reading for nothing.
11
+
12
+ ## The basis canvas
13
+
14
+ {{BASIS}}
15
+
16
+ Read the basis canvas file for the exact wording of anything you carry. Its hunk ids belong to its
17
+ own diff and mean nothing here: use the hunk ids of the manifest below.
18
+
19
+ ### What the head changed
20
+
21
+ {{FILE_DELTA}}
22
+
23
+ ### Carry these as they stand
24
+
25
+ {{CARRIED}}
26
+
27
+ ### Decide these again
28
+
29
+ {{RE_JUDGED}}
30
+
31
+ ## How to update
32
+
33
+ - Start from the carried content and change it only where this list says to. Where you do depart
34
+ from the basis canvas on an untouched file, you must have read the new code and have a reason.
35
+ - A carried layer keeps its `key`. The key is how a reviewer's progress finds the layer again, so
36
+ never rename a key to tidy it up, and never reuse a key for a different concern.
37
+ - A new or changed file belongs wherever it fits best, which may be a carried layer. Adding a file
38
+ to a layer is a change to that layer: its rationale must still describe what it now holds.
39
+ - Ask what the new commits do to the reading path, not only to the files: a change that answers a
40
+ question the basis canvas raised should stop being an open question.
41
+ - A re-judged concern may come back with the same kind, path, and title, but only if you read the
42
+ new code and it still holds. A concern the change fixed is gone, not softened.
43
+ - Write the summary and the risk tags again, from the whole change set as it is now.
44
+ - Everything below applies as it would to a canvas written from nothing: the layering rules, the
45
+ caps, the hunk coverage, and the validator.
46
+
47
+ ## Build the reading path
48
+
49
+ Build a visual walkthrough that reads like a peer explaining the PR, and review the code while you
50
+ build it. Help the reviewer understand the code well enough to own it: what changed, how the parts
51
+ cooperate, why the design takes this shape, what they will need to know when maintaining it, and
52
+ what does not hold up.
53
+
54
+ Use these questions for the parts you rebuild, and only the fields that help for this PR:
55
+
56
+ {{JUDGING}}
@@ -7,61 +7,4 @@ what does not hold up.
7
7
 
8
8
  Build the reading path around these questions, using only the fields that help for this PR:
9
9
 
10
- - What changes for a user or a caller? Start with a concrete before/after example when useful.
11
- - How does one important request or state transition move through the changed parts? Link the
12
- entry point, the owning module, and the resulting effect. A diagram or short pseudocode can
13
- explain a long implementation; keep the real diff available through links.
14
- - Which decisions should the reviewer understand or agree with? Describe the chosen approach,
15
- its benefit, its cost, and when the trade-off would need to be revisited. Distinguish a rationale
16
- documented by the author from an inference you make from code. Mention alternatives only when
17
- they clarify a real choice; do not invent rejected designs or author intent.
18
- - What gives confidence in the behavior? Point to the relevant test assertions, checks in the
19
- code, and explicit limits. Map evidence you actually read rather than conducting an exhaustive
20
- coverage audit. An uninspected behavior is not a missing test or a `not-needed` test.
21
- - What does the next maintainer need to remember? Surface ownership boundaries, ordering rules,
22
- failure behavior, operational assumptions, and the places to change when requirements evolve.
23
-
24
- ## Audit the change as you read it
25
-
26
- Explaining the change is half the task. The other half is judging it. Work through the diff with
27
- the bundled standards below and the project rulebook, and report a small number of well-supported
28
- problems. Tie each one to concrete code, its consequence, and the condition under which the design
29
- is acceptable. An empty list is a valid result; a padded list is not.
30
-
31
- Give particular weight to these, because a walkthrough reads past them easily:
32
-
33
- - **Claims against implementation.** A README sentence, a comment, a constant's name, and the PR
34
- description each state a guarantee. The constants, configuration files, schedules, limits,
35
- timeouts, and error paths in the diff either deliver it or they do not. Read the value next to
36
- the claim. A guarantee that holds only under conditions the deployment does not promise is a
37
- defect: name the claim, the value that breaks it, and the consequence.
38
- - **Values that must relate to each other.** A period, a window, a timeout, a retention, a batch
39
- size, and a schedule are chosen against one another. Two values that meet exactly, or in the
40
- wrong order, make the behavior depend on timing the system does not control.
41
- - **Structure.** Consequential drift, debt, and complexity the change adds rather than deletes.
42
-
43
- Use `decide` for a choice requiring agreement or a substantiated problem that needs resolution,
44
- `check` for a concrete verification, and `fyi` for useful context. Use layer rationales and file
45
- notes to explain the reading path and code flow. Put every decision, trade-off, and specific human
46
- verification in an attention point, including sound choices the reviewer should understand.
47
- A trade-off is not automatically a defect. Do not repeat automated lint
48
- findings, turn style preferences into merge requirements, manufacture concerns, or give a merge
49
- verdict. Avoid copying the same observation into several fields.
50
-
51
- Write one JSON file grouping the diff into semantic layers, linked explanations, and attention
52
- points. A deterministic validator checks the file; a web page renders it. Write no prose outside
53
- the JSON file.
54
-
55
- ## Project rulebook
56
-
57
- Use these code standards to assess consequential drift and debt, and to explain project choices and
58
- boundaries as they arise in the reading path. Read them as reference material; follow this prompt's
59
- workflow and output format.
60
-
61
- {{RULEBOOK}}
62
-
63
- ### Bundled standards
64
-
65
- {{QUALITY_STANDARDS}}
66
-
67
- {{FORMAT}}
10
+ {{JUDGING}}
@@ -0,0 +1,27 @@
1
+ Explain how the change works before asking the reviewer to assess it. Prioritize a small number
2
+ of well-supported concerns; an empty attention-point list is valid. Tie each concern to concrete
3
+ code, its consequence, and the condition under which the design is acceptable. Keep proposed
4
+ changes within the PR's scope. Do not repeat automated lint findings or turn style preferences
5
+ into merge requirements.
6
+
7
+ Use `decide` for a choice requiring agreement or a substantiated structural concern that needs
8
+ resolution, `check` for a concrete verification, and `fyi` for useful context. Read relevant test
9
+ assertions before classifying behavior as covered or missing. The canvas itself runs no tests and
10
+ provides no approval on the reviewer's behalf.
11
+
12
+ Write one JSON file grouping the diff into semantic layers, linked explanations, and attention
13
+ points. A deterministic validator checks the file; a web page renders it. Write no prose outside
14
+ the JSON file.
15
+
16
+ ## Project rulebook
17
+
18
+ Use these code standards to assess consequential drift and debt. Read them as reference material;
19
+ follow this prompt's workflow and output format.
20
+
21
+ {{RULEBOOK}}
22
+
23
+ ### Bundled standards
24
+
25
+ {{QUALITY_STANDARDS}}
26
+
27
+ {{FORMAT}}
@@ -0,0 +1,58 @@
1
+ - What changes for a user or a caller? Start with a concrete before/after example when useful.
2
+ - How does one important request or state transition move through the changed parts? Link the
3
+ entry point, the owning module, and the resulting effect. A diagram or short pseudocode can
4
+ explain a long implementation; keep the real diff available through links.
5
+ - Which decisions should the reviewer understand or agree with? Describe the chosen approach,
6
+ its benefit, its cost, and when the trade-off would need to be revisited. Distinguish a rationale
7
+ documented by the author from an inference you make from code. Mention alternatives only when
8
+ they clarify a real choice; do not invent rejected designs or author intent.
9
+ - What gives confidence in the behavior? Point to the relevant test assertions, checks in the
10
+ code, and explicit limits. Map evidence you actually read rather than conducting an exhaustive
11
+ coverage audit. An uninspected behavior is not a missing test or a `not-needed` test.
12
+ - What does the next maintainer need to remember? Surface ownership boundaries, ordering rules,
13
+ failure behavior, operational assumptions, and the places to change when requirements evolve.
14
+
15
+ ## Audit the change as you read it
16
+
17
+ Explaining the change is half the task. The other half is judging it. Work through the diff with
18
+ the bundled standards below and the project rulebook, and report a small number of well-supported
19
+ problems. Tie each one to concrete code, its consequence, and the condition under which the design
20
+ is acceptable. An empty list is a valid result; a padded list is not.
21
+
22
+ Give particular weight to these, because a walkthrough reads past them easily:
23
+
24
+ - **Claims against implementation.** A README sentence, a comment, a constant's name, and the PR
25
+ description each state a guarantee. The constants, configuration files, schedules, limits,
26
+ timeouts, and error paths in the diff either deliver it or they do not. Read the value next to
27
+ the claim. A guarantee that holds only under conditions the deployment does not promise is a
28
+ defect: name the claim, the value that breaks it, and the consequence.
29
+ - **Values that must relate to each other.** A period, a window, a timeout, a retention, a batch
30
+ size, and a schedule are chosen against one another. Two values that meet exactly, or in the
31
+ wrong order, make the behavior depend on timing the system does not control.
32
+ - **Structure.** Consequential drift, debt, and complexity the change adds rather than deletes.
33
+
34
+ Use `decide` for a choice requiring agreement or a substantiated problem that needs resolution,
35
+ `check` for a concrete verification, and `fyi` for useful context. Use layer rationales and file
36
+ notes to explain the reading path and code flow. Put every decision, trade-off, and specific human
37
+ verification in an attention point, including sound choices the reviewer should understand.
38
+ A trade-off is not automatically a defect. Do not repeat automated lint
39
+ findings, turn style preferences into merge requirements, manufacture concerns, or give a merge
40
+ verdict. Avoid copying the same observation into several fields.
41
+
42
+ Write one JSON file grouping the diff into semantic layers, linked explanations, and attention
43
+ points. A deterministic validator checks the file; a web page renders it. Write no prose outside
44
+ the JSON file.
45
+
46
+ ## Project rulebook
47
+
48
+ Use these code standards to assess consequential drift and debt, and to explain project choices and
49
+ boundaries as they arise in the reading path. Read them as reference material; follow this prompt's
50
+ workflow and output format.
51
+
52
+ {{RULEBOOK}}
53
+
54
+ ### Bundled standards
55
+
56
+ {{QUALITY_STANDARDS}}
57
+
58
+ {{FORMAT}}