What is the difference between Turbo and Stimulus, and what exactly is Hotwire?

If it has been a while since you last used Rails, you may be feeling a little lost with some of the newer, front-end focussed features that Rails has added over the years. Stimulus, Turbo Drive, Turbo Frames, Turbo Streams, Strada, Hotwire - what is all this stuff, and where do you start? You do remember Turbolinks, but the last few times you had to deal with it, you ended up turning it off so that your app would work as expected.

I’m going to try to help out by giving you a quick overview of what these things are, and where they fit in to the bigger picture. I’ll assume you’re familiar with the “basic” Rails stack - DB -> Models -> Controllers -> Views. Then, I’ll point you to some resources which you can use to dive deeper.

hotwire umbrella with stimulus, strada and turbo under it

Hotwire

“Hotwire” (HTML Over The Wire) is an umbrella term that encompasses a set of technologies. The technologies within this “umbrella” all share a goal - make web apps feel speedy and responsive to the user. Turbo Drive, Turbo Frames, Turbo Streams, Stimulus and Strada are the individual technologies that comprise Hotwire.

In the old days (actually, even these days if you have nothing special going on under the hood), clicking on a link, or submitting a form would involve the entire browser page reloading to display the updated contents of the page. SPA frameworks like React attempt to solve this by making you write your entire front-end in JavaScript. Hotwire attempts to solve this by doubling down on Rails’ “default” use case - serving HTML.

Turbo

To make web apps feel speedy and responsive to the user, Hotwire solves the “entire browser page has to reload for the user to see a change” problem with basically one weird trick.

First, it intercepts things like link clicks and form submits, using Javascript that runs when your page loads. Then, after preventing the click event from bubbling up to the browser, it fetch’s the content at the link and replaces the content of the current page with the new content.

I can imagine doing this naively with something like:

// on page load
document
  .querySelectorAll("a")
  .forEach((link) => link.addEventListener("click", linkInterceptor));

async function linkInterceptor(event) {
  event.preventDefault();
  const newContent = await fetch(event.target.href);
  document.querySelector("body").innerHTML = newContent;
}

That’s not all that Hotwire does, but this is the first important idea that Hotwire brings to the table. The technology that does this work is called Turbo.

Turbo is another umbrella term, and it refers to four technologies: Turbo Drive, Turbo Frames, Turbo Streams and Turbo Native. Turbo Drive does what I’ve described above. Turbo Frames extends the idea of replacing body’s content with new HTML and allows you to replace any section (frame) of the page. Turbo Streams goes even further by letting the updates to frames on the page come through WebSocket channels that your user may be subscribed to, and not just responses to requests they are making. This is pretty cool, because all of a sudden, without adding any JavaScript of your own (though Turbo itself is a combination of JavaScript and server side Rails code), your Rails app, which even “past you” from 10 years ago would be able to grok, now looks and feels like a “modern” SPA.

To get a detailed idea of what Turbo is capable of, because I certainly haven’t covered anything close to that here, check out the Turbo homepage.

Stimulus

Turbo does not support custom JavaScript. Its functionality is constrained to rendering new HTML on the page, whether the HTML came from a click that was “converted” into a fetch request, a WebSocket channel, or anywhere else.

If what Turbo does is not enough for your use case, and you want more interactive functionality like showing or hiding elements, copying content to the clipboard etc, then you could consider reaching for Stimulus. Stimulus is a JavaScript framework that operates on the HTML that has been rendered on the page. Elements in the DOM are wired to Stimulus controllers. Stimulus controllers, via the MutationObserver API, are able to spring to life when the DOM element that is wired to them is rendered on the page, and then perform any interaction that you may want them to.

Though Stimulus is part of the Hotwire toolkit, it doesn’t have to be used with Turbo. It can stand on its own. With the recent improvements to the Javascript language, especially how the DOM is accessed, and what Stimulus provides, there is really no need for something like jQuery anymore.

For more information, check out the Stimulus homepage.

Beyond Stimulus

Sometimes, the interaction you require in your app may be so complex that even using Stimulus doesn’t cut it. You may want to bring in some React or Vue to take advantage of the way those frameworks allow you to describe and compose complex front-end behavior. All is not lost in those situations. You can selectively use React or Vue (or anything else) just in the places that need them, and you can use Stimulus to help you do so. You may find the article I wrote about how to use React just on one page in a Rails app useful, if that’s what you’re interested in doing.

Strada - an upcoming Hotwire technology

As of March 2023, details about Strada are currently not available on the Hotwire homepage. From what I can tell, Strada will serve as a bridge between native and web components of a mobile hybrid application. This potentially means that you can, on a piecemeal basis, replace web components with native components and vice versa. It is unclear if Strada is of any help to you if you are developing a “pure” web application.

Conclusion, and further reading

Rails has come a long way since the early days, and in my opinion has only gone from strength to strength. Whether you’re coming back to Rails after a long break, or just needing to brush up on the latest so you can get on with building your next feature, I hope this article has helped to orient you to the front-end focussed features that Rails now offers.

You will likely want to do some further reading to dive deeper. To that end, here are some resources for you to check out.

If you liked this article and want to hear more from me, please subscribe to my email newsletter. I’ll notify you whenever I publish a new article.

Want to be notified when I publish a new article?