Classes, ids and data attributes

  • classes are for styling

  • ids are for content

  • data- attributes are for Javascript

In my ideal codebase them's the rules. Simple as that.

Refactoring doesn't need to be hard

The main goal of this division is to make sure that refactoring one concern (content, style, or interactivity) won't create bugs in the others.

CSS classes are easily reusable for styling, which is great for consistency. Mix classes on an element to get things looking just right in a scalable fashion.

Element ids are actually part of the content, in that they can appear in the URL. They will be linked to, and should convey a sense of the relevant part of the document.

data- attributes are basically a wildcard API for your HTML, which makes them flexible in similar ways to Javascript. You can even add values, conveying rich information.

Why we need rules

If, like me, your first experience of learning Javascript was mostly learning jQuery, you've probably written a few hundred variations of this:

var title = $('.section-title');

The logic is simple — go find the thing, save the thing for later. And how should I look for the thing? Well, I've already given the thing a class name, so I can just use that. It's how they do it in the docs, and what you'll find in most jQuery codebases.

Two illusive assumptions are made here, though:

  1. This class name will always be only used for this kind of thing

  2. This class name will never need to change

Neither of these assumptions tend to hold over time. But the real issue it that this kind of thing is exactly the kind of definition that can change over time without you noticing. CSS can be a lot harder than Javascript, and it can grow a lot faster before it feels like a problem. And when it does come time to refactor CSS, changing some class names is sometimes the best way to clarify what has become murky. But what does .section-title becoming .section-title-dark-blue have to do with our Javascript? Nothing, probably.

The best tool HTML gives us to describe the element's interactive role is the data- attribute. The attribute can be anything you want, and so can the value. Whatever complex settings we have for the element can be represented in it. By marking our element data-page-title, so long as that's still the page's title element, we probably won't need to refactor, regardless of content or styling changes.