Skip to content

🏗️✨:lint filenames for kebab-case - #1274

Merged
DerekNonGeneric merged 2 commits into
OpenINF:livefrom
DerekNonGeneric:feat/lint-kebab-case
Aug 13, 2026
Merged

🏗️✨:lint filenames for kebab-case#1274
DerekNonGeneric merged 2 commits into
OpenINF:livefrom
DerekNonGeneric:feat/lint-kebab-case

Conversation

@DerekNonGeneric

@DerekNonGeneric DerekNonGeneric commented Jun 15, 2024

Copy link
Copy Markdown
Member

Picks up the branch opened in June 2024, keeping the intent and replacing the implementation. Filenames should be predictable, and under collections/ a filename is a published URL.

Why the original commits are not in here

Rebasing was tried first and abandoned. The branch was 435 commits behind, and every conflict was in package.json and pnpm-lock.yaml — resolving them meant re-adding recursive-readdir and change-case to a 2026 lockfile only to remove them again. The old tip is c103036 if any of it is wanted back.

What was there could not have worked:

  • The loop was for (path of filepaths) — no declaration. In an ESM module that is a ReferenceError the first time the callback fires, so the script had never run. The final commit message, "this is still missing logging", is consistent with that.
  • The guard was parsedPath.ext === '.ts', and all 29 build task files are .mts now. Even fixed, it would match nothing.
  • recursive-readdir duplicates the glob() helper that replaced globby in 🏗️♻️:replace globby with node's built-in fs.promises.glob #1784, and drags in minimatch@3, brace-expansion@1 and concat-map. change-case would have been a dependency for one function.

Reports, rather than renames

The original was a format task calling renameSync. This is a verify task, and I think that is the more important change: a rename has to be accompanied by updating every import, {% include %} and link that points at the old name, and no formatter can do that. An autofix here would silently change published URLs. Same reasoning as #1803 — a verify task that edits is a verify task you cannot trust.

The title said "lint", so this is faithful to it.

The rule

A name is a run of lowercase words joined by hyphens, with an optional leading underscore for the things Eleventy and Sass mark as not-output (_layouts/, _custom.scss). Extensions are not part of the name, and there may be several (vnu-jar.d.ts).

Two categories are out of scope, because the name is not ours to pick:

  • Anything under a dot-directory.github/ISSUE_TEMPLATE/, .vscode/settings.json, .devcontainer/Dockerfile. Whatever reads them decides what they are called.
  • Shouted metadata namesREADME.md, AUTHORS, COPYING.md, LICENSE/ and the licence identifiers inside it (CC-BY-SA-4.0.txt).

One exemption is spelled out: _data/eleventyDataSchema.mjs. Eleventy takes the global data key from the filename, so kebab-casing it would quietly unhook the front matter validator that #1802 just fixed.

What it catches

Across 212 tracked paths, two — both unreferenced, so the second commit is a rename and nothing else:

_assets/img/sublime-theme/flower_of_life.svg
_assets/img/sublime-theme/prism_outro.svg

Probed with deliberate violations, in the manner of the rest of the pipeline:

planted reported
collections/_pages/snake_case.md yes
collections/_pages/Bad Dir/ yes
collections/_pages/Bad Dir/someFile.md yes
_assets/styles/_OkPartial.scss yes

Considered instead: biome

Biome 2.5.7 has style/useFilenamingConvention with a kebab-case option, and it is free. I did not use it: it only sees the 31 JS/TS files, on this tree it reports exactly one thing and that thing is a false positive (eleventyDataSchema.mjs), and the 134 content files that become URLs are where the risk is. Running both would mean two enforcers with two exemption lists.

Verification

  • nps test — 14/14 tasks pass
  • nps build — 26 copied, 34 written, unchanged by the rename
  • nps verify.filenames exits 0 on this tree, 1 on each planted violation above

Depends on nothing else; #1804 is unrelated but touches the same helper.

@DerekNonGeneric

Copy link
Copy Markdown
Member Author

i think it would be nice to include the no-file-name-consecutive-dashes remark lint rule here (implemented stand-alone in this task), just applied to all relevant files; we can even use the underlying reporter infra from remark-lint to log failure/success

@netlify

netlify Bot commented Aug 12, 2026

Copy link
Copy Markdown

Deploy Preview for gh-pages-openinf ready!

Name Link
🔨 Latest commit 6f44f51
🔍 Latest deploy log https://app.netlify.com/projects/gh-pages-openinf/deploys/6a7d532c8eb41000083265f6
😎 Deploy Preview https://deploy-preview-1274--gh-pages-openinf.netlify.app
📱 Preview on mobile
Toggle QR Code...

QR Code

Use your smartphone camera to open QR code link.

To edit notification comments on pull requests, go to your Netlify project configuration.

@DerekNonGeneric DerekNonGeneric changed the title feat: lint kebab case 🏗️✨:lint filenames for kebab-case Aug 12, 2026
@DerekNonGeneric
DerekNonGeneric marked this pull request as ready for review August 12, 2026 02:38
@DerekNonGeneric
DerekNonGeneric force-pushed the feat/lint-kebab-case branch 2 times, most recently from f612eb7 to 1363f27 Compare August 13, 2026 02:35
Revives the intent of the original branch: filenames should be
predictable, and under `collections/` a filename is a published URL.

Reports rather than renames, which is where this departs from the
earlier attempt. A rename has to be accompanied by updating every
import, include and link that points at the old name, and no formatter
can do that -- an autofix here would silently change URLs.

Names a tool dictates are out of scope: anything under a dot-directory,
and the shouted metadata names (`README.md`, `AUTHORS`, `LICENSE/`).
`_data/eleventyDataSchema.mjs` is exempt outright, since Eleventy takes
the global data key from the filename.

Assisted-by: Claude-Code:claude-opus-5
Nothing references either file, so this is a rename and no more.

Assisted-by: Claude-Code:claude-opus-5
@DerekNonGeneric
DerekNonGeneric merged commit 80f91b7 into OpenINF:live Aug 13, 2026
13 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant