Flag inset stripes written with the two-length box-shadow form

box-shadow takes <length>{2,4}: only the two offsets are required, so
`inset 4px 0 red` is valid and paints the same single-edge stripe as
`inset 4px 0 0 red`. The scan demanded a third length, so the short form was
silently missed.

Blur and spread now default to 0 when omitted, which is exactly the stripe shape
the rule looks for. The neutral-color and blur/spread exclusions still hold:
`inset 4px 0 #000` and `inset 4px 0 5px var(--brand-accent)` both pass. Fixture
covers both orders of the short form plus those two exclusions, and fails against
the previous regex.

Third false negative found in this rule (after trailing `inset` and literal
neutral colors), all from the same cause: the scan was written against one
spelling of the syntax rather than the grammar.

Prepared with AI assistance under maintainer direction.

Co-Authored-By: Claude <noreply@anthropic.com>
This commit is contained in:
Paul Bakaus
2026-07-18 12:24:16 -07:00
co-authored by Claude
parent c654acb005
commit 97dbaad4a4
3 changed files with 23 additions and 2 deletions
+6 -2
View File
@@ -425,11 +425,15 @@ function scanInsetStripeCss(rawContent, filePath, lineOffset = 0) {
// an unchanged layer had no inset keyword and is not our shape.
const body = layer.replace(/(^|\s)inset(?=\s|$)/i, '$1').trim();
if (body === layer) continue;
const shadow = body.match(/^(-?\d*\.?\d+)(px)?\s+(-?\d*\.?\d+)(px)?\s+(-?\d*\.?\d+)(px)?(?:\s+(-?\d*\.?\d+)(px)?)?\s+(.+)$/i);
// box-shadow takes <length>{2,4}: only the two offsets are required, so
// `inset 4px 0 red` is valid and paints the same stripe as
// `inset 4px 0 0 red`. Demanding a third length missed the short form.
const shadow = body.match(/^(-?\d*\.?\d+)(px)?\s+(-?\d*\.?\d+)(px)?(?:\s+(-?\d*\.?\d+)(px)?)?(?:\s+(-?\d*\.?\d+)(px)?)?\s+(.+)$/i);
if (!shadow) continue;
const x = Number(shadow[1]);
const y = Number(shadow[3]);
const blur = Number(shadow[5]);
// Omitted blur and spread default to 0, which is exactly the stripe shape.
const blur = shadow[5] == null ? 0 : Number(shadow[5]);
const spread = shadow[7] == null ? 0 : Number(shadow[7]);
if ((x !== 0 && !shadow[2]) || (y !== 0 && !shadow[4]) || blur !== 0 || spread !== 0) continue;
const ax = Math.abs(x);