yam-flow 2.5.0 → 2.6.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 CHANGED
@@ -2,6 +2,57 @@
2
2
 
3
3
  All notable changes to yam-flow are documented here.
4
4
 
5
+ ## v2.6.0 - 2026-08-07
6
+
7
+ ### Added
8
+
9
+ - Added effective executable identity validation for global yam install and rollback, including npm global root, package/bin mapping, PATH target, canonical realpaths, and observed version.
10
+ - Added bounded paired-sample promotion receipts with explicit thresholds, deterministic evidence digests, operator-asserted measurement truth, and strict keep/revert gates.
11
+ - Added a capability matrix to `yam tools doctor --json` that separates maturity from observed runtime readiness.
12
+ - Added digest-bound strict gate results at release, external-update, Mission-completion, and benchmark-promotion boundaries.
13
+ - Added the opt-in Demand-Gated Design Production Phase: pre-recorded operator demand, local static Plan Review Canvas Lite, at most two chronologically finding-backed revisions, final gallery manifest, and digest-verifiable immutable phase receipt.
14
+
15
+ ### Improved
16
+
17
+ - External update receipts preserve the deepest actionable Doctor or rollback failure as the primary blocker while keeping receipt persistence failures as secondary evidence.
18
+ - Ueye design-production artifacts bind one canonical revision state to its closed Canvas, enforce Canvas-comment and archive chronology at record time, and revalidate source, exact anchors, protected-asset editability, final-round gallery linkage, upstream digests, nested receipt semantics, session state, and aggregate state without upgrading those checks into visual, license, or implementation proof.
19
+
20
+ ### Security
21
+
22
+ - Same-version PATH shadows, malformed global package/bin identities, path/symlink escapes, protected-asset replacement attempts, and inconsistent gate contracts fail closed.
23
+ - Canvas rendering is local static HTML with a no-script/no-network CSP and escaped reviewer content; it starts no server or background process.
24
+
25
+ ### Verification
26
+
27
+ - Focused external-update identity, strict-gate/promotion/capability/Mission, and design-production smokes.
28
+ - TypeScript typecheck, clean build, self-verification, packaged CLI, package-boundary/secret, and bounded Deep checks.
29
+
30
+ ## v2.5.1 - 2026-07-31
31
+
32
+ ### Added
33
+
34
+ - Added bounded stdin readers with a 1 MiB hook limit and a 4 MiB general CLI limit. Malformed or oversized hook payloads now return a valid fail-open response without echoing or acting on rejected input.
35
+ - Added a final read-only `yam doctor --json` verification to yam updates and automatic rollbacks. The updater accepts success only when the command exits cleanly and returns the expected healthy Doctor contract.
36
+ - Added a release-time secret guard over the actual npm dry-run packlist. It scans regular UTF-8 text files for high-signal private-key and provider credential patterns while reporting only pattern, path, and line metadata.
37
+
38
+ ### Improved
39
+
40
+ - Install and Ueye integrity manifests now use locale-independent ordinal ordering. Existing yam 2.5.0-and-earlier receipts retain compatibility with their stored legacy order while new digests are deterministic across locales.
41
+
42
+ ### Security
43
+
44
+ - Rejected stdin payloads are byte-bounded, are not included in diagnostics, and cannot supply hook context or trigger workspace mutation.
45
+ - `verify:self`, `prepack`, `prepublishOnly`, and `release:check` now inherit the npm packlist secret guard; the inner pack inspection disables lifecycle scripts to avoid recursive execution.
46
+ - Updater Doctor output recorded in receipts remains redacted and bounded, and an unhealthy rollback is not reported as an automatic recovery.
47
+
48
+ ### Verification
49
+
50
+ - TypeScript typecheck and build
51
+ - Bounded hook latency/read-only smoke and packaged CLI smoke
52
+ - Locale-independent install/Ueye manifest regression smokes
53
+ - External update/rollback Doctor smoke
54
+ - Npm packlist secret-pattern and redaction smoke
55
+
5
56
  ## v2.5.0 - 2026-07-30
