fix(defaults): repair class attributes mangled by a class sorter - #2210
Merged
Conversation
`9e06583afc` ("chore: fix lint errors", 542 files) ran a Tailwind-style class
sorter over `class="..."` values. It split them on whitespace without
respecting `{{ }}` boundaries, so `{{`, the expression, and `}}` were sorted as
if they were class names:
before class="mx-auto max-w-7xl px-4 sm:px-6 lg:px-8 {{ className }}"
after class="mx-auto px-4 sm:px-6 lg:px-8 max-w-7xl {{ }} className"
stx then throws on the orphaned operators, which aborts the build once the
route scanner reaches the file.
61 attributes across 23 files, not the single view #2209 reported. That one is
gone from the tree already, but `storage/framework/defaults/resources/` is live
(`frameworkPath('defaults/resources/…')`, path/src/index.ts:416) and `buddy new`
copies the repo wholesale, so every one of these shipped into scaffolded apps.
Repaired mechanically rather than by rewriting intent. A sort permutes but
preserves the token multiset, so each mangled value matches exactly one
pre-commit value under `tokens.sort()` - 61/61 matched, 0 ambiguous. That
matters at this volume: hand-reconstructing 61 ternaries invites new bugs, and
the nested cases are genuinely hard to read, e.g.
": : ? ? '' 'bg-blue-100 'bg-gray-100 'ring-2 {{ {{ }} }} <= == currentStep
currentStep loop.index loop.index"
recovers to two separate expressions in one attribute.
`ModelRecordsDashboard.stx` is deliberately untouched: its two `{{ }}` hits are
prose in comments explaining that a placeholder in a class attribute is not
reactively bound.
The current formatter no longer does this - verified `pickier --fix` and
`buddy format --write` both leave `{{ ternary }}`-in-class intact - so this is
committed damage, not a live regression.
Closes #2209
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Closes #2209.
It's 61 attributes across 23 files, not one view
The issue found
blog/category.stxand noted it may already be gone upstream. It is — but the same corruption is sitting in 23 other files that are still shipped.storage/framework/defaults/resources/is live (frameworkPath('defaults/resources/…'),path/src/index.ts:416) andbuddy newcopies the repo wholesale, so all 61 reached every scaffolded app. One of them is inresources/components/InputGroup.stx— this repo's own app code.Root cause:
9e06583afcgit log -Spins it to9e06583afc"chore: fix lint errors" (2026-04-14, 542 files). It ran a Tailwind-style class sorter overclass="..."that split on whitespace without respecting{{ }}boundaries, so{{, the expression, and}}sorted as if they were class names:The tell is that the classes really are in sort order. stx then throws on the orphaned operators, aborting the build once the route scanner reaches the file.
Not a live regression. I verified both
pickier --fixandbuddy format --writeleave{{ ternary }}-in-class intact today. This is committed damage.Repaired mechanically, not by rewriting intent
A sort permutes but preserves the token multiset, so each mangled value matches exactly one pre-commit value under
tokens.sort(). 61/61 matched, 0 ambiguous.That mattered at this volume — hand-reconstructing 61 ternaries invites fresh bugs, and the nested cases are genuinely unreadable:
recovers to two separate expressions in one attribute:
Deliberately untouched
ModelRecordsDashboard.stxhas two{{ }}hits that are prose in comments, explaining that a placeholder in a class attribute is not reactively bound. The repair skips it, and the audit grep excludes it.Verification
lintStxStrict(0 parse errors)Follow-up
The issue's second ask — "audit for other similarly-mangled
{{ … }}-in-attribute default views" — is what found these. To stop it recurring, an empty-interpolation-inside-an-attribute check belongs inbuddy lint --stx(#2208), scoped to attribute values so the comment case above stays legal. I'll add it there rather than widening this PR.🤖 Generated with Claude Code