Skip to main content

srcset-sizes-constraint

Enforces WHATWG constraints between the srcset, sizes, and loading attributes on <img> and <source> elements.

This rule checks the following constraints based on the HTML Living Standard:

#ConstraintTarget
1When sizes is present, srcset must use width descriptors (w) onlyimg, source
2srcset must not mix width (w) and pixel density (x) descriptorsimg, source
3sizes="auto" on <img> requires loading="lazy"img
4sizes="auto" on <source> requires the following sibling <img> to have loading="lazy"source (in <picture>)
5When srcset uses width descriptors, sizes is requiredimg

How It Works

  • Only <img> and <source> elements inside <picture> are checked.
  • Dynamic attribute values (e.g., Vue :srcset, JSX srcset={...}) and elements with spread attributes are skipped.
  • A descriptor-less image candidate (e.g., image.png without 480w or 2x) is treated as an implied 1x density descriptor.
  • sizes="auto" is recognized when auto appears at the start of the attribute value (case-insensitive). For example, sizes="auto, 100vw" is treated as auto, but sizes="100vw, auto" is not.

Examples

❌ Examples of incorrect code for this rule

<!-- Check 1: sizes + density descriptors -->
<img srcset="a.png 1x, b.png 2x" sizes="100vw" src="a.png" alt="photo" />

<!-- Check 2: mixing width and density descriptors -->
<img srcset="a.png 480w, b.png 2x" src="a.png" alt="photo" />

<!-- Check 3: sizes=auto without loading=lazy -->
<img srcset="a.png 480w" sizes="auto" src="a.png" alt="photo" />

<!-- Check 4: source sizes=auto without lazy img -->
<picture>
<source srcset="a.webp 480w" sizes="auto" />
<img src="a.jpg" alt="photo" />
</picture>

<!-- Check 5: width descriptors without sizes -->
<img srcset="a.png 480w, b.png 1024w" src="b.png" alt="photo" />

✅ Examples of correct code for this rule

<!-- Width descriptors with sizes -->
<img srcset="a.png 480w, b.png 1024w" sizes="(max-width: 600px) 480px, 1024px" src="b.png" alt="photo" />

<!-- Density descriptors without sizes -->
<img srcset="a.png 1x, b.png 2x" src="a.png" alt="photo" />

<!-- sizes=auto with loading=lazy -->
<img srcset="a.png 480w" sizes="auto" loading="lazy" src="a.png" alt="photo" />

<!-- source sizes=auto with lazy img -->
<picture>
<source srcset="a.webp 480w" sizes="auto" />
<img src="a.jpg" loading="lazy" alt="photo" />
</picture>

Note on overlap with invalid-attr

Check 2 (descriptor mixing) overlaps with the Srcset type validator used by the invalid-attr rule. When both rules are enabled, mixing width and density descriptors may be reported by both rules. This is intentional — invalid-attr validates the srcset attribute value syntax, while this rule checks inter-attribute constraints. If you want to avoid duplicate reports for descriptor mixing, you can rely on invalid-attr alone for that check.

References

Interface

{
"srcset-sizes-constraint": boolean
}

Default Severity

error