6
57
 
7
58
  ### Added
package/COMMANDS.md CHANGED
@@ -154,7 +154,33 @@ yam update apply --component yam --json
154
154
  yam update apply --all --json
155
155
  ```
156
156
 
157
- `yam update check` is read-only. Every `apply` needs explicit authorization, uses a concurrent-run lock, records a component receipt, and stops on failed/manual results. `--all` runs yam last. Insane Search is never remove-first and `.codex/plugins/cache` is never edited directly.
157
+ `yam update check` is read-only. Every `apply` needs explicit authorization, uses a concurrent-run lock, records a component receipt, and stops on failed/manual results. `--all` runs yam last. A yam install verifies the effective executable identity before any yam-side install command and repeats that check during rollback. This identity contract currently supports POSIX symlink layouts; Windows npm `.cmd` shims fail closed as unverified. Insane Search is never remove-first and `.codex/plugins/cache` is never edited directly.
158
+
159
+ ## Demand-Gated Design Production
160
+
161
+ Use only after repeated plan-review or large multi-asset coordination demand is real. A one-off review remains on the ordinary Ueye/Mission path.
162
+
163
+ ```bash
164
+ yam ueye production canvas create --session-id campaign --title "Campaign review" --demand-kind multi_asset_production --demand-evidence "Five coordinated assets require one review package" --artifact-spec ./canvas-artifact.json --json
165
+ yam ueye production canvas comment --session-path .yam/ueye/design-production/campaign/plan-review.json --render-path .yam/ueye/design-production/campaign/canvas.html --comment-id finding-1 --artifact-id campaign-plan --anchor-kind line --locator L12 --finding "CTA hierarchy is ambiguous" --requested-change "Make the primary CTA explicit" --json
166
+ yam ueye production canvas close --session-path .yam/ueye/design-production/campaign/plan-review.json --render-path .yam/ueye/design-production/campaign/canvas.html --verdict request_changes --json
167
+ yam ueye production revision init --session-id campaign --json
168
+ yam ueye production revision record --state-path .yam/ueye/design-production/campaign/revision-state.json --finding-id round-1 --source-comment-id finding-1 --finding-summary "CTA hierarchy is ambiguous" --finding-evidence "Canvas line L12" --planned-change "Clarify the primary CTA" --outcome accepted --revision-ref ./ueye-revision-ref.json --json
169
+ yam ueye production gallery write --manifest-path .yam/ueye/design-production/campaign/gallery.json --session-id campaign --completion-state packaged --artifact-spec ./gallery-artifact.json --json
170
+ yam ueye production gallery verify --manifest-path .yam/ueye/design-production/campaign/gallery.json --json
171
+ yam ueye production finalize --demand-kind multi_asset_production --demand-evidence "Five coordinated assets require one review package" --canvas-session-path .yam/ueye/design-production/campaign/plan-review.json --revision-state-path .yam/ueye/design-production/campaign/revision-state.json --gallery-manifest-path .yam/ueye/design-production/campaign/gallery.json --receipt-path .yam/ueye/design-production/campaign/phase-receipt.json --json
172
+ yam ueye production phase verify --receipt-path .yam/ueye/design-production/campaign/phase-receipt.json --json
173
+ ```
174
+
175
+ Canvas artifact specs use `{ "id", "role", "file_path" }`; gallery specs include `{ "id", "role", "provenance", "revision_ref", "dimensions", "sha256", "completion_state", "final_path" }`. A revision reference also carries the archive receipt's exact `archived_at`, which must match its Ueye manifest entry. All project paths are relative and confined; Canvas session/render paths and the single revision state are fixed under the session-specific `.yam/ueye/design-production/` directory. Revision init binds that state to the closed `request_changes` Canvas path and digest; record/show/finalize reject alternate state files, and record immediately checks the source Canvas comment plus the current archive-time boundary. Demand is operator-asserted but must be recorded before Canvas creation and match at finalize. Canvas source hashes and exact anchors are rechecked before comment/close/finalize. Every phase round names its source Canvas comment and supplies at least one newly archived Ueye revision created within that round's review window; gallery artifacts bind to the final round. Ueye asset/revision hashes are rechecked, a protected `do_not_replace` asset requires `intent: "preserve"`, and `edit_copy` requires `allowed_for_edit: true`. The phase receipt stores upstream and canonical receipt digests, and `phase verify` re-reads their semantics as well as detecting later byte changes. Overall phase truth remains `partial`, and gallery visual, license, and implementation claims always remain `not_verified`.
176
+
177
+ ## Bounded Promotion
178
+
179
+ ```bash
180
+ yam benchmark report --label "scout strategy" --candidate-digest <sha256> --baseline-digest <sha256> --sample seed-1:0.82:0.71 --sample seed-2:0.79:0.70 --unit score --evidence-source "fixed local fixture" --target higher --min-samples 2 --min-mean-delta 0.05 --min-win-rate 0.5 --json
181
+ ```
182
+
183
+ This command records paired arithmetic; it does not run the benchmark. A `keep` decision still has `measurement_truth: operator_asserted` and overall `truth_status: partial`.
158
184
 
159
185
  ## Tool Doctor / Proof / Safety
160
186
 
package/README.md CHANGED
@@ -99,6 +99,8 @@ yam hook status --global
99
99
 
100
100
  The profile installs `UserPromptSubmit` and `Stop` handlers. At `Stop`, yam checks the latest assistant message with the same read-only Study Note Guard used by `yam study-note check`. If changed artifacts lack the required role, execution point, before/after, expected behavior, syntax/structure, verification, limits, or relevant architecture hygiene, Codex receives one correction prompt. A second failed check warns but does not loop forever. If Git change scope is unavailable, the guard reports partial truth and keeps a manual-inspection warning visible instead of claiming the project is clean. The hook never writes the Study Note or runs verification for the agent.
101
101
 
102
+ Hook stdin is limited to 1 MiB. Malformed JSON or an oversized payload produces a valid fail-open response without echoing the rejected content, deriving hook context from it, or mutating the workspace. Other CLI commands that read piped text use a 4 MiB limit and fail closed when it is exceeded.
103
+
102
104
  `yam hook status` reports stale or missing command targets as `broken` and exits nonzero. Run `yam hook enable <profile> --global` again to create a timestamped backup, preserve unrelated hooks, and migrate that profile to the current installed path and event coverage. Restart Codex or open a new task after changing hooks.
103
105
 
104
106
  ## Install
@@ -120,7 +122,7 @@ yam install --replace-user-skill quick
120
122
 
121
123
  Repeat `--replace-user-skill <name>` for each reviewed conflict. Unproven legacy, retired, and Codex mirror directories are preserved rather than deleted by name.
122
124
 
123
- A successful install writes `~/.agents/skills/.yam-flow-install-receipt.json`. The receipt records the package version, source identity, install timestamp, destination, managed skill inventory, and per-file hashes. `yam status` independently recomputes source and installed hashes, so a stale package install, local file change, unexpected file, or modified receipt is reported as drift.
125
+ A successful install writes `~/.agents/skills/.yam-flow-install-receipt.json`. The receipt records the package version, source identity, install timestamp, destination, managed skill inventory, and per-file hashes. Integrity paths and digests use locale-independent ordinal ordering; receipts written by yam 2.5.0 and earlier are also checked against their stored legacy order during upgrade. `yam status` independently recomputes source and installed hashes, so a stale package install, local file change, unexpected file, or modified receipt is reported as drift.
124
126
 
125
127
  The receipt is local integrity provenance, not a cryptographic signature or a security boundary against another process running as the same OS user. An actor that can rewrite both the receipt and every recorded file can forge local ownership evidence.
126
128
 
@@ -148,7 +150,11 @@ yam update apply --component yam
148
150
  yam update apply --all --json
149
151
  ```
150
152
 
151
- `--all` processes Scrapling, then Insane Search, then yam so the running updater replaces itself last. It stops at the first failed or manual-only component. Each attempt writes a component receipt under `~/.local/state/yam/update-receipts/` with the old/new version, source revision, checks, side effects, outcome, and rollback guidance. A lock prevents concurrent apply runs.
153
+ `--all` processes Scrapling, then Insane Search, then yam so the running updater replaces itself last. It stops at the first failed or manual-only component. After the global npm install, yam resolves `npm root -g`, the installed package manifest and bin mapping, the first `yam` on `PATH`, canonical realpaths, and the observed version before any `yam install` mutation. A same-version PATH shadow, malformed package, or identity mismatch fails closed; legitimate multi-hop symlinks remain valid. Rollback repeats the same identity check before rollback-side yam commands.
154
+
155
+ A yam update is successful only after the installed version and status checks plus a final read-only `yam doctor --json` return the expected healthy contract. Doctor failure triggers the existing rollback path, and rollback is considered automatic only when its own identity, version, status, and Doctor checks pass. The deepest actionable rollback or Doctor cause remains primary even if receipt persistence also fails. Each attempt writes a bounded, redacted component receipt under `~/.local/state/yam/update-receipts/` with the old/new version, source revision, executable identity, checks, side effects, outcome, and rollback guidance. The aggregate apply response emits and verifies the strict `yam.gate-result.v1`; an already-held lock also returns a blocked gate without mutating components. A lock prevents concurrent apply runs.
156
+
157
+ Effective yam identity currently verifies POSIX-style executable/symlink layouts through `which` and canonical realpaths. Windows npm `.cmd` shim identity is intentionally unverified and fails closed until a dedicated shim parser and fixture exist.
152
158
 
153
159
  Scrapling updates install an exact stable PyPI version into a new versioned virtual environment. `pip check`, ordinary HTTP extraction, and headless browser extraction must pass before the executable symlink changes atomically; the previous environment is retained. An existing environment must have a matching `.yam-scrapling-install.json` ownership marker before yam will replace its link. Insane Search uses only the official `codex plugin` commands. yam never edits `.codex/plugins/cache`, never removes the plugin first, and returns `manual_plugin_update_required` when the installed Codex CLI cannot update it safely in place.
154
160
 
@@ -214,6 +220,13 @@ yam ueye asset add --manifest .yam/ueye/assets.json --id official-logo --file ./
214
220
  yam ueye asset verify --manifest .yam/ueye/assets.json --json
215
221
  yam ueye revision archive --file .yam/screens/home.png --round 1 --artifact-id home --root .yam/ueye/revisions --json
216
222
  yam ueye revision verify --manifest .yam/ueye/revisions/manifest.json --json
223
+ yam ueye production canvas create --session-id campaign --title "Campaign plan review" --demand-kind multi_asset_production --demand-evidence "Five coordinated campaign assets require one bounded review package" --artifact-spec ./canvas-artifact.json --json
224
+ yam ueye production canvas comment --session-path .yam/ueye/design-production/campaign/plan-review.json --render-path .yam/ueye/design-production/campaign/canvas.html --comment-id finding-1 --artifact-id campaign-plan --anchor-kind line --locator L12 --finding "CTA hierarchy is ambiguous" --requested-change "Make the primary CTA explicit" --json
225
+ yam ueye production canvas close --session-path .yam/ueye/design-production/campaign/plan-review.json --render-path .yam/ueye/design-production/campaign/canvas.html --verdict request_changes --json
226
+ yam ueye production revision init --session-id campaign --json
227
+ yam ueye production gallery verify --manifest-path .yam/ueye/design-production/campaign/gallery.json --json
228
+ yam ueye production finalize --demand-kind multi_asset_production --demand-evidence "Five coordinated campaign assets require one bounded review package" --canvas-session-path .yam/ueye/design-production/campaign/plan-review.json --revision-state-path .yam/ueye/design-production/campaign/revision-state.json --gallery-manifest-path .yam/ueye/design-production/campaign/gallery.json --receipt-path .yam/ueye/design-production/campaign/phase-receipt.json --json
229
+ yam ueye production phase verify --receipt-path .yam/ueye/design-production/campaign/phase-receipt.json --json
217
230
  yam proof --route ueye --truth verified --visual "implementation screenshot evidence recorded" --design-completion '{"completion_claim":"done","has_implementation_screenshot":true,"design_quality":"pass","states_checked":true,"mobile_checked":true,"contrast_checked":true,"cta_checked":true,"direction_locked":true,"truth_status":"verified"}'
