Skip to content

Fix embeds intermittently lost until page refresh#1

Closed
RobbyV2 wants to merge 1 commit into
mainfrom
worktree-embed-resolve-race
Closed

Fix embeds intermittently lost until page refresh#1
RobbyV2 wants to merge 1 commit into
mainfrom
worktree-embed-resolve-race

Conversation

@RobbyV2

@RobbyV2 RobbyV2 commented Jul 9, 2026

Copy link
Copy Markdown
Owner

Problem

Embeds occasionally never render until the page is refreshed.

Embed resolution is fully async on the backend: a fire-and-forget task fetches the link preview and broadcasts a separate EmbedsResolved ws event, decoupled from the Message event with no ordering guarantee tying the embed to the message being present in the store.

The embeds_resolved handler applied embeds only through patchMessage, which silently no-ops when the target message isn't in any cache at that instant (message merged after the event, or the real id still sitting in the optimistic outbox). Separately, merge gives precedence to incoming messages, so a late duplicate message echo carrying embeds: [] (the POST response / ws echo of a freshly sent message) clobbers embeds already applied. Either path drops the embed until a refresh reloads history with embeds baked in from the DB.

Fix

Buffer resolved embeds in a bounded (256-entry FIFO) map keyed by message id, and enrich every recent-message insertion (drain, ws message merges for channel and thread, openChannel/openDm/openThread fetches, poll refresh) from it via a small applyEmbeds helper. Embeds now survive regardless of EmbedsResolved vs Message ordering. embeds_removed keeps the buffer consistent so a removed embed doesn't reappear on a later insert.

Tests

Added two store_reducer cases: embed resolving before the message is inserted still lands, and a later duplicate message echo does not clobber resolved embeds. Full suite 47/47, eslint clean, tsc --noEmit clean.

🤖 Generated with Claude Code

EmbedsResolved arrives as a separate ws event from the message it
belongs to, with no ordering guarantee tying it to the message being
present in the store. The handler applied embeds only via patchMessage,
a silent no-op when the target message is not yet in any cache; merge
also lets a later duplicate message echo (embeds: []) clobber embeds
already applied. Both drop the embed until a refresh reloads history
with embeds baked in.

Buffer resolved embeds in a bounded map keyed by message id and enrich
every recent-message insertion from it, so embeds survive regardless of
event ordering.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
@gitnotebooks

gitnotebooks Bot commented Jul 9, 2026

Copy link
Copy Markdown

Review these changes at https://app.gitnotebooks.com/RobbyV2/RChat/pull/1

@RobbyV2 RobbyV2 closed this Jul 9, 2026
@RobbyV2 RobbyV2 deleted the worktree-embed-resolve-race branch July 10, 2026 19:48
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