Comments: Rich-Text Formatting, Delivery Status, and One-Click Retry for Failed Messages
Executive summary
This release promotes a batch of Comments enhancements from development into the QA environment. Users can now apply rich-text formatting (bold, italics, underline) alongside @mentions in comments, see delivery-status indicators on their own messages, and retry a failed comment or reply with a single click instead of losing it.
Why this was needed
The comments composer previously flattened everything to plain text on send, so any formatting and structure entered by the user was discarded. There was also no visibility into whether a message actually reached the server: when a post failed, the optimistic message was silently removed and the typed content was lost, forcing the user to retype it. These changes preserve formatting, surface send status, and make failures recoverable.
Client / user impact
- Comments and replies now retain rich-text formatting (bold/italic/underline) along with @mentions, producing clearer, more readable threads.
- Pressing Shift+Enter (in addition to Ctrl/Cmd+Enter) inserts a line break, making multi-line comments easier to compose.
- Each message the user sends shows a status: sending, sent (double check), or failed.
- A failed comment or reply is no longer discarded; it stays in the thread with a Retry button so the user can resend without retyping.
Technical scope
Batch promotion (dev -> qa) bundling Comments work from feature PRs #464, #465, #469, #471, #472. Changes are confined to src/components/common/Comments/* and src/types/comments.types.ts:
- Rich-text preservation: new
getHTMLWithMentionsAsText()inmention-badge-utils.tsconverts mention badges back to@usernametext while keeping formatting tags;Composer.tsxnow emits and loadsinnerHTMLinstead of plain text, and treats Shift+Enter as a line break.MessageBubble.tsxuseshtmlToPlainText()when populating the edit draft. - Delivery status: added an optional
statusfield (sending/sent/failed) toCommentMessage; newMessageStatusIndicatorrenders check/double-check/alert icons on the current user's own messages.normalizeCommentmarks server-fetched messages assent. - Retry flow: new
handleRetry()inuseCommentsDrawer.tslocates the failed comment or reply, re-sends it viacreateComment, and updates status on success/error. Failed posts are now markedfailed(with a Retry control) rather than removed from state.onRetryis threaded throughCommentsDrawer,ThreadView, andMessageBubble. - Net diff: ~286 additions, ~22 deletions across 8 files; no API/schema changes on the frontend side.
Risk & mitigation
Low-to-moderate, scoped entirely to the comments UI. The main risk is the switch from storing plain text to storing/rendering HTML in the composer and bubbles: malformed or unexpected HTML could affect rendering, and existing plain-text comments must still display correctly. Content continues to pass through the existing rendering helpers (wrapMentionsInHTML, renderPlainTextContent) and is converted via toServerContent on send. Retry reuses the same create-comment path, so duplicate-post risk exists only if the server succeeded but did not return a comment id. Mitigation: verify in QA against legacy comments and confirm sanitization behaves as expected.
QA validation focus
- Compose a comment with bold/italic/underline plus an @mention; verify formatting and the mention are preserved after send and on reload.
- Confirm Shift+Enter and Ctrl/Cmd+Enter both insert a line break (do not submit).
- Check status icons on your own messages: sending state, sent (double-check), and failed (alert) states.
- Force a network/API failure and confirm the message stays with a Retry button; click Retry and confirm it sends and flips to sent.
- Repeat the failure/retry flow inside a thread reply.
- Verify older/plain-text comments still render correctly and that editing a comment shows plain text in the edit box.
- Confirm mentions still notify the correct users after the HTML change.