Git hooks and pre-commit: Automatic checks before the commit
In short: Git hooks run scripts on certain events, such as before a commit; this lets formatting, linting, tests and secret scans be enforced automatically.
In more detail: Finding errors early saves time. Git hooks are scripts in the folder .git/hooks/ that Git starts on events: pre-commit, commit-msg, pre-push, post-merge and others. If a hook returns an error code, Git aborts the action.
In Depth
Example: own hook
#!/bin/sh
# .git/hooks/pre-commit (make executable: chmod +x)
npm run lint --silent || {
echo "Lint errors: commit aborted"; exit 1;
}Problem: .git/hooks is not versioned and not shared with the team. Better: manage hooks with a tool that installs them from the repository.
Tools
- pre-commit (Python-based, language-independent): configuration in
.pre-commit-config.yaml, installationpre-commit install; hooks for Black, Ruff, Prettier, ESLint, shellcheck, gitleaks, trailing whitespace and much more. - Husky + lint-staged (JavaScript): checks only changed files.
- Lefthook (fast, Go).
- In the Git configuration:
git config core.hooksPath .githooksif the folder lies in the repo.
# .pre-commit-config.yaml
repos:
- repo: https://github.com/astral-sh/ruff-pre-commit
rev: v0.5.0
hooks: [{id: ruff}, {id: ruff-format}]
- repo: https://github.com/gitleaks/gitleaks
rev: v8.18.0
hooks: [{id: gitleaks}]What to have checked
- Formatting and linting (keep fast so nobody bypasses the hooks).
- Secrets (gitleaks) and large files.
- Commit messages (commit-msg, Conventional Commits).
- Quick tests before the push (
pre-push). - No merge-conflict markers, no
console.log/debugger. Slow checks (the full test suite) belong in CI.
Limits
Hooks are local and bypassable (git commit --no-verify), so no replacement for CI and server rules (branch protection, required checks, required reviews). They are a convenience that makes errors visible early. Keep them fast (under a few seconds), document the setup in the README and check again in CI.
See also: CI/CD pipeline, Conventional Commits, Managing secrets