Files
buzz/desktop
Duncan da94c3e127 fix(readState): round-4 v4 conformance — deferred-enqueue latch, boundary validation, behavioral witnesses
Non-reentrant drain transaction via deferred-enqueue latch:
- pendingOverrideIntentStore gains beginTransaction/commitTransaction; any
  enqueue() for a locked channel is buffered, not applied; commitTransaction
  flushes the buffer as the new queue entry for the next drain pass.
- drainPendingIntents wraps each channel iteration in beginTransaction /
  try-finally commitTransaction; no post-callback gen re-check or rollback
  code is needed (Amendment A holds structurally, not by compensation).
- Step-1 storage-failure rollback retained (register+receipt+publishable+
  extraSlots only; frontier advance is monotone and safe to leave).
- markChannelReadDirect: frontier advance stays before the register check
  (spec order: frontier → C-bump); for already_inactive the advance is
  correct; for step-1 failure it is idempotent on the next drain attempt.

Boundary validation on hydrated intent fields (readStateStorage.ts):
- readTarget: must be a finite integer in [0, 0xFFFFFFFF]; 1e300 or NaN
  are rejected, preventing Date.toISOString() RangeError in the drain.
- sourceScope: constrained to the ForcedUnreadSource vocabulary
  ("inbox" | "manual"); unknown strings skip the intent.
- priorForcedEntry: validated via parseForcedUnreadEntry (new helper);
  present-but-malformed values skip the intent; absent fields are fine.
- MAX_PROTOCOL_TIMESTAMP = 0xFFFFFFFF constant defined once and shared
  between the register validators and the new field validators.

Behavioral witnesses (Test 30/33 rewritten; Tests 36/36b/37/45/46/47):
- Test 30 (drain_gen2EnqueuedDuringReplay_bufferedUntilTransactionCommit):
  proves gen2 is buffered by latch mid-replay, gen1 commits cleanly, gen2
  appears in queue after commitTransaction flush.
- Test 33 (drain_compareDeletePreservesNewerIntent): uses direct
  pendingOverrideIntentStore.enqueue() in the outcome callback to simulate
  a concurrent pre-ready enqueue; asserts v2 blob has gen1 register but no
  pi/receipt, and gen2 is byte-for-byte correct in the queue.
- Tests 36/36b: fake scheduler fires timer callbacks; proves automatic
  second attempt fires with a fresh fetch after initialize() incomplete.
- Tests 45/46/47: hook/store round-trips via wireDrainCallback helper;
  45 drives markAt > partial frontier and asserts frontier advance,
  C-bump, persisted register, forced-source removal, versionBumps=1;
  46 asserts silent-inactive removes exactly the captured source from the
  persisted forcedUnreadStore; 47 asserts priorForcedEntry is restored
  byte-for-byte in forcedUnreadStore after post-restart refusal.

Co-authored-by: Will Pfleger <pfleger.will@gmail.com>
Signed-off-by: Will Pfleger <pfleger.will@gmail.com>
2026-08-08 12:34:22 -04:00
..
2026-08-03 21:51:17 -04:00
2026-03-09 13:02:11 -07:00
2026-06-11 15:06:24 +00:00
2026-03-09 13:02:11 -07:00

Buzz

Desktop chat shell with:

  • Tauri + React + TypeScript + Vite
  • Tailwind CSS
  • shadcn/ui-ready shared components
  • Biome (lint/format/check)
  • Feature-driven frontend structure

Scripts

  • pnpm dev - run the web frontend
  • pnpm tauri dev - run the desktop app
  • pnpm build - typecheck and build frontend
  • pnpm typecheck - TypeScript checks
  • pnpm lint - Biome lint
  • pnpm format - Biome format (write)
  • pnpm check - Biome check

Structure

  • src/shared - reusable app-wide code (ui, lib, styles)
  • src/features - feature modules (vertical slices)
  • src/app - top-level app composition