# The element “h3” must not appear as a descendant of the “th” element.

> Canonical HTML version: https://rocketvalidator.com/html-validation/the-element-h3-must-not-appear-as-a-descendant-of-the-th-element
> Attribution: Rocket Validator (https://rocketvalidator.com)
> License: CC BY 4.0 (https://creativecommons.org/licenses/by/4.0/)

The `th` element is specifically designed to represent a header cell in a table. It inherently conveys header semantics to browsers, screen readers, and other assistive technologies. When you place a heading element like `h3` inside a `th`, you're creating a structural conflict — the content is simultaneously acting as a table header and a document section heading. The HTML specification restricts the content model of `th` to "flow content, but with no `header`, `footer`, sectioning content, or heading content descendants."

This matters for several reasons:

- **Accessibility:** Screen readers use heading elements to build a document outline and allow users to navigate between sections. A heading buried inside a table header cell disrupts this navigation, creating confusion about the page structure. The `th` element already communicates its role as a header through the table's own semantics.
- **Document structure:** Headings define the hierarchical structure of a document. Placing them inside table cells implies that a new document section begins within the table, which is almost never the intended meaning.
- **Standards compliance:** Browsers may handle this invalid nesting inconsistently, leading to unpredictable rendering or accessibility tree representations.

The fix is straightforward: remove the heading element from inside the `th`. If the text inside the `th` needs to be visually larger or bolder, apply CSS styles directly to the `th` element or use a `span` with a class. If the heading was meant to title the entire table, move it outside the table or use the `caption` element.

## Examples

### ❌ Incorrect: heading inside `th`

```html
<table>
  <tr>
    <th>Month</th>
    <th><h3>Revenue</h3></th>
  </tr>
  <tr>
    <td>January</td>
    <td>$500</td>
  </tr>
</table>
```

The `h3` inside the second `th` triggers the validation error.

### ✅ Fixed: remove the heading, use plain text

```html
<table>
  <tr>
    <th>Month</th>
    <th>Revenue</th>
  </tr>
  <tr>
    <td>January</td>
    <td>$500</td>
  </tr>
</table>
```

The `th` element already communicates that "Revenue" is a header. No heading element is needed.

### ✅ Fixed: use CSS for visual styling

If the heading was used to make the text look bigger or styled differently, apply CSS to the `th` instead:

```html
<table>
  <tr>
    <th>Month</th>
    <th class="prominent">Revenue</th>
  </tr>
  <tr>
    <td>January</td>
    <td>$500</td>
  </tr>
</table>

<style>
  .prominent {
    font-size: 1.2em;
    font-weight: bold;
  }
</style>
```

### ✅ Fixed: use `caption` for a table title

If the heading was meant to describe the entire table, use the `caption` element:

```html
<table>
  <caption>Monthly Revenue</caption>
  <tr>
    <th>Month</th>
    <th>Revenue</th>
  </tr>
  <tr>
    <td>January</td>
    <td>$500</td>
  </tr>
</table>
```

The `caption` element is the semantically correct way to provide a title or description for a table. You can style it with CSS to match the appearance of a heading. If you still need a heading in the document outline to precede the table, place it before the `table` element:

```html
<h3>Revenue Report</h3>
<table>
  <tr>
    <th>Month</th>
    <th>Revenue</th>
  </tr>
  <tr>
    <td>January</td>
    <td>$500</td>
  </tr>
</table>
```

This approach keeps the document structure clean while maintaining proper table semantics. The same rule applies to all heading levels — `h1`, `h2`, `h3`, `h4`, `h5`, and `h6` are all equally invalid inside `th` (and `td`) elements.
