taste-lint 0.3.0 → 0.4.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (48) hide show
  1. package/data/corpus/copywriting.jsonl +4 -4
  2. package/data/rule-drafts/interaction/interaction-layout-shift.yaml +3 -3
  3. package/data/rules/copywriting/copywriting-antithesis-contrast.yaml +43 -0
  4. package/data/rules/copywriting/copywriting-antithesis-frame.yaml +4 -2
  5. package/data/rules/copywriting/copywriting-artificial-balance.yaml +4 -1
  6. package/data/rules/copywriting/copywriting-boilerplate-offer.yaml +1 -1
  7. package/data/rules/copywriting/copywriting-canned-phrasing.yaml +1 -1
  8. package/data/rules/copywriting/copywriting-claim-without-evidence.yaml +10 -1
  9. package/data/rules/copywriting/copywriting-copula-avoidance.yaml +1 -1
  10. package/data/rules/copywriting/copywriting-dead-link.yaml +28 -0
  11. package/data/rules/copywriting/copywriting-em-dash-in-ui.yaml +23 -0
  12. package/data/rules/copywriting/copywriting-excessive-hedging.yaml +1 -1
  13. package/data/rules/copywriting/copywriting-external-arrow-internal-link.yaml +26 -0
  14. package/data/rules/copywriting/copywriting-fabricated-specificity.yaml +6 -3
  15. package/data/rules/copywriting/copywriting-generic-framing.yaml +12 -6
  16. package/data/rules/copywriting/copywriting-generic-language.yaml +12 -4
  17. package/data/rules/copywriting/copywriting-generic-validation.yaml +1 -1
  18. package/data/rules/copywriting/copywriting-machine-prose.yaml +4 -1
  19. package/data/rules/copywriting/copywriting-mechanism-over-outcome.yaml +4 -1
  20. package/data/rules/copywriting/copywriting-meta-commentary.yaml +1 -1
  21. package/data/rules/copywriting/copywriting-missing-reasoning-link.yaml +4 -1
  22. package/data/rules/copywriting/copywriting-over-explanation.yaml +4 -1
  23. package/data/rules/copywriting/copywriting-participle-tail.yaml +1 -1
  24. package/data/rules/copywriting/copywriting-prompt-restatement.yaml +5 -2
  25. package/data/rules/copywriting/copywriting-punctuation-tics.yaml +4 -1
  26. package/data/rules/copywriting/copywriting-reader-first.yaml +4 -1
  27. package/data/rules/copywriting/copywriting-repetitive-transitions.yaml +1 -1
  28. package/data/rules/copywriting/copywriting-semantic-links.yaml +2 -2
  29. package/data/rules/copywriting/copywriting-slogan-headings.yaml +27 -0
  30. package/data/rules/copywriting/copywriting-structural-symmetry.yaml +4 -1
  31. package/data/rules/copywriting/copywriting-tee-up.yaml +4 -2
  32. package/data/rules/copywriting/copywriting-unexplained-action.yaml +5 -2
  33. package/data/rules/copywriting/copywriting-unnatural-polish.yaml +8 -5
  34. package/data/rules/copywriting/copywriting-unverifiable-proof.yaml +1 -1
  35. package/data/rules/copywriting/copywriting-vague-error.yaml +2 -0
  36. package/data/rules/craft/craft-atmosphere-gradient.yaml +1 -1
  37. package/data/rules/craft/craft-decoration-no-role.yaml +2 -1
  38. package/data/rules/craft/craft-decorative-ordinals.yaml +26 -0
  39. package/data/rules/craft/craft-faux-product-chrome.yaml +4 -1
  40. package/data/rules/schema/rule.schema.json +7 -1
  41. package/dist/cli.js +565 -97
  42. package/dist/cli.js.map +1 -1
  43. package/dist/index.d.ts +34 -18
  44. package/dist/index.d.ts.map +1 -1
  45. package/dist/index.js +275 -17
  46. package/dist/index.js.map +1 -1
  47. package/package.json +2 -2
  48. package/data/rules/copywriting/copywriting-idea-repetition.yaml +0 -34
@@ -1,6 +1,7 @@
1
1
  # One of the 21 AI-writing checks Every ran with Jev (Mike Taylor, "Jev judged
2
- # everything I've written in 0.7 seconds", 15 Sep 2026). The question is the
3
- # published wording; the second sentence says what to ignore.
2
+ # everything I've written in 0.7 seconds", 15 Sep 2026). The question started as
3
+ # the published wording; it now also says what cannot be a violation, because
4
+ # Jev read plain labels, identifiers and instructions as violations (2026-09-23 eval).
4
5
  # Candidate list from EveryInc/compound-writing skills/cw-ai-check/SKILL.md, category 0 (structural overcompletion, performed voice).
