Skip to content

a11y.label missing control

github-actions[bot] edited this page Sep 6, 2026 · 2 revisions

a11y.label-missing-control

Rule ID: a11y.label-missing-control Severity: ERROR Category: a11y Target Standards: WCAG 2.2 Success Criterion 1.3.1 (Info and Relationships - Level A), W3C WAI-ARIA Authoring Practices (Form Labeling), HTML5 Specification (Section 4.10.4 The label element)


1. Overview & Core Invariant

Ensures label htmlFor attributes match an existing input control ID in the same document (WCAG 1.3.1)

Core Invariant:

"Every declaring an 'htmlFor' (or 'for') attribute must match the 'id' of an existing element in the same file."


2. Technical Grounding & Engine Realities

HTML form labels use the htmlFor (or for) attribute to create a programmatic bond between text instructions and form controls.

When developers introduce typos (e.g. htmlFor="user_id" vs <input id="userId">) or delete inputs without updating labels:

  1. Broken Click Targets: Clicking the label fails to focus or toggle the control, frustrating desktop and mobile touch users alike.
  2. Screen Reader Disconnect: Screen readers read the label as isolated static text, leaving the actual input unannounced and unlabelled.
  3. Linter False Negatives: Conventional linters only check that htmlFor exists as a string, completely ignoring that the target ID is missing.

Charites traverses the document AST symbol table to confirm that every declared htmlFor target actually exists.


3. Vulnerability & Risk Taxonomy

Risk Vector Severity Impact
Broken Label Association HIGH Screen reader users receive unlabelled inputs; clicking labels fails to focus controls.
WCAG 1.3.1 Non-Compliance HIGH Critical Level A accessibility non-compliance.

4. Non-Compliant Code Patterns (Bad Examples)

TSX (Typo in htmlFor target (user_id vs userId)):

<label htmlFor="user_id">ID Pengguna</label><input id="userId" className="border px-3 py-2" />

ASTRO (Label referencing non-existent control ID):

<label for="missing-input">Nama Lengkap</label><input id="fullname" class="border p-2" />

5. Compliant Implementation Patterns (Good Examples)

TSX (Matching htmlFor and input id):

<label htmlFor="userId">ID Pengguna</label><input id="userId" className="border px-3 py-2" />

ASTRO (Accurate for reference matching input element):

<label for="fullname">Nama Lengkap</label><input id="fullname" class="border p-2" />

6. How to Suppress (Ignore Directives)

If this pattern is required for an intentional exception, suppress the diagnostic using the canonical Charites Rule ID:

<!-- charites:ignore a11y.label-missing-control intentional exception -->
// charites:ignore a11y.label-missing-control intentional exception

7. Configuration Reference (charites.yaml)

rules:
  a11y.label-missing-control:
    severity: error # error | warn | info | off

8. Architectural Domain & Verification Reference


Rule Categories

A11y (16 rules)
Browser (12 rules)
Cls (16 rules)
Design (1 rules)
Ergonomy (5 rules)
Inp (16 rules)
Lcp (16 rules)
Mobile (5 rules)
Performance (16 rules)
Pwa (10 rules)
Responsive (18 rules)
Semantic (1 rules)
Theme (32 rules)
Ux (20 rules)

Clone this wiki locally