Skip to content

Conversation

@sanity
Copy link
Contributor

@sanity sanity commented Jan 21, 2026

Problem

Users cannot edit or delete their own messages, nor can they react to messages with emoji. This limits the expressiveness and usability of the chat experience. (Issue #67)

Approach

Implements message actions (edit, delete, reactions) as special message types that flow through the normal message timeline:

  1. Actions are messages: New RoomMessageBody variants (Edit, Delete, Reaction, RemoveReaction) are stored as signed messages in the timeline
  2. Computed state: MessagesV1::actions_state tracks the effective state (edited content, deleted messages, reactions) - rebuilt from action messages on each delta
  3. Authorization: Only the original message author can edit/delete their own messages. Anyone can add reactions, and users can only remove their own reactions
  4. Display: UI shows "(edited)" indicator on edited messages and displays reaction badges below messages

This approach preserves the append-only, signed message model while enabling interactive features.

Why this design over alternatives?

  • Actions as messages allows them to sync naturally through the existing delta mechanism
  • Computed state with #[serde(skip)] avoids signature invalidation issues - the signed message content is never mutated
  • Authorization in rebuild_actions_state() means invalid actions (e.g., editing someone else's message) are simply ignored, not rejected

Testing

New unit tests added (7 tests):

  • test_edit_action - Verify edit applies and edited flag is set
  • test_edit_by_non_author_ignored - Verify unauthorized edits don't apply
  • test_delete_action - Verify deleted messages are marked and filtered from display
  • test_reaction_action - Verify reactions from multiple users aggregate correctly
  • test_remove_reaction_action - Verify users can remove their own reactions
  • test_action_on_deleted_message_ignored - Verify actions on deleted targets are no-op
  • test_display_messages_filters_actions - Verify action messages are not shown directly

Local validation:

  • cargo test -p river-core - All 94 tests pass
  • cargo clippy -p river-core - No errors (some pre-existing warnings)
  • cargo fmt - All code formatted

What still needs testing:

  • Full UI testing with multiple simulated users (requires dev server setup)
  • Multi-peer sync testing to verify actions propagate correctly

Breaking Change

This adds new RoomMessageBody enum variants, which will cause deserialization errors for older clients. This is acceptable during alpha. Before production, consider adding #[serde(other)] fallback variant.

Critical Files

File Changes
common/src/room_state/message.rs +569 lines: New variants, computed state, delta processing, helper methods, tests
ui/src/components/conversation.rs +109 lines: Display edited indicator and reactions
ui/src/components/conversation/message_actions.rs New file: Context menu/emoji picker component (basic structure)
ui/src/components/app/notifications.rs Handle new message types in notification previews

Future Work (not in this PR)

  • Wire up context menu to actually send Edit/Delete/Reaction messages
  • Add emoji picker UI interaction
  • CLI support for edit/delete/react commands

Closes #67

[AI-assisted - Claude]

sanity and others added 7 commits January 21, 2026 12:42
Implements the foundation for message actions as described in issue #67:

- Add new RoomMessageBody variants: Edit, Delete, Reaction, RemoveReaction
- Actions are stored as signed messages in the timeline
- Delta processing applies actions to build computed state (edited content,
  deleted flags, reaction counts)
- Authorization enforced: only authors can edit/delete their messages
- UI displays "(edited)" indicator and reaction badges
- Add message_actions.rs component for future context menu/emoji picker

Breaking change: New enum variants will cause deserialization errors for
older clients. This is acceptable during alpha.

Test plan:
- 7 new unit tests covering all action types
- Tests verify authorization (edit by non-author is ignored)
- Tests verify action on deleted message is no-op
- Tests verify display_messages filters actions

Closes #67

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
…uttons

- Add hover action bar that appears when hovering over messages
- React button (👍) adds thumbs-up reaction to any message
- Delete button removes user's own messages
- Edit button shown but disabled (coming soon)
- Wire up handlers to create and apply action messages

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
Clicking the delete button now shows a confirmation modal asking
'Delete Message?' before actually deleting. Users can cancel or confirm.

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
Replace single thumbs-up button with an expandable emoji picker:
- Click 😊 to open picker with 8 curated emojis (👍❤️😂😮😢😡🎉🤔)
- Visual hierarchy separates reactions from actions (edit/delete)
- Warm amber hover for reaction trigger, red hover for delete
- Picker closes after selecting an emoji
- Divider visually separates reaction zone from action zone

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
…lick-outside dismiss

- Change from horizontal row to 2-column vertical grid
- Raise z-index to z-50 so picker appears above room list
- Add invisible backdrop to catch outside clicks and close picker
- Keep action bar visible while picker is open (override hover behavior)
- Larger emoji buttons (text-xl, more padding) for easier clicking

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
Fixes #72

- Remove overflow-y-auto from aside, add to member list only
- Add flex-shrink-0 to header, invite button, and status sections
- Member list now scrolls independently while footer stays visible

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
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.

feat: Add message editing, deletion, and reactions

2 participants