218
231
  yam media proof --requested --attempted --output ./generated.png --wait-loop --json
219
232
  yam proof --route mission --mission-envelope '{"agent_id":"implementer","assigned_scope":"target component","changed_files":["src/file.ts"],"verification_hint":"npm run typecheck","truth_status":"partial"}'
@@ -255,6 +268,8 @@ yam status
255
268
 
256
269
  After `yam status` reports all skills and the install receipt as `ok`, restart Codex so the refreshed skills reload.
257
270
 
271
+ Before packaging or publishing, `verify:self` inspects the exact file list returned by `npm pack --dry-run --json --ignore-scripts`. The release gate scans regular UTF-8 text files up to 2 MiB for high-signal private-key, npm, GitHub, OpenAI, Anthropic, and AWS credential patterns. Findings expose only the pattern id, package-relative path, and line number; matched text is never printed. Binary, symlink, non-regular, unreadable, outside-root, and oversized entries are reported as skipped rather than silently represented as scanned.
272
+
258
273
  Publishing still requires confirming the final npm package name and account access.
259
274
 
260
275
  ## Trust Kernel
@@ -316,6 +331,10 @@ These shapes keep reports machine-readable without turning normal work into a he
316
331
  - Ueye design brief and anti-slop review: `$ueye` reports can record operator-provided brief dimensions, constraints, invented metrics, placeholder copy, generic visuals, and custom anti-slop blockers. P0 anti-slop findings block `done` claims.
317
332
  - Ueye deep visual review: `$ueye` can record acceptance criteria, touched/read/verified files, skipped checks, residual risks, stop condition, resume hint, design-system evidence, implementation evidence, and a state matrix so serious UI work can carry Deep-grade verification without leaving the Ueye route.
318
333
  - Ueye asset/revision integrity: `$ueye` can record license/provenance and protected/editable flags for local references, then preserve pre-edit artifacts in hash-verified numbered rounds.
334
+ - Demand-gated design production: when repeated Plan Review or large multi-asset work creates real coordination demand, Ueye can add a local static Canvas-lite review, at most two finding-backed revision rounds, a final gallery manifest, and one phase receipt. One-off review and single-asset work stay on the ordinary Ueye/Mission path. Integrity evidence never becomes proof of visual quality, licensing, or implementation correctness.
335
+ - Bounded promotion receipt: `yam benchmark report` can compare paired candidate/baseline measurements under explicit sample, mean-delta, and win-rate thresholds. Arithmetic is verified, while measurement provenance remains `operator_asserted` and overall truth stays `partial`.
336
+ - Honest capability matrix: `yam tools doctor --json` reports feature maturity separately from observed runtime readiness; instruction-only or unprobed capabilities are not reported as executed.
337
+ - Strict gate result: release, update, benchmark-promotion, and Mission completion boundaries emit a digest-bound `yam.gate-result.v1` and fail closed on missing or inconsistent required evidence.
319
338
 
320
339
  ## Ueye Capture And Compare
321
340
 
@@ -327,6 +346,7 @@ yam ueye compare --reference ./reference.png --actual .yam/screens/home.png --js
327
346
  yam ueye preflight . --json
328
347
  yam ueye asset verify --manifest .yam/ueye/assets.json --json
