hotwire

Turbo Streams: swap a button state and counter in one response

A “follow” button usually needs two updates: the button label/state and the follower count. Turbo Streams make this trivial because one server response can carry multiple DOM operations. I render both UI pieces as partials with stable targets (dom_id(

Disable Turbo Drive on external links

Turbo Drive is great for internal navigation, but I disable it for external links or pages that should do a full reload (third-party auth, docs). data-turbo='false' is the simplest switch: it tells Turbo not to intercept the click, so the browser hand

Turbo Streams: server-driven redirect (Turbo Native friendly)

Sometimes you want to “redirect” from a turbo stream response (especially for Turbo Native flows). Returning a stream that updates a frame to include a turbo-visit shim keeps behavior consistent across clients.

Importmap setup for Stimulus controllers (Rails 7 style)

If you’re using importmap, a clean Stimulus setup matters: it keeps controllers discoverable and avoids mystery load order bugs. I pin @hotwired/turbo-rails and @hotwired/stimulus, then use controllers index discovery to register everything. The payof

Link that submits DELETE with Turbo (data-turbo-method)

In Hotwire apps, I still use Rails’ RESTful routes heavily. For destructive actions from a link, data-turbo-method='delete' is the cleanest approach: you keep semantic links where appropriate and let Turbo perform the method override. I usually pair i

Turbo Drive lifecycle: attach global error handler

You’ll eventually hit non-200 responses or network flakiness. Hook Turbo events to log failures (and optionally show a toast). This is a pragmatic production addition that helps debugging without adding heavy tooling.

Stimulus: nested fields add/remove without re-rendering

For nested forms, Stimulus can manage the DOM while Rails handles the final params. Use a hidden template + a unique timestamp key. This keeps the server-rendered form simple and avoids JS frameworks.

Optimistic toggle button with Stimulus “revert on failure”

I like optimistic UI for tiny interactions (like “star” or “follow”) because it makes the interface feel instant. The tradeoff is handling failure cleanly. I implement this with Stimulus: flip CSS + text immediately, then submit a Turbo request in the

Reorder a list server-side and reflect instantly with Turbo Streams

Drag-and-drop reorder can be fancy, but the core is: user triggers a reorder action, server persists positions, and the UI updates. For simpler UIs, I skip drag-and-drop and use up/down buttons. Each click POSTs to a move_up action, updates position,

Autofocus first input when a Turbo modal opens (Stimulus)

A modal that opens without focusing an input is a tiny annoyance that adds up. In Hotwire apps, modals often swap in via Turbo Frames, which means the DOM is injected after navigation. Stimulus is ideal here: attach an autofocus controller to the moda

Turbo Stream flash messages without custom JS

Instead of sprinkling custom JS for notifications, I treat flash as UI state and render it via Turbo Streams. When a create/update succeeds, the controller responds to format.turbo_stream and the template uses turbo_stream.replace to swap the flash co

Stimulus: intersection observer for “mark as read”

For notifications/messages, it’s nice to mark items read when they actually enter the viewport. IntersectionObserver + Stimulus keeps it lightweight, and Turbo streams can update badges in real time.