Yes. A pre-commit hook runs on the developer's machine, and Git lets anyone bypass it with a flag. Hooks are also not copied when you clone. So a pre-commit secret check is a helpful first filter, not an enforcement point. Enforce on the server with CI checks or push time blocking.
What the Git documentation says
The githooks reference states that the pre-commit hook is invoked by git commit and can be bypassed with the --no-verify option. If the hook exits with a non-zero status, the commit is aborted. That is the whole mechanism: a script on the local machine, which the person at the keyboard controls.
The pre-commit framework adds its own convenience. Setting a SKIP variable skips named hooks for one commit, so a developer does not need to skip all of them.
Why hooks are not copied
Hooks live in the repository's local .git/hooks folder by default, which is not part of what gets cloned. The pre-commit framework documentation says that after cloning, running pre-commit install should always be the first thing you do. People forget.
Two Git features reduce the friction. The core.hooksPath setting points Git at another directory, such as a committed .githooks folder. A template directory can seed hooks into new clones. Both still rely on each developer's configuration.
Where to enforce instead
| Layer | Can a developer skip it? | Best used for |
|---|---|---|
| Pre-commit hook | Yes | Fast feedback before the secret is in history |
| CI job on pull request | Not without changing CI config, which is reviewed | Required status check on every change |
| Server side pre-receive hook | No, runs before refs update | Blocking pushes that contain secrets |
| Platform push protection | Usually only with a logged bypass | Blocking at push time with an audit trail |
The Git documentation notes that a pre-receive hook runs once per push, just before refs are updated, and if it exits non-zero none of the refs are updated. That makes it a real gate, because the client cannot opt out.
A sensible setup
- Offer the local hook, and make installing it a line in the contributing guide.
- Run the same scanner in CI as a required check, using
pre-commit run --all-filesor a changed-files range. - Protect the default branch so the check must pass before merge.
- Where your platform supports it, turn on push time blocking.
- Log bypasses and review them.
The local hook is there for speed. The server side check is there for certainty. Our post on pre-commit versus CI checks covers the split in more detail.
Try it yourself
Click through it at your own pace, or open it full screen. Look at how a gate on the pull request cannot be skipped from a laptop.
Quick check
If someone bypasses the hook and commits a secret, what next?
Treat it as exposed once it is pushed: revoke and rotate it. A server side check should have stopped the push or flagged the pull request.
Is a pre-commit hook still worth having?
Yes. Catching a secret before it enters history saves a rotation. Just do not rely on it alone.
Safeguard runs policy gates on pull requests, and you can try a free scan on your repository.
Sources
Last reviewed: 19 October 2026.