CSSBEM Methodology

BEM Methodology

BEM stands for Block, Element, Modifier — a naming convention for CSS classes developed at Yandex with one goal: make the relationship between two classes obvious just from reading their names, without having to open a stylesheet or inspect the DOM to figure out how they relate.

The three parts

Part

Syntax

Meaning

Block

.block

A standalone, reusable component — e.g. a card, a menu, a form

Element

.block__element

A piece of a block that has no standalone meaning outside it — e.g. a card's title

Modifier

.block--modifier or .block__element--modifier

A variant or state of a block/element — e.g. a featured card

Worked example: a card component

HTML
<div class="card card--featured">
  <img class="card__image" src="thumb.jpg" alt="" />
  <h3 class="card__title">Product Name</h3>
  <p class="card__description">Short summary text.</p>
  <button class="card__button card__button--disabled">Add to cart</button>
</div>

CSS
.card {
  border: 1px solid #e0e0e0;
  border-radius: 8px;
  padding: 1rem;
}

.card--featured {
  border-color: #f5a623;
  box-shadow: 0 0 0 2px rgba(245, 166, 35, 0.3);
}

.card__title {
  font-size: 1.1rem;
  font-weight: 600;
  margin: 0.5rem 0;
}

.card__button {
  background: #0066cc;
  color: white;
  border: none;
  padding: 0.5em 1em;
}

.card__button--disabled {
  background: #ccc;
  cursor: not-allowed;
}
Why the explicitness matters
Look at .card__button--disabled in isolation — with no other context, the class name alone tells you three facts: it lives inside a card block, it's specifically the button element, and it represents that button's disabled state. Compare that to a plain class like .disabled-btn, which tells you nothing about which component it belongs to or whether it's safe to reuse elsewhere. That self-documenting quality is BEM's biggest practical benefit — it makes large stylesheets navigable by grep and by class name alone, and it makes accidental collisions between unrelated components far less likely because every class is implicitly namespaced to its block.
Flat structure — elements don't nest in the name
A common mistake is nesting elements in the class name to mirror DOM nesting, e.g. .card__body__title. BEM intentionally keeps element names flat against the block — every element belongs directly to the block, not to another element:

CSS
/* Avoid — implies deep, fragile coupling to DOM structure */
.card__body__title { }

/* Prefer — flat, and unaffected if you move .card__title around inside the block */
.card__title { }
BEM's verbosity is a genuine trade-off, not a flaw everyone agrees on
Long, hyphenated, double-underscored class names make markup denser and require more typing than shorter alternatives. Some teams find the readability and collision-safety worth it; others find it noisy, especially in deeply nested UI, and prefer scoping tools (CSS Modules, CSS-in-JS) that give collision-safety without the naming overhead. Neither position is objectively wrong — it depends on team size, tooling, and how much you value being able to understand a class's role without other context.
BEM is a naming convention, not a file organization strategy
BEM only prescribes how to name classes — it says nothing about specificity tiers, file structure, or import order. It's commonly combined with a structural methodology like ITCSS, which does address those concerns.
Next
See a methodology that categorizes rules by role instead of naming classes by structure: SMACSS.