fix(package): books.start runs the real integrity check (U0b)

books.start passed Integrity::default() to the attention engine, so it
asserted "database matches, no file failures". On a book whose database
differs from the journal, or whose stored file is missing or corrupt, the
viewer showed the database/stored-files items and the server did not: the
two lists diverged exactly where they matter most.

Call find, which computes the check: every distinct stored blob is read
and hash-checked once (a damaged blob is still reported per attachment
filed from it), and Store::disk_check now makes the viewer's comparison
through a snapshot of its data directory instead of reporting a match.

The parity test now damages its own fixture (removes the receipt's blob,
then changes a projected account row) and asserts both lists still agree
item for item and both name the damage. On the demo books (138
attachments, 138 distinct blobs, debug build) books.start takes about
0.26 s warm, 0.29 s cold, so the real check costs no decision.
This commit is contained in:
swaits committed 2026-10-27 06:12:55 -06:00
1 parent 0cf2f8f5c5
commit 26d3a9941b
6 files changed
+146 -27

No files matched your search

+9 -2
View File
@@ -1246,8 +1246,15 @@ Each unit follows the 8.0.4 template. "A-n" is an owner answer numbered in 8.3.1
- `books.start` lists at most 12 attention steps (the eventual
`needs_attention` top 12; counts by kind come with P5), each step's
`why` cut to 160 characters (a free-text description could otherwise
push the result past 8 KB), and passes `Integrity::default()`: the
server's own damage check is `books.verify`.
push the result past 8 KB), and calls `find` — the real integrity
check, so a damaged database or stored file produces the same items
for the server as for the viewer. `Store::disk_check` makes the
viewer's comparison (a snapshot of its data directory) rather than
assuming a match; the check hashes each distinct stored blob once and
replays the journal once. On the demo books (138 attachments, 138
distinct blobs, debug build) `books.start` takes about 0.26 s warm,
0.29 s cold; a real book's cost scales with its stored bytes, and a
cache would be the next step if that ever exceeds a second.
- The W-9 and reconciliation prompts and the 1099 predicate moved to
`ledger-package`; `pages/parties.rs`, `pages/reconciliation.rs` and
`Books::files_1099` delegate to them (two files beyond the Build's