auditmysitev2.0.2

HTML5 content model violation

html-content-model

WCAG success criterion
1.3.1 (level A)
Outcome class
Automatic. An automated check that can report a confirmed violation.
Area
Accessibility, Structure & Semantics
Default severity
medium
axe-core rule
html-content-model

Why we flag this

Screen readers cannot reliably parse the structure, even when it appears superficially valid.

Unexpected child element inside a structural container (e.g. <ul>, <table>, <select>).

What the rule checks

Scope. The served HTML of the page, where it contains structural containers whose content model AT relies on (dl, table and its sections, ul/ol, select/optgroup, fieldset).

Expectation. Fails for every content-model violation that occurs inside such a container in the served markup, e.g. a div as a child of ul. The browser repairs or absorbs such markup, so the accessibility tree can look valid while the structure is broken. Allowed wrappers pass (div grouping dt/dd in dl), and so does a well-formed table. Selector is the container's tag.

Source. WCAG 2.2 SC 1.3.1 Info and Relationships; HTML content models: §4.4.5 ul, §4.4.6 ol, §4.4.9 dl, §4.9 tabular data, §4.10.7 select, §4.10.15 fieldset

Detection: pipeline; needs network.

Failing example

The check reports a violation here. Corpus case structure_content_model, element ul. The page may contain further findings for other rules.

structure_content_model.htmlHTML
<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="utf-8">
    <meta name="viewport" content="width=device-width, initial-scale=1">
    <title>Index of tool specifications – Acme Hardware</title>
    <style>
        body { font: 16px/1.5 sans-serif; margin: 0 16px; }
        a { display: inline-block; min-width: 44px; min-height: 44px; line-height: 44px; }
        input, button { min-width: 44px; min-height: 44px; }
    </style>
</head>
<body>
    <!-- Product data from a page builder (#783). The feature list wraps its
         items in a div, which the <ul> content model does not allow; the
         browser repairs the tree, the markup stays wrong. The definition list
         groups name-value pairs in div elements, which <dl> does allow, and
         the table is well-formed. -->
    <a href="#main" class="skip-link">Skip to content</a>
    <header>
        <p>Acme Hardware</p>
    </header>
    <nav aria-label="Main">
        <ul>
            <li><a href="/">Home</a></li>
            <li><a href="/tools/">Tools</a></li>
        </ul>
    </nav>
    <main id="main">
        <!-- The page's h1 is hidden; the visible outline starts at h2. -->
        <h1 hidden>Cordless drill CD-18</h1>
        <p class="product-name">Cordless drill CD-18</p>
        <h2>Features</h2>
        <ul id="features">
            <div class="feature-row">
                <li>Two speeds</li>
                <li>LED work light</li>
            </div>
        </ul>
        <h2>Specifications</h2>
        <dl id="specs">
            <div><dt>Voltage</dt><dd>18 V</dd></div>
            <div><dt>Weight</dt><dd>1.4 kg</dd></div>
        </dl>
        <h2>Spare parts</h2>
        <table id="parts">
            <caption>Spare parts and prices</caption>
            <thead>
                <tr><th scope="col">Part</th><th scope="col">Price</th></tr>
            </thead>
            <tbody>
                <tr><td>Battery 2 Ah</td><td>39 EUR</td></tr>
                <tr><td>Charger</td><td>29 EUR</td></tr>
            </tbody>
        </table>
    </main>
    <footer>
        <p>Acme Hardware, Berlin</p>
    </footer>
</body>
</html>

Passing example

The check passes here and reports nothing. Corpus case structure_outline_clean. The page may contain further findings for other rules.

structure_outline_clean.htmlHTML
<!DOCTYPE html>
<html lang="en" xml:lang="en-GB">
<head>
    <meta charset="utf-8">
    <meta name="viewport" content="width=device-width, initial-scale=1">
    <title>Opening hours and contact – Acme Hardware Berlin</title>
    <style>
        body { font: 16px/1.5 sans-serif; margin: 0 16px; }
        a { display: inline-block; min-width: 44px; min-height: 44px; line-height: 44px; }
        input, button { min-width: 44px; min-height: 44px; }
    </style>
</head>
<body>
    <!-- Conforming look-alike for the structure rules (#783): every
         structure the rules look at is present and correct. -->
    <a href="#main" class="skip-link">Skip to content</a>
    <header>
        <p>Acme Hardware</p>
    </header>
    <nav aria-label="Main">
        <ul>
            <li><a href="/">Home</a></li>
            <li><a href="/shop/">Shop</a></li>
            <li><a href="/contact/">Contact</a></li>
        </ul>
    </nav>
    <main id="main">
        <h1>Opening hours and contact</h1>
        <p>Our store in Berlin is open six days a week. We are happy to help you
           find the right tool for your project, and you can always call us before
           you visit to check that an item is in stock.</p>
        <h2>Opening hours</h2>
        <dl>
            <div><dt>Monday to Friday</dt><dd>8:00 to 18:00</dd></div>
            <div><dt>Saturday</dt><dd>9:00 to 14:00</dd></div>
        </dl>
        <h2>Directions</h2>
        <!-- English text with German proper names: names are exempt from
             3.1.2, and only two German function words occur. -->
        <p id="directions">The store is a short walk from the Haus der Kunst gallery and the
           old bridge that locals call die Brücke. Take the tram to the main square, then
           follow the river for about five minutes until you see our green sign.</p>
        <article>
            <h3>Store news</h3>
            <p>We now stock garden tools from local makers.</p>
        </article>
        <section aria-labelledby="contact-heading">
            <h2 id="contact-heading">Contact</h2>
            <p>Call us or send a message. Prices include <abbr title="value-added tax">VAT</abbr>.</p>
            <form action="/contact" method="post">
                <label for="contact-email">E-mail</label>
                <input id="contact-email" name="email" type="email" autocomplete="email" aria-describedby="contact-hint">
                <p id="contact-hint">We reply within one working day.</p>
                <button type="submit">Send</button>
            </form>
        </section>
    </main>
    <footer>
        <p>Acme Hardware, Berlin</p>
    </footer>
    <!-- Hidden leftover outside every landmark: not rendered, not content. -->
    <div hidden>Summer sale banner</div>
</body>
</html>

This page is generated from the rule catalogue and the rule contracts; see therule overview for how the outcome classes are derived.