Repository navigation
chore: replace husky and lint-staged with a Git hook - #165
Merged
Merged
Conversation
Both packages were installed but never wired: there is no `.husky/` directory and no `prepare` script, so no hook ever ran. Replace them with a checked-in hook that uses Biome's own `--staged` mode. • Remove `husky`, `lint-staged`, and `.lintstagedrc.json`. • Add `.githooks/pre-commit`, which formats and lints staged files with the local Biome binary and refuses to rewrite the index when staged files also have unstaged changes (`MM`, `AM`, and the other mixed states). • Add `scripts/install-hooks.js` plus `prepare` and `hooks:install` scripts. It points `core.hooksPath` at `.githooks` only when unset or already pointing there, so a developer's own hooks directory is never overwritten, and exits silently outside a Git checkout. • Migrate `linter.recommended` to `preset` (deprecated in Biome 2.6) so hook and CI output stay clean.
cawalch
force-pushed
the
chore/replace-husky-with-git-hooks
branch
from
November 1, 2026 16:52
79861cf to
a4ebb3a
Compare
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.
Remove
huskyandlint-staged— neither has ever run in this repository — and replace them with a checked-in Git hook that uses Biome's own--stagedmode. No hook framework and nonpxin the commit path.Is
.githooksidiomatic?core.hooksPathwith a version-controlled directory is Git's recommended mechanism (Git 2.9+) and is documented by Biome's own shell-script recipe. It is still a minority pattern: roughly 5,000 indexed public repositories configure it frompackage.json, against about 285,000 that use"prepare": "husky". So: legitimate, but not the default expectation — the trade-offs are called out below.Why not keep the existing tools: there is no
.husky/directory and nopreparescript, so both packages were dead weight. Husky's last release was v9.1.7 in November 2024 (only documentation commits since), andlint-staged@17requires Node ≥22.22.1 while this package still declares>=20.19.0.Why not swap in Lefthook (Biome's first recommendation): it is fast and actively maintained, but adds a Go binary plus a
postinstallscript that needs npm 12 install-script approval. For one Biome command, the native route is smaller and has no supply-chain surface.Changes
• Remove
husky,lint-staged, and.lintstagedrc.json(8 packages leave the tree).• Add
.githooks/pre-commit: format, organize imports, lint, and apply safe fixes to staged files only, then re-stage the result. It calls./node_modules/.bin/biomerather thannpx.• Refuse to rewrite the index when staged files also have unstaged changes — every mixed state (
MM,AM,RM, …), not justMM;git update-index --againwould otherwise silently include those edits.• Add
scripts/install-hooks.jswithprepareandhooks:installscripts. It readscore.hooksPathfirst and only writes when it is unset or already.githooks, so a developer's own hooks directory is never overwritten. Outside a Git checkout it exits silently.• Migrate
linter.recommendedtopreset(deprecated in Biome 2.6), which was printing a warning on every lint run.Concerns and trade-offs
preparepoints Git at the hook afternpm install, so checked-in code runs on the next commit. This is the same trust model as Husky.git commit --no-verifybypasses it, and an existingcore.hooksPathis left untouched.sh; Git for Windows provides one, but there is no Windows CI job to prove it.lint:ciandtypecheck; the hook is a convenience, not the enforcement.prepareentry and keepnpm run hooks:installexplicit if automatic installation is unwanted.Verification
export const hookTest = { a: 1, b: 2 };) and re-staged the fix;git hook run pre-commitresolves viacore.hooksPath.AM) and modified a tracked file after staging (MM): both refused with "Some staged files have unstaged changes".core.hooksPathto.custom-hooks, ran the installer: value preserved. Unset it and ran again: set to.githooks.npm run install-hooksoutside a Git checkout: exits 0.npm run lint:ci,npm run typecheck,npm run build,npm test— 1,380 tests passed;npm audit— 0 vulnerabilities.npm pack --dry-run— 29 files, unchanged:filesisdist/, so the hook and installer are not published.CI (22.x/24.x/26.x), OSV, and
verify-lockfilerun on this pull request.