@@ -5177,3 +5177,5 @@ Before: managed project/thread verbs had no Console conversation area. After: fi
2026-10-21T01:28:05Z | Darkwing | row 232 #1734 installer I1 build, round 1 in review | Before: stack-release.sh managed only user units (systemctl --user), and stack-copy.sh had no bundle copy. After: --units external (adopt, activate, rollback --to, status, confirm, revert, gate --since, AWAITING-UNITS, stale-start, external-pm, --plan --expect-from) and stack-copy check --units external, copy --bundle FILE SHA, wrapper ID --create; user mode byte-identical to the base by test. First build 0af0c73c6 on 00d4cc1f6; rebased onto row 200 (cb5fdb064) as a0ffabc3f on darkwing/row232-r1; --sso refused under external (D9), row 200 config_checks run under external (D10). Gate on Sage's slot (sage-1618): cli 561/0, every scripts/test-*.sh green; 17/17 mutants killed. Results commit 84f1a91e6 (pushed, seat branch only). Manifest 7a3b4ea1 (9 paths), queue revs 2595-2596, request comment 29825, reviewer Filbert. Packet agents/darkwing/work/queue-232/BUILD.md.
2026-10-21T04:50:44Z | Darkwing | row 233 #1735 installer I3 build, round 1 in review | Before: root had no upgrade driver for root-owned units and no host run sheet; stack-release.sh had no rehearse --backup last and no external plan refusals. After: scripts/stack-upgrade.sh upgrade and rollback (r6 A1-A5, A2f, R1-R4) with 20 tests, docs/guides/host-run-sheet.md, TOOLS.md lines, and on Sage's rulings stack-release.sh --backup last, BACKUP_STORE and the --plan refusals open-activation and migrate-required (3 tests). Base e65a3ab4d (row 232's landing). Gate on Sage's slot (sage-1704) on d99166ade: cli 616/0, every scripts/test-*.sh green, 1201/0 summed by awk; m1-m8 8/8 killed. Correction: the process sweep after the gate found an orphaned sleep 60 from the lock test's flock holder (N1); 08db6ac3f fixes it test only, Sage ruled the gate stands (sage-1707), rerun c0 20/0 and m1 killed with 0 left (sage-1708). Tip 1a1dc80ca (pushed, seat branch only). Manifest 464ce9eb (7 paths), queue revs 2644 and 2647, request comment 29901, reviewer Filbert. Packet agents/darkwing/work/queue-233/BUILD.md.
2026-10-21T06:37:41Z | Darkwing | row 240 #1746 installer I4 build, round 1 in review | Before: root had no host check for the bwrap AppArmor profile, its pins or a boot unit, and stack-upgrade.sh exited 1 args-failed when the args move after A5 failed, while exit 1 means the old copy runs. After: scripts/case1-hostcheck.sh (seven items, --check, --enforce, --upstream), scripts/case1-pins.sh, mosaic-hostcheck.service and 16 tests; the args move failure exits 5 args-failed, documented in TOOLS.md and run sheet section 6 and tested; run sheet section 3 puts the pinned npm on PATH and names the bin/claude.exe --claude path; sections 8 and 10 have precheck lines. Verification: slot run r1 on 47ec9fe2f failed at the singles (the new N1 test's after hook threw ENOENT after the fixture cleanup removed the root); b45852daa drops the hook; r2 on b45852daa green: singles 16/0 and 21/0, c0 plus M1-M8 8/8 killed, cli 639/0, scripts 585/0. Candidate darkwing/row240-r3 ad1b23ab2 on c771a36f4, manifest 573ece95 (9 paths), revs 2694 and 2695, comment 29943.
2026-10-21 16:18:11 UTC | Q195 WordCraft evaluation (Vikunja #448) | Before: no source-level or build measurements existed for the browser editor decision. After: report records two reproducible Trunk builds (same four artifact hashes), CSP and iframe requirements, pane/API limits, synthetic DOC/DOCX/Markdown conversions, MCP surface, thesaurus count and web dependency/source scale. WordCraft source stayed in the scratch clone; no Console code or live stack changed. Report staged on louie/wordcraft-eval; CI queue guard and push not yet run.
@@ -1419,3 +1419,4 @@ are never rewritten or removed; corrections are new entries.
2026-10-21T06:47:54Z | researcher | row 228 (#1729) round 3 in review (rev 2702; start rev 2700) | rebase of r2 onto the 234 landing c771a36f4 as researcher/row228-r3 cf18c42b9 (one commit, pushed) with Webby's round 2 N1 (:711 and :718); manifest 82cf98c6 (3 files); slot sage-1796: session.test 13 + host.test 42 = 55/0, manifest OK before and after, busy228.sh copy named in the clear; r2 94/0 and M1 killed stand (seat blobs unchanged); request attempt left in requesting state (lock held by sage-238-review-2b when the outcome rev was written, exit 3; transport said failed pre-send, no token), Sage resolves and posts as jarvis; packet agents/researcher/work/queue-228/r3
2026-10-21T07:29:23Z | researcher | row 228 (#1729) landed as 86249ac55 (pushed 07:25Z by Sage) | patch-id b6ffe31feb0d matches my r3 candidate cf18c42b9 (checked here against origin/refactor); Sage combined gate with 238: seat 165/0, cli 640/0, scripts 585/0; queue note rev 2725, done rev 2727, #1729 closed comment 29966 (sage-1824); q228r2 worktree removed, branches researcher/row228, -r2 and -r3 stay on origin and locally; packets agents/researcher/work/queue-228 r1 r2 r3 uncommitted
2026-10-21T15:19:14Z | Sage (Opus 5.5, 1ef1e4f8) | MVP push 10-21 afternoon: rows 249, 197 proof 3/4, 222 singles, 66 r4d, queue-commit | 249 landed 9de5a57ab (+7b9737953 DEFERRED N1, #1751 closed, Vikunja 445 c442); 197 proof 3 rc=1 on a driver defect, Herb's fix a5b636750 to Webby, proof 4 set up in sage-r197p4; 222 singles 34/34 and 5 mutants killed (sage-2028); 66 round 4 in review (82c830779, c30083/30084); queue revs 2642-2904 committed 0636721e6
2026-10-21T16:18:11Z | Louie (T3, louie-0001) | Vikunja #448, Q195/Q196 WordCraft evaluation | Two identical-hash `trunk build --release` outputs and all requested source/fixture measurements recorded in `docs/plans/2026-10-21_q195-wordcraft-eval.md`; queue next returned nothing; report and log entries staged, local commit and origin push pending.
Measured 2026-10-21 from `/mnt/storage/scratch/louie-wordcraft`, cloned from the protected source at `e05b7fe86f3b85454000dffc321de638d7009817` (WordCraft 0.9.0). No source was changed.
## Measured
### Browser build
Command, twice, from `apps/wordcraft-web`: `nice -n 19 trunk build --release` (`CARGO_BUILD_JOBS=4`). Toolchain: rustc/cargo 1.99.1, Trunk 0.22.0, wasm-bindgen 0.2.129, wasm-opt 131. UTC build 1: 16:02:29–16:09:02, 392.786 s. Build 2: 16:09:43–16:12:35, 172.324 s. Both succeeded; engine emitted three dead-code warnings.
The two sorted `sha256sum` manifests diffed empty. Trunk's `data-wasm-opt="z"` stages a 59,077,399-byte WASM file, then applies `-Oz`. The generated JS constructs a `WebAssembly.Module`.
### CSP
Console currently sends `default-src 'self'; script-src 'self'; style-src 'self' 'unsafe-inline'; connect-src 'self'; font-src 'self'; object-src 'none'; base-uri 'none'; frame-ancestors 'none'; form-action 'self'` (`packages/webui/src/serve.mjs:495`). `WebAssembly.Module` needs `'wasm-unsafe-eval'` in `script-src`. WordCraft's PDF preview uses a `blob:` URL in an iframe (`apps/wordcraft-web/src/web.rs:548-604`), so its policy needs `frame-src 'self' blob:`. With an iframe pane, the **WordCraft response route** also needs `frame-ancestors 'self'`; keep the Console response's `'none'`. Same-origin iframe loading is already allowed by the Console's `default-src 'self'` fallback. Direct canvas mounting instead requires the Console document's `script-src` and `frame-src` changes, while its `frame-ancestors 'none'` can remain.
No `worker-src` or GPU-specific CSP directive is needed; the web renderer has no worker thread and WebGPU/WebGL2 are browser APIs. Commands: `nl -ba packages/webui/src/serve.mjs | sed -n '495p'`; `rg -n 'WebAssembly|worker|new Worker|blob:' dist/web/wordcraft-web-*.js`. The required `script-src` exception and iframe policy differ from Q167 D3's no-CSP-loosening ruling.
### Pane and page API
`index.html:10-18` currently makes the body and canvas fill the viewport. `web.rs:26-43` looks up a canvas by ID and gives it to eframe; eframe 0.36.2 observes the canvas content box with `ResizeObserver` (`eframe-0.36.2/src/web/events.rs:1001-1074`). **Inference:** it can fit a pane if the host gives the canvas a sized, positioned container, or if the page hosts the full build in a sized iframe. It is not a drop-in DOM editor. The `Session` and `WordApp` stay inside the WASM closure (`web.rs:60-82`); file open uses the browser picker (`web.rs:214-230`). No exported JavaScript API, `postMessage` bridge, or page event reports the open document, selection, or edits. The browser build explicitly has no TCP control channel (`main.rs:7-10`). Commands: `rg -n 'wordcraft_canvas|ResizeObserver|postMessage|TCP' apps/wordcraft-web/src apps/wordcraft-web/index.html`.
### Format fixtures
Fixture: my OOXML DOCX with a Heading 1, italic text, one footnote and one comment; LibreOffice 26.8.0.3 converted it to `.doc`. Converting that `.doc` back to DOCX in LibreOffice confirmed both note and comment were in the fixture. Commands: `libreoffice --headless --convert-to doc`; `wordcraft-cli inspect <fixture.doc>`; `wordcraft-cli convert <fixture.doc> <roundtrip.docx>`; `wordcraft-cli convert <fixture.doc> <export.md>`; `wordcraft-cli convert <fixture.md> <roundtrip.docx>`; `wordcraft-cli convert <roundtrip.docx> <roundtrip.md>`; `inspect` on both DOCX outputs.
| Round trip | Survived | Lost or changed |
|---|---|---|
| `.doc`→`.docx` | Heading 1, italics, footnote reference and body | Comment; WordCraft inspect reports `comments: 0` |
| `.doc`→`.md` | Heading and italics | Footnote reference/body and comment are absent from Markdown output |
| `.md`→`.docx`→`.md` | Heading and italic formatting | `[^1]` and its definition remain ordinary text, not a semantic footnote; exporter escapes the brackets |
The `.doc` importer drops comment references (`crates/docbin/src/lib.rs:538`); WordCraft's Markdown subset has no footnote construct (`crates/formats/src/markdown.rs` module description). Fixture and all conversions stayed under `/mnt/storage/scratch`.
### Thesaurus and proofing
Python count of `crates/engine/src/cmd/review.rs:914`'s `T`: **29 headword entries, 122 synonym values**. It is a built-in table. Proofing loads Hunspell `.aff`/`.dic` spelling dictionaries from `WORDCRAFT_DICTIONARIES` or system/LibreOffice folders on desktop; the web has no system dictionary (`crates/proof/src/hunspell.rs:1-10,70-124`). Count command: Python regex over the `T` initializer in `review.rs`. **Inference:** a larger thesaurus does not plug into that spelling dictionary path; it needs a separate thesaurus data source or changes to `T`.
### MCP and review scale
`crates/mcp/src/tools.rs` defines 16 tools: `list_commands`, `execute`, `batch`, `new_document`, `open_document`, `save_document`, `type_text`, `select_text`, `get_text`, `inspect_document`, `render_page`, `parity`, `screenshot`, `click`, `key`, `ui_inspect`. `wordcraft-cli mcp` serves newline-delimited JSON-RPC on stdio; `--connect HOST:PORT` bridges to a desktop app's loopback TCP control server (`127.0.0.1`, `apps/wordcraft/src/control_server.rs:36-44`). It can run headless or drive the connected desktop app; **it cannot drive the browser document**. Inspection command: `sed -n '60,155p' crates/mcp/src/tools.rs`, with transport in `crates/mcp/src/server.rs`, `crates/mcp/src/backend.rs` and `apps/wordcraft/src/control_server.rs`.
`cargo tree -p wordcraft-web --target wasm32-unknown-unknown --edges normal` resolves 15 local WordCraft crates and **199 third-party packages in Cargo.lock** (unique name/version pairs; the web app does not compile `wordcraft-mcp`). Physical Rust lines under each crate's `src/**/*.rs`:
Line counts cover source files in those resolved crates, including cfg-specific files. The whole workspace lock has 558 package records (538 third-party); 339 third-party records are outside the web target's dependency tree.
Commands for review scale: `cargo tree -p wordcraft-web --target wasm32-unknown-unknown --edges normal --format '{p}'`; Python matched unique name/version pairs to `Cargo.lock` and summed `src/**/*.rs` lines for the resolved local crates. The browser build, fixtures and source reads were all performed on the scratch clone.
## Inferred design signal
WordCraft brings a Word-like canvas interface and working `.doc` import, but the browser artifact is a 44.18 MB standalone app with no Console-facing document API; embedding its canvas is feasible, while page control requires new bridge work. Its `.doc` import loses comments and Markdown loses footnote semantics. Any use of this web build in the Console also depends on CSP exceptions that conflict with Q167 D3, so the UI/engine option is technically possible but not currently within the approved CSP boundary.
Reference in New Issue
Block a user
Blocking a user prevents them from interacting with repositories, such as opening or commenting on pull requests or issues. Learn more about blocking a user.