← Home ← Codex ← DEBT
Browse by Category
+ added · updated 7d
← Back to glossary

Heading Hierarchy (h1-h6)

accessibility Beginner
debt(d5/e3/b3/t7)
d5 Detectability Operational debt — how invisible misuse is to your safety net

Closest to 'specialist tool catches it' (d5), axe, lighthouse, wave, and webhint automatically flag level jumps and missing h1, but they cannot judge whether the chosen rank is semantically correct, only structural gaps.

e3 Effort Remediation debt — work required to fix once spotted

Closest to 'simple parameterised fix' (e3), quick_fix is to renumber tags so levels descend without gaps and move sizing to CSS, a small pattern replacement, though faked headings may need component changes across a few files.

b3 Burden Structural debt — long-term weight of choosing wrong

Closest to 'localised tax' (b3), applies_to is web only and headings are scattered across components, so a broken outline assembled from nested components creates a recurring but contained structural tax rather than defining system shape.

t7 Trap Cognitive debt — how counter-intuitive correct behaviour is

Closest to 'serious trap' (t7), the misconception that heading levels are about font size directly contradicts their true purpose of conveying structural rank, so a developer's intuitive choice based on appearance is reliably wrong.

About DEBT scoring →

Also Known As

heading levels document outline h1-h6 structure heading structure

TL;DR

Headings must form a logical, sequential outline (h1 then h2, no skipped levels) so screen reader users can navigate and grasp page structure.

Explanation

HTML heading elements h1 through h6 communicate document structure, not visual size. Screen reader users rely heavily on headings to navigate: NVDA, JAWS, and VoiceOver all let users jump from heading to heading and pull up a list of all headings to scan a page like a table of contents. For this to work, headings must form a meaningful outline. There should be exactly one h1 describing the page's primary subject, followed by h2 for major sections, h3 for subsections, and so on. Levels must not be skipped when descending (an h2 followed directly by an h4 implies a missing section), because the gap suggests structure that is not there. You may jump back up freely (an h4 followed by an h2 starts a new major section). The cardinal sin is choosing a heading level for its default font size rather than its semantic rank, or using styled <div>s and <p>s that look like headings but carry no heading role in the accessibility tree. WCAG 2.1 covers this under Success Criterion 1.3.1 (Info and Relationships, Level A) and 2.4.6 (Headings and Labels, Level AA); the practice of a logical heading order is also reflected in SC 2.4.10 (Section Headings, AAA). Tools like axe and Lighthouse flag skipped levels and missing h1, but they cannot judge whether a heading is semantically appropriate, so manual review with a heading-navigation command is essential. Use CSS to control appearance and reserve heading levels for structure; if you need large text that is not a section heading, style a paragraph or span instead.

Common Misconception

Heading levels are about font size, so you pick whichever h tag looks right visually. In reality heading levels convey structural rank for assistive technology; appearance should be controlled with CSS while the level reflects the section's place in the outline.

Why It Matters

Screen reader users navigate primarily by jumping between headings, so a broken or illogical heading order makes a page disorienting or impossible to scan, and it fails WCAG SC 1.3.1 at Level A.

Common Mistakes

  • Skipping a level when descending, such as following an h2 directly with an h4.
  • Choosing a heading level for its default font size instead of its semantic rank.
  • Using multiple h1 elements or no h1 at all on a page.
  • Faking headings with styled <div> or <b> elements that have no heading role.
  • Wrapping non-heading text (like a tagline) in a heading tag just to make it large.

Avoid When

  • Do not change a heading level purely to match a desired font size when the level is structurally correct; adjust CSS instead.
  • Do not introduce extra heading elements to create visual separators that carry no structural meaning.

When To Use

  • On every page, to provide a single h1 and a logical, gap-free descending outline of sections and subsections.
  • When refactoring components that render headings, to verify the assembled page still produces a valid outline across nested components.

Code Examples

✗ Vulnerable
<!-- Levels skipped and sized by appearance -->
<h1>Acme Store</h1>
<h4>Featured Products</h4>  <!-- jumps h1 -> h4 -->
<div class="big-text">Sale Items</div>  <!-- looks like a heading, isn't one -->
<h2>Customer Reviews</h2>
✓ Fixed
<!-- Logical outline, size controlled in CSS -->
<h1>Acme Store</h1>
<h2>Featured Products</h2>
<h3>Sale Items</h3>
<h2>Customer Reviews</h2>

<style>
  /* Style for appearance, not structure */
  h3 { font-size: 1.75rem; }
</style>

Added 5 Jun 2026
Views 9
Rate this term
No ratings yet
🤖 AI Guestbook educational data only
| |
Last 30 days
0 pings T 0 pings W 0 pings T 0 pings F 0 pings S 0 pings S 0 pings M 0 pings T 0 pings W 0 pings T 0 pings F 0 pings S 0 pings S 0 pings M 0 pings T 0 pings W 0 pings T 0 pings F 0 pings S 0 pings S 0 pings M 0 pings T 0 pings W 0 pings T 3 pings F 1 ping S 2 pings S 2 pings M 0 pings T 0 pings W
No pings yet today
No pings yesterday
Google 4 Scrapy 2 Ahrefs 1 Majestic 1
crawler 7 crawler_json 1
DEV INTEL Tools & Severity
🟡 Medium ⚙ Fix effort: Low
⚡ Quick Fix
Audit headings with a heading-navigation tool, ensure one h1, and renumber tags so levels descend without gaps while controlling size via CSS.
📦 Applies To
html web
🔗 Prerequisites
🔍 Detection Hints
<h[1-6][^>]*>.*?</h[1-6]> sequences with a level jump greater than one, or no <h1> present
Auto-detectable: ✓ Yes axe lighthouse wave webhint
⚠ Related Problems
🤖 AI Agent
Confidence: Medium False Positives: Medium ✗ Manual fix Fix: Medium Context: File

✓ schema.org compliant