Skip to content

A reply counts as read once delivered - #25

Merged
rennf93 merged 1 commit into
masterfrom
replies-read
Oct 22, 2026
Merged

rennf93 merged 1 commit into
masterfrom
replies-read

Conversation

@rennf93

@rennf93 rennf93 commented Oct 22, 2026

Copy link
Copy Markdown
Owner

A reply counts as read once it is delivered, so unread means the asks still waiting on you.

Why

unread is queued, sent or delivered (src/core.ts). An ask stays unread until you ack or answer it, which is right. A reply needs no answer, but it stayed delivered forever once it reached the asker's session. On my bus, after the 0.2.7 restart, Ledger's session shows unread 72, and all 72 are replies in state delivered; one of them arrived after the restart. 0.2.7 only covered replies handed over inside a murmur_wait.

What changed

  1. Store.markDelivered is the one rule: a reply delivery (messages.is_reply = 1) that reaches delivered ends acknowledged, with acked_at set to the delivery time. Asks are unchanged. Every path goes through it: push proof, adapter delivered, hook pull (pendingPush), read, and the wait handover, whose separate markAcked call is removed.
  2. Store.open turns reply deliveries an older version left at delivered into acknowledged (acked_at = COALESCE(acked_at, delivered_at)). It is idempotent and only runs where the store is opened: murmur init and murmur serve.
  3. README, docs/concepts.md, docs/reference/protocol.md and CHANGELOG [Unreleased] Changed.

Issue

No issue filed. Found on my bus after the 0.2.7 restart.

How it was verified

  • Tests first. On master's src the new tests fail with expected 'delivered' to be 'acknowledged' (broker: a reply confirmed by an adapter; core: a reply handed over by the hook pull; store: markDelivered and the open-time update).
  • npm run build and npm run coverage: Tests 522 passed (522), 100 percent on statements (2357/2357), branches (1327/1327), functions (438/438) and lines (2277/2277). tsc --noEmit exit 0, markdownlint 0 issues, no em or en dashes.
  • Live, two real Claude Code sessions (haiku) on this branch, isolated rig. X asked Y with a plain murmur_send (no wait), so Y's reply was pushed into X and proven by X's transcript:
    • PASS the reply pushed into X (no wait) ends acknowledged with a delivery time: {"recipient":"claude-murmur","state":"acknowledged","delivered":1,"acked":1}
    • PASS murmur status shows X with unread 0: claude-murmur busy claude unread 0
    • RESULT: PASS
  • An independent review confirmed all six claims: markDelivered is the only writer of delivered, the PR No queued_delivered note for a reply handed over in the wait #14 notice rules key off the state before the update, a reply can still go from acknowledged to replied, and murmur_ack on it is a no-op. One cosmetic point I left as is: core.read and pendingPush still emit onStateChange with to: 'delivered' for a reply that is now acknowledged; the only consumer is a no-op in src/cli.ts.

Behavior changes

  • A reply delivery ends acknowledged instead of delivered, so murmur status no longer counts replies as unread.
  • On the next murmur serve, existing reply rows at delivered become acknowledged.

@rennf93
rennf93 merged commit de7a67c into master Oct 22, 2026
21 checks passed
@rennf93
rennf93 deleted the replies-read branch October 22, 2026 08:06
@rennf93 rennf93 mentioned this pull request Oct 22, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant