Git pre-commit hooks run once per commit (not per file), so you can filter by file to keep the commits efficient.

git-pre-commit-hooks-run-once-per-commit-not-per-file

Today I learned that Git’s pre-commit hook is executed/triggered once per commit, not once per file included in the commit.

If you want to restrict its behavior to certain files, you need to implement that logic inside your pre-commit script (for example, by checking git diff --cached --name-only to see which files are staged).

✼ Example 1: Strip YAML front matter from README.md

#!/bin/sh
if git diff --cached --name-only | grep -q '^README.md$'; then
if head -n1 README.md | grep -q '^---$'; then
sed '1,/^---$/d' README.md > README.md.tmp && mv README.md.tmp README.md
git add README.md
fi
fi

✼ Example 2: Run a Python script to update README.md

#!/bin/sh
if git diff --cached --name-only | grep -q '^README.md$'; then
python3 .scripts/update_readme.py
git add README.md
fi

By adding file-based checks, you can avoid unnecessary work and speed up commit performance, especially in large projects.

Thanks for reading! If you found this page useful, consider buying me a coffee.
© 2025 Hua-Ming Huang · licensed under CC BY 4.0