5
6
  id: copywriting-unnatural-polish
6
7
  title: Polished in a way that suppresses personal texture
@@ -27,18 +28,20 @@ preconditions:
27
28
  question:
28
29
  context: [docType]
29
30
  instructions: >-
30
- Does the writing feel polished in a way that suppresses personal texture or irregularity? Ignore reference documentation and UI copy, where a neutral register is the point.
31
+ Is the writing polished in a way that suppresses personal texture: smooth, abstract praise or summary where a specific fact, opinion or rough edge should be? Neutral, plain writing is not polish. Answer no for instructions, technical explanation, data, labels, names, identifiers and headings, and for any sentence that states a concrete fact, number or opinion, even if no person is visible. Ignore reference documentation and UI copy, where a neutral register is the point.
31
32
  criteria:
32
33
  true:
33
- what: Even, frictionless prose with no person behind it.
34
+ what: Even, frictionless prose that smooths over what should be specific.
34
35
  examples:
35
36
  - "The initiative delivered meaningful improvements across several dimensions, and stakeholders responded positively to the enhanced experience."
36
37
  - "Each component was carefully considered to ensure a cohesive, thoughtful result that balances form and function."
37
38
  false:
38
- what: Prose with a specific person, opinion or rough edge in it.
39
+ what: Prose with a specific fact, person, opinion or rough edge in it, or plain functional text.
39
40
  examples:
40
41
  - "I hated the old settings page. It had 14 toggles and I could never remember which one hid the sidebar."
41
42
  - "The first version was ugly and we shipped it anyway, because the two people who needed it were waiting."
43
+ - "Run commands from the repository root:"
44
+ - "Each enabled scout runs once per day and draws from the 24-run daily budget."
42
45
  thresholds: { review: 0.4, act: 0.75 }
43
46
  severity: minor
44
47
  fix:
@@ -26,4 +26,4 @@ review:
26
26
  exceptions: Clearly labeled placeholders, teaching examples, chart data, and claims supported by supplied evidence.
27
27
  evidence: The exact claim and location, its displayed context, and a checkable source or an accountable owner.
28
28
  verification: Verify the claim against its source or remove only the unsupported claim; preserve real evidence and clearly marked examples.
29
- sourceHash: 0901fbcaeac7ed1d59328aa3012fb808332c4761ab4cb44c268433eb5a48d7f1
29
+ sourceHash: fd0234fa235214885b51d0645416a224ec35fa32d3990bba46817f6c13932aba
@@ -15,6 +15,8 @@ mechanical:
15
15
  - an error has occurred
16
16
  - something went wrong
17
17
  - please try again
18
+ - try again
19
+ - try saving again
18
20
  - try again later
19
21
  - oops
20
22
  - invalid
@@ -24,5 +24,5 @@ review:
24
24
  exceptions: Brand colours, data visualisation ramps, and illustrations where the gradient carries meaning.
25
25
  evidence: The brand palette and what the gradient surface contains.
26
26
  verification: Confirm the gradient carries a brand or content role, or replace it with a flat surface from the theme.
27
- sourceHash: 696321dfa9cb90a6d31bba628bba33aecf23ff4aaadd3516ca2a2eea4e6219e1
27
+ sourceHash: fd4edd9d4dc8f0ec9c09c49390e37482535f899972c5d7c15c9d8f1344360f82
28
28
  handWritten: [mechanical, fix, review, scope]
@@ -1,3 +1,4 @@
1
+ # The mechanical regex is widened from the source: an empty element hung off the box by a negative offset counts as decorative, and so does a large bordered ring (GPT-6 and Opus output, 2026-09-23).
1
2
  id: craft-decoration-no-role
2
3
  title: Stacked decorative layers with no role
3
4
  categoryId: generic-decoration
@@ -14,7 +15,7 @@ unit:
14
15
  - source
15
16
  mechanical:
16
17
  flags: gus