329
348
  yam ueye revision verify --manifest .yam/ueye/revisions/manifest.json --json
349
+ yam ueye production --help
330
350
  yam ueye report --reference ./reference.png --actual .yam/screens/home.png --brief-dimension "primary CTA clarity" --constraint "mobile first" --anti-slop "placeholder copy remains" --acceptance-criterion "pricing card CTA remains visible on mobile" --design-system-evidence "uses existing button token" --implementation-evidence "browser screenshot reviewed" --state-check default:pass --state-check mobile:partial --skipped-check "hover state not checked on touch viewport" --residual-risk "tablet breakpoint still needs visual pass" --stop-condition "stop after primary states are checked and residual risk is recorded" --resume-hint "capture tablet screenshot next" --completion-claim done --design-quality pass --direction-locked --reference-read --states-checked --mobile-checked --contrast-checked --cta-checked --provider-context local --execution-surface in-app-browser --browser-surface in-app-browser --preserved-state --json
331
351
  ```
332
352
 
@@ -338,6 +358,8 @@ yam ueye report --reference ./reference.png --actual .yam/screens/home.png --bri
338
358
 
339
359
  `preflight` does not claim visual verification. It is a pre-work checklist for reference source, target states, mobile/responsive needs, CTA/contrast/accessibility risk, screenshot availability, and likely P0/P1 candidates.
340
360
 
361
+ The design production phase is deliberately dormant by default. Use it only when repeated plan annotation or a large coordinated asset set makes prose/file-by-file review costly. The operator-asserted demand trigger is recorded before Canvas creation and must match at finalize. Canvas is static local HTML with no server; its closed `request_changes` session binds one canonical `revision-state.json`, so init/record/show/finalize cannot select an alternate state to reset the two-round budget. Each recorded round must link a current Canvas comment and a newly archived Ueye revision created within that review boundary; the final gallery verifies path/hash/dimension/final-round linkage only and must be created no earlier than Canvas close or the final revision record. `finalize` binds SHA-256 digests for Canvas, revision state, and gallery into an immutable receipt, while `phase verify` re-reads nested upstream semantics and detects later evidence changes. Overall truth remains `partial`, correctness claims remain false, and a two-round unresolved stop remains draft.
362
+
341
363
  Generated media can guide visual direction, but it cannot prove the implemented UI by itself:
342
364
 
343
365
  ```bash
package/ROADMAP.md CHANGED
@@ -172,7 +172,7 @@ Tasks:
172
172
 
173
173
  - Add `.yam/memory/records/*.json` storage. Done.
174
174
  - Add `yam memory init/add/list/summary/resolve`. Done.
175
- - Add lightweight secret-pattern blocking. Done.
175
+ - Add lightweight secret-pattern blocking, including an actual npm dry-run packlist release guard with redacted findings. Done.
176
176
  - Teach context reuse to prefer `summary.md`, not full record reads. Done.
177
177
  - Keep memory opt-in only. Done.
178
178
 
@@ -308,6 +308,7 @@ Tasks:
308
308
  - Keep `yam-lite` advisory-only through `UserPromptSubmit`. Done.
309
309
  - Add Study Note `UserPromptSubmit` reminder plus one-pass `Stop` completion gate. Done.
310
310
  - Detect broken hook targets and migrate stale paths without replacing unrelated hooks. Done.
311
+ - Bound hook/general stdin and fail open safely for rejected hook payloads. Done.
311
312
  - Add `references/tool-trust-layer.md`. Done.
312
313
  - Add read-only `yam tools doctor`. Done.
313
314
  - Add `yam proof` summary command. Done.
@@ -318,6 +319,8 @@ Tasks:
318
319
  - Add shallow `.sql` destructive keyword scan. Done.
319
320
  - Add `yam proof write`. Done.
320
321
  - Prepare npm/npx package metadata and dry-run packaging. Done.
