Skip to content
Back to blog
CI/CD

Pre-commit Hooks for Security Scanning

Which security checks belong in a pre-commit hook versus CI, and how to set them up without slowing developers down or training them to bypass checks.

S
SecureScout Team· Security Engineering
August 1, 20265 min read

A pre-commit hook is local, fast feedback — the earliest point in the entire development lifecycle a check can run. That speed constraint is also what determines which checks actually belong there.

What belongs in a pre-commit hook

The bar is: fast (sub-second to a couple seconds), high-confidence (very low false positive rate), and relevant to nearly every commit.

  • Secret detection — scanning staged changes for patterns matching API keys, tokens, and credentials. Fast, and a leaked secret is exactly the kind of mistake worth catching before it's even committed locally.
  • Basic linting for dangerous patterns — things like eval() usage or obviously unsafe string concatenation into queries, where the check is simple and fast.

What doesn't belong there

  • Dependency vulnerability scanning — usually too slow, and doesn't change on every commit.
  • Full SAST scans — comprehensive static analysis is valuable but too slow for a pre-commit loop; it belongs in CI.
  • Anything with meaningful false positives — a hook that blocks commits incorrectly trains developers to bypass it, which defeats the entire purpose.

Setting it up without creating friction

# .pre-commit-config.yaml
repos:
  - repo: https://github.com/gitleaks/gitleaks
    rev: v8.18.0
    hooks:
      - id: gitleaks

Tools like pre-commit (the framework) make this trivial to install consistently across a team, rather than relying on each developer to remember to run a script manually.

Remember: it's not an enforcement boundary

git commit --no-verify bypasses any pre-commit hook trivially. This is fine — the hook's job is fast local feedback, not the actual security guarantee. The real enforcement backstop is the same check running again in CI, where it can't be skipped with a flag.

Don't let it become a second full CI run locally

If a pre-commit hook takes 30+ seconds, developers will find it annoying enough to disable or route around. Keep the local hook narrow and fast, and trust CI to catch anything slower or more thorough that the hook intentionally left out.

The goal of a pre-commit hook isn't total coverage — it's catching the highest-confidence, most damaging mistakes (like a leaked secret) before they even leave a developer's machine.

pre-commitsecret-detectiondeveloper-experience

Frequently Asked Questions

Can developers just bypass a pre-commit hook?

Yes, with `git commit --no-verify` — pre-commit hooks are a convenience and fast-feedback layer, not an enforcement boundary. CI-level checks are what actually enforce the requirement.

Should dependency vulnerability scanning run in a pre-commit hook?

Generally no — it's usually too slow for the tight feedback loop a pre-commit hook needs, and most dependency changes don't happen on every single commit. It fits better as a PR-level or CI check.

Related Articles

S

SecureScout Team

Security Engineering

Learn more →