17
- regex: <(?:div|span)\b(?=[^>]*?(?:\babsolute\b|\bfixed\b))(?=[^>]*?(?:pointer-events-none|aria-hidden))(?=[^>]*?(?:gradient|bg-linear|bg-radial|\bblur|backdrop-blur|mix-blend|opacity-))(?![^>]*?(?:size-\[max\(100%|pointer-fine:hidden|bg-clip-text|\bmask-))[^>]*?/>
18
+ regex: '<(?:div|span)\b(?=[^>]*?(?:\babsolute\b|\bfixed\b))(?=[^>]*?(?:pointer-events-none|aria-hidden|["\s]-(?:inset|top|right|bottom|left)-(?:[2-9]|\d{2})\b))(?=[^>]*?(?:gradient|bg-linear|bg-radial|\bblur|backdrop-blur|mix-blend|opacity-|(?=[^>]*?\brounded-full\b)(?=[^>]*?\bborder\b)(?=[^>]*?\b(?:h|w|size)-(?:[2-9]\d|\d{3})\b)))(?![^>]*?(?:size-\[max\(100%|pointer-fine:hidden|bg-clip-text|\bmask-))[^>]*?/>'
18
19
  severity: minor
19
20
  fix:
20
21
  hint: "A blurred blob, a grid overlay, a noise layer and a radial glow behind the heading: absolutely positioned elements that contain nothing and mean nothing. Cut them until each remaining layer has a job a reader could name."
@@ -0,0 +1,26 @@
1
+ # Hand-ported: the upstream rg pattern, narrowed to JSX text.
2
+ id: craft-decorative-ordinals
3
+ title: Ordinal numbers on items that are not a sequence
4
+ categoryId: generic-decoration
5
+ source:
6
+ repo: mblode/agent-skills
7
+ path: skills/ui-design/rules/slop-decorative-ordinals.md
8
+ line: 10
9
+ ruleId: slop-decorative-ordinals
10
+ scope:
11
+ include: ["**/*.tsx", "**/*.jsx"]
12
+ unit: [source]
13
+ mechanical:
14
+ regex: '\b(?:number|num|step|index|idx|no|label|eyebrow)\s*:\s*["''`]0[1-9]\b|>\s*0[1-9]\s*[./)]?\s*<'
15
+ flags: gu
16
+ severity: minor
17
+ fix:
18
+ hint: Drop the numbers unless the order is real (install steps, a setup flow, a fallback chain). Cards a reader could shuffle need no number.
19
+ status: review-only
20
+ review:
21
+ applicability: "Zero-padded numbers label cards or sections."
22
+ exceptions: "A real sequence: install steps, a setup flow, a ranked list, a fallback chain."
23
+ evidence: "Whether the items could be reordered without changing their meaning."
24
+ verification: "Confirm the order means nothing, then remove the numbers."
25
+ sourceHash: ae618ad62bb446ec2c7019f60acfe8ca48d1f5adea14ba6286463446cf596be9
26
+ handWritten: [mechanical]
@@ -1,4 +1,5 @@
1
1
  # Ported from mblode/agent-skills skills/ui-design/rules/slop-faux-product-chrome.md by scripts/port-rules.ts.
2
+ # The mechanical regex is widened from the source: three adjacent empty dots of any colour (Opus, Astra and Sol drew them in pastel and hex, 2026-09-23).
2
3
  # Keys listed in handWritten are preserved on re-run; everything else is regenerated.
3
4
  id: craft-faux-product-chrome
4
5
  title: Faux product chrome wrapping nothing
@@ -15,11 +16,13 @@ unit:
15
16
  - source
16
17
  mechanical:
17
18
  flags: gu
18
- regex: rounded-full[^"`]*\bbg-(red|rose|yellow|amber|green|emerald)-[45]00
19
+ regex: '(?:<(?:span|div|i)\b(?=[^>]*\brounded-full\b)(?=[^>]*\b(?:size|h)-(?:1|1\.5|2|2\.5|3|3\.5)\b)[^>]*/>\s*){3}'
19
20
  severity: minor
20
21
  fix:
21
22
  hint: "Three coloured dots in a row, a rounded bar with a URL typed into it, a laptop outline around an empty gradient panel: this is a drawing of a product where the product should be. A visitor reads it as a screenshot, leans in to see what the app actually looks like, and finds there is nothing to see. "
22
23
  status: review-only
24
+ handWritten:
25
+ - mechanical
23
26
  review:
24
27
  applicability: Decorative browser or device chrome presents itself as a product preview.
25
28
  exceptions: Real screenshots, video, rendered product content, labeled status dots, and intentionally illustrative examples.
@@ -127,7 +127,9 @@
127
127
  "writingFacts",
128
128
  "writingProfile",
129
129
  "writingInstructions",
130
- "section"
130
+ "section",
131
+ "earlier",
132
+ "brief"
131
133
  ]
132
134
  }
133
135
  },
@@ -224,6 +226,10 @@
224
226
  },
225
227
  "smartQuotesAtBuild": {
226
228
  "const": false
229
+ },
230
+ "minWords": {
231
+ "type": "integer",
232
+ "minimum": 1
227
233
  }
228
234
  }
229
235
  },