abenteuer-schmiede/.pre-commit-config.yaml

61 lines
2.9 KiB
YAML

# .pre-commit-config.yaml — rendered by adopt-standard.sh.
# Local mirror of the CI gates: hygiene + shell lint + secret scanning + policy.
# Install: pre-commit install | Run on everything: pre-commit run -a
# See ../SECURITY.md (no plaintext secrets) and SOP-001 (branch & merge).
minimum_pre_commit_version: "3.5.0"
fail_fast: false
repos:
# ── Baseline file hygiene ─────────────────────────────────────────────
- repo: https://github.com/pre-commit/pre-commit-hooks
rev: v4.6.0
hooks:
- id: trailing-whitespace
# Preserve markdown hard line breaks (two trailing spaces).
args: [--markdown-linebreak-ext=md]
- id: end-of-file-fixer
- id: check-yaml
args: [--allow-multiple-documents]
- id: check-added-large-files
args: [--maxkb=1024]
- id: check-merge-conflict
- id: mixed-line-ending
args: [--fix=lf]
# ── Shell lint (POSIX / MinGW-safe scripts) ───────────────────────────
- repo: https://github.com/shellcheck-py/shellcheck-py
rev: v0.10.0.1
hooks:
- id: shellcheck
args: [--severity=warning]
# ── Secret scanning — no plaintext secrets, ever ──────────────────────
- repo: https://github.com/gitleaks/gitleaks
rev: v8.18.4
hooks:
- id: gitleaks
# ── Local project hooks (no external pin; degrade gracefully) ─────────
- repo: local
hooks:
# Optional: validate config/manifests against the standard's Rego
# policies. Skipped automatically if `conftest` is not installed, so a
# missing optional binary never blocks a commit (graceful degradation).
- id: conftest
name: conftest (policy gate, optional)
entry: 'bash -c ''command -v conftest >/dev/null 2>&1 && conftest test --policy policies . || echo "conftest not installed - skipping policy gate"'''
language: system
pass_filenames: false
always_run: true
# Refuse to commit any *.sops.yaml / *.enc.yaml that is NOT actually
# SOPS-encrypted (i.e. missing the `sops:` metadata block). This catches
# the classic "saved the plaintext under the encrypted name" mistake.
# Implementation note: `grep -L` lists files MISSING the marker (no shell
# loop, no nested double quotes) so it survives the YAML/shell quoting layers.
# The marker is `sops:` (SOPS-YAML) or `"sops"` (SOPS-JSON).
- id: sops-encrypted-check
name: sops-encrypted-check (no plaintext under encrypted names)
entry: 'bash -c ''bad=$(grep -L -E ''"''"''^sops:|"sops"''"''"'' "$@"); if [ -n "$bad" ]; then echo "ERROR: named encrypted but missing SOPS metadata:"; echo "$bad"; exit 1; fi'' --'
language: system
files: '\.(sops|enc)\.(yaml|json)$'