ruby 36 lines · 8 steps

Live-updating comments with Turbo in Rails

A Comment model pushes its own creates, updates, and deletes to subscribers over Turbo Streams.

Explained by highlit
1class Comment < ApplicationRecord
2 belongs_to :post
3 belongs_to :author, class_name: "User"
4 
5 validates :body, presence: true, length: { maximum: 2_000 }
6 
7 scope :recent, -> { order(created_at: :desc) }
8 
9 after_create_commit :broadcast_creation
10 after_update_commit :broadcast_replacement
11 after_destroy_commit :broadcast_removal
12 
13 private
14 
15 def broadcast_creation
16 broadcast_prepend_later_to(
17 [post, :comments],
18 target: dom_id(post, :comments),
19 partial: "comments/comment",
20 locals: { comment: self }
21 )
22 broadcast_update_later_to(
23 [post, :comments],
24 target: dom_id(post, :comments_count),
25 html: post.comments.count
26 )
27 end
28 
29 def broadcast_replacement
30 broadcast_replace_later_to([post, :comments], target: self)
31 end
32 
33 def broadcast_removal
34 broadcast_remove_to([post, :comments], target: self)
35 end
36end
01 / 01
STEP 01

Walkthrough

Space play step click any line
Three takeaways
  1. 1Commit-time callbacks fire only after the transaction succeeds, so broadcasts never reference uncommitted data.
  2. 2Streaming to a shared `[post, :comments]` stream lets every subscriber receive the same DOM updates.
  3. 3Targeting elements by `dom_id` keeps server-rendered partials and client DOM in sync without custom JavaScript.

Related explainers

Share this explainer

Here's the card — post it anywhere.

Live-updating comments with Turbo in Rails — share card
Made with highlit — turn any snippet into a walkthrough like this in about a minute.
Explain your code