Skip to content

Learning Stimulus JS as a New Developer: My First Impressions

When you're learning web development, JavaScript frameworks can feel… intimidating. At least they did for me.

4 min read

When you’re learning web development, JavaScript frameworks can feel… intimidating. At least they did for me.

When I first started exploring frontend tools, I kept hearing about frameworks that required entire application architectures, build tools, component systems, and a bunch of concepts that felt overwhelming as a new developer.

Then I came across Stimulus, and it honestly felt like a breath of fresh air. Instead of replacing your html.erb, Stimulus does something much simpler. It adds Javascript behavior to the html.erb you already have.

As someone still learning the ropes, this approach made things click much faster. So here’s a quick walkthrough of what I’ve been learning about Stimulus and why I think it’s such a great tool for beginner developers.

The Problem I Kept Running Into#

While learning backend development with Ruby on Rails, I noticed something. Rails is great at generating pages and handling server logic, but sometimes you just want small interactive features. My first instinct was to reach for plain JavaScript and start using things like :

document.querySelector()
addEventListener()

Which works… but quickly becomes messy when your page grows. That’s where Stimulus comes in.

What Stimulus Actually Is#

Stimulus is a lightweight JavaScript framework created by the team behind Basecamp. Instead of controlling your entire UI, it focuses on injecting behavior onto your html.erb. Stimulus works by connecting JavaScript to html.erb using data attributes.

At first this looked strange to me, but once I understood it, it actually felt really clean.

The Core Idea: Controllers#

In Stimulus, JavaScript behavior lives inside something called a controller. A controller is just a JavaScript class.

When the page loads, Stimulus automatically connects this controller to any html.erb element that declares it, for example:

<div data-controller="example"></div>

That data-controller attribute is what links your HTML to your JavaScript. Once I understood that connection, everything else started making more sense.

Actions: Listening for Events#

Stimulus also gives you a really clean way to handle events. Instead of writing JavaScript like this:

button.addEventListener("click", ...)

You define the event directly in your html.erb. For example:

<button data-action="click->disable-button#disable">
Click me
</button>

This code is saying that we are listening for a click, using a disable-button controller and running the disable method.

When I first saw this syntax it looked weird, but after using it a few times it actually makes your html.erb very self-explanatory.

Targets: Accessing Elements Easily#

One thing I struggled with early in JavaScript was selecting elements correctly. Stimulus solves this with targets. For example:

<div data-controller="disable-button">
<button data-disable-button-target="button">
Click me
</button>
<a data-disable-button-target="link" class="d-none">
Reset
</a>
</div>

Then inside the controller you simply declare:

static targets = [“button”, “link”]

Now Stimulus automatically gives you: this.buttonTarget ; this.linkTarget. No querySelector needed. As someone still getting comfortable with DOM manipulation, this felt like a really nice abstraction.

My First Stimulus Feature#

One of the first things I built was a button that disables itself and reveals a reset link.

import { Controller } from "@hotwired/stimulus"
export default class extends Controller {
static targets = ["button", "link"]
disable() {
this.buttonTarget.innerText = "Bingo!"
this.buttonTarget.setAttribute("disabled", "")
this.linkTarget.classList.remove("d-none")
}
reset() {
this.buttonTarget.innerText = "Click me!"
this.buttonTarget.removeAttribute("disabled")
this.linkTarget.classList.add("d-none")
}
}

Stimulus + APIs#

Another thing I tried was using Stimulus with an API to search for movies. The controller fetches data and inserts results into the page.

fetch(`http://www.omdbapi.com/?s=${query}&apikey=YOUR_KEY`)
.then(response => response.json())
.then(data => {
data.Search.forEach(movie => {
const movieTag = `
<li>
<img src="\({movie.Poster}" alt="\){movie.Title}">
</li> `
this.resultsTarget.insertAdjacentHTML("beforeend", movieTag)
})
})

Seeing real data appear dynamically on the page was one of those “okay this is cool” moments.

Why I Think Stimulus Is Great for Beginners#

As a new developer, I think Stimulus is great because it:

  • builds on basic HTML and JavaScript concepts

  • avoids overwhelming frameworks

  • keeps JavaScript organised

Instead of forcing you to learn an entire frontend ecosystem, it helps you improve your existing JavaScript skills.

Final Thoughts#

Learning web development sometimes feels like trying to drink from a firehose. There are so many frameworks, tools, and patterns that it’s easy to feel behind. What I like about Stimulus is that it doesn’t try to reinvent everything. It simply helps you write cleaner, more structured JavaScript on top of the HTML you already understand. And as someone still early in their software engineering journey, that approach makes learning feel a lot more manageable.