322
+ - Make integrity-critical install and Ueye manifest ordering locale-independent. Done.
323
+ - Require a final read-only Doctor contract for yam update and rollback success. Done.
321
324
  - Add small route-scoped trust kernel: truth caps, fake/real policy, runtime truth matrix, and completion proof object. Done.
322
325
 
323
326
  ### 16. Deferred Triggers
@@ -432,7 +435,7 @@ Keep out for now:
432
435
 
433
436
  #### Plan Review Canvas Lite
434
437
 
435
- Status: deferred until repeated real-use demand.
438
+ Status: available only inside the opt-in Demand-Gated Design Production Phase.
436
439
 
437
440
  Trigger:
438
441
 
@@ -440,15 +443,47 @@ Trigger:
440
443
  - Terminal-only approval causes revision ambiguity or costly re-reading.
441
444
  - A local browser review surface would materially shorten an approved Mission or Ueye feedback loop.
442
445
 
443
- First shape:
446
+ Implemented shape:
444
447
 
445
- - local-only artifact review.
446
- - anchored comments and approve/request-changes verdict.
447
- - explicit session end and bounded idle shutdown.
448
- - Host/Origin checks, path confinement, and sandboxed artifact rendering.
448
+ - local-only, path-confined static HTML artifact review with no server or background process.
449
+ - exact line/text anchors and bounded operator-asserted image regions.
450
+ - source hash and exact-anchor revalidation before comments, close, and finalize.
451
+ - anchored findings plus explicit approve/request-changes verdict and session end.
449
452
 
450
453
  Keep out for now:
451
454
 
452
455
  - default local server.
453
456
  - remote sharing or hosting.
454
457
  - automatic implementation start without an explicit approval verdict.
458
+
459
+ #### Demand-Gated Design Production Phase
460
+
461
+ Status: implemented as an opt-in phase; remain dormant until repeated plan review or large multi-asset design production creates real coordination cost.
462
+
463
+ Trigger:
464
+
465
+ - Plan review repeatedly needs exact-element annotations that prose feedback cannot express efficiently.
466
+ - A Ueye task produces several related visual assets that must preserve cross-asset consistency and provenance.
467
+ - Reviewers need bounded before/after comparison or a packaged overview instead of inspecting files one by one.
468
+
469
+ Phases:
470
+
471
+ 1. Record the operator-asserted demand kind and concrete evidence before Canvas creation, then require an exact match at finalize.
472
+ 2. Run Plan Review Canvas Lite as a local-only, explicitly closed review session.
473
+ 3. Bind one canonical revision state to the closed Canvas path/digest, then run at most two Canvas-comment-linked revision rounds, requiring at least one new hash-verified Ueye archive in the current review boundary per round.
474
+ 4. Write and verify a final gallery manifest with artifact ids, roles, provenance, final-round revision references, dimensions, hashes, completion state, and final paths.
475
+ 5. Finalize one immutable phase receipt with Canvas/revision/gallery and canonical receipt digests only when the demand trigger, closed Canvas, archive chronology, terminal revision state when required, matching session ids, and gallery integrity agree; re-verify it to detect later evidence changes.
476
+
477
+ Entry and stop rules:
478
+
479
+ - Enter only after the trigger appears in real work; a one-off plan, screenshot review, or single-asset edit stays on the existing Ueye/Mission path.
480
+ - Each round requires a concrete finding from the bound Canvas; alternate state paths fail closed, and the phase ends after acceptance, two rounds, or a blocked integrity gate, whichever comes first.
481
+ - The gallery is an inspection and packaging artifact, not proof that visual quality, licensing, or implementation correctness passed.
482
+ - A two-round-limit stop may finalize only a draft gallery; it cannot be upgraded into a packaged or complete result.
483
+
484
+ Keep out for now:
485
+
486
+ - automatic creation of a design runtime or typed JSONL message bus.
487
+ - unbounded revision loops or autonomous approval.
488
+ - remote gallery hosting, public sharing, or background review services.
489
+ - replacing protected source assets or weakening existing provenance and `do_not_replace` checks.