pre-commit
pre-commit is a framework that runs a list of checks on the files you are about to commit and refuses the commit if one fails. Every platform repository carries a .pre-commit-config.yaml, so the same formatters, scanners and guard scripts that CI runs also run on an engineer's machine first.
What it does
The configuration names hook repositories and pinned versions; pre-commit install wires them into Git, and pre-commit run --all-files runs everything on demand. Hooks can be published ones (formatters, linters) or local scripts from the repository itself. A global exclude pattern keeps generated folders out of every hook.
How BuiltForProd uses it
Infrastructure repositories (acme-aws-platform-baseline, acme-aws-blueprint-webapp-infra, acme-aws-blueprint-etl-infra) share one shape:
| Hook source | Hooks |
|---|---|
| Local guard scripts | check-mock-outputs.py (every dependency has complete mocks), check-stack-layout.py (a stack file beside every region.hcl, every unit definition referenced, nothing generated in the catalog), check-module-versions.py (module versions.tf matches root.hcl), check-required-inputs.py (every unit supplies its module's required inputs; renders the generated units, so Terragrunt must be installed) |
pre-commit-hooks v6.0.0 | Trailing whitespace, end-of-file newline, YAML syntax, merge-conflict markers, private-key detection |
pre-commit-opentofu v2.4.2 | tofu_fmt, tofu_validate, tofu_docs |
pre-commit-terraform v1.109.1 | terragrunt_fmt, terraform_trivy, and in the Baseline terraform_tflint |
| Checkov 3.3.19 | Terraform framework, compact output |
The Baseline adds two address-plan guards: check-no-hardcoded-cidrs.py, which rejects any private CIDR literal in .hcl or .tf files, and check-vpc-maps.py, which validates both VPC map files, including the inactive one, so switching maps stays possible.
Code repositories (acme-aws-blueprint-webapp-code, acme-aws-blueprint-etl-code) run the same pre-commit-hooks, ruff and ruff-format (v0.16.8) for Python, and Checkov over the tree. The web application repository also runs helmlint from the Gruntwork hooks on the chart.
The exclude pattern in every infrastructure repository skips .terragrunt-cache/, .terragrunt-stack/, .terraform/modules/ and .external_modules/, so hooks never lint generated or downloaded code. The contributor rules in instructions.md list the same checks as the validation to run before any commit, and note the one expected offline failure: the web application's EKS units need AWS credentials to render because they look up the account id.
Terms you will see
| Term | Meaning |
|---|---|
| Hook | One check, with the files it applies to. |
| Local hook | A script from this repository rather than a published package. |
rev | The pinned version of a hook repository. |
pass_filenames: false | Run the hook once over the tree rather than per changed file. |
| Guard script | A platform-specific check under scripts/ that CI runs too. |
Where to read more
- Checkov, Trivy and tflint for the scanners among the hooks
- Terragrunt for the layout the guards protect
- Policy as code