refactor(web): number every session log record in the relay and publish under one lock
Summary
- The relay and the session writer both numbered records in a session log. A title or an agent switch written by the host could get one number in the log and another number in the live stream. A stream event and a host record could also reach a client out of order.
- This change gives the relay the only right to number a record. It also publishes each record in one locked step, so the number, the durable write and the delivery stay in order.
Related Issue
Refs #1070
Searched open and closed PRs for the same problem. No PR covers it. This is the first of several PRs for the read-model work in #1070.
Type of Change
- feat: new feature
- fix: bug fix
- docs: documentation only
- style: formatting or non-functional styling changes
- refactor: internal cleanup with no behavior change
- perf: performance improvement
- test: adds or updates tests
- build: build or dependency changes
- ci: CI/CD workflow changes
- chore: maintenance or tooling
- revert: reverts a previous change
What Changed
WsRelaySinknow numbers every record, also host-written ones. Newrecord_host_eventnumbers, stores and delivers a title or an agent-switch marker in one step.- The session writer no longer assigns a number. The shutdown
interruptedmarker takes its number from the relay. Without a relay it uses the next number after the last stored one. - The number, the durable write, the ring entry and the delivery to subscribers run in one critical section.
subscribeand the snapshot register in that same section, after a writer barrier. A snapshot and the live stream now split the log exactly. - A host record is refused when the writer is missing or unhealthy. Nothing is numbered or delivered in that case.
- The agent-switch marker is now durable and live under one number. A background title is now also sent live.
- The sink module splits into
sink/files so each file stays below the size limit.
How It Was Tested
-
bun run ci(Biome lint + format + imports, strict mode) -
bun run typecheck -
bun run test -
cargo clippy --all-targets -- -D warnings(in src-tauri) -
cargo test(in src-tauri) - Manual verification completed
- Not applicable
New Rust tests cover: a title and relay events written at the same time get distinct, ordered numbers; a snapshot plus the live stream equal the stored log; the marker number comes from the relay; a host record without a usable writer allocates nothing; the agent-switch marker reaches other sinks once and exists once in the log.
Screenshots or Recordings
No user-visible UI change. The change affects the host only. The Rust tests above cover the behavior.
CI & Review Gate
- All CI checks pass (PR Validation, Rust Checks, Build Verification, Security Scans)
- Code review comments from CodeRabbit / Claude have been addressed or resolved
- No unresolved review findings remain
Checklist
- My PR title follows the conventional commit format used by this repo
- I linked the related issue or explained why none exists
- I updated docs when needed
- I added or updated tests when needed
- I verified the change does not introduce unrelated modifications
- I read AGENTS.md and followed the contributor guidelines
- A human reviewed the complete diff before submission
Summary by cubic
Makes the relay the single authority for numbering session log records so the durable log and live stream can never disagree.
Previously the relay and session writer both assigned sequence numbers, so a title or agent switch could carry one seq in the log and another in the live stream, and events could arrive out of order. Now WsRelaySink numbers every record — including host-authored titles and agent switches — and assigns, persists, and delivers each record in one locked step, so the ordering guarantee holds across the replay and live handoff. The session writer no longer assigns numbers; the shutdown interrupted marker takes its seq from the relay. The sink module splits into sink/ files to stay under the size limit.
- A host record is refused when the writer is missing or unhealthy, allocating nothing.
- The agent-switch marker is now durable and live under one number, and background titles are sent live.
- Subscribe and snapshot registration run under the same lock behind a writer barrier, so snapshots and the live stream split the log exactly.
subscribereturns a head cursor, andlocal_title_generatedis added to the WS event type registry.
Refs #1070.
Summary by CodeRabbit
- Reliability
- Live session events and durable records now share a consistent sequence, supporting more orderly replay and recovery after reconnection.
- Agent switches and generated titles are recorded in session history; agent-switch records use the same sequence as their live updates.
- Session snapshots report the event-log watermark, including sequences used by events that aren’t retained in durable history.
- Snapshot and live-subscription registration are synchronized to help prevent missed or duplicated events during recovery.