#!/usr/bin/env bash # Fast, local sanity checks before a commit is allowed to happen. # # Deliberately dependency-free (plain bash + git + godot), matching the rest # of tools/*.sh -- no pip install, no pre-commit framework, so `tools/install-hooks.sh` # is the entire setup cost for a fresh clone. # # Scope: things that are cheap enough to run on every commit (a few seconds). # The full end-to-end smoke test lives in pre-push instead, where 35s is a # reasonable price to pay less often. set -uo pipefail cd "$(git rev-parse --show-toplevel)" fail=0 staged=$(git diff --cached --name-only --diff-filter=ACMR) if [[ -z "$staged" ]]; then exit 0 fi echo "pre-commit checks..." # --- Hygiene, on every commit, regardless of file type ----------------- if git diff --cached --check --diff-filter=ACMR | grep -q .; then echo "FAIL: unresolved merge conflict markers" git diff --cached --check --diff-filter=ACMR fail=1 fi big=$(git diff --cached --diff-filter=ACMR --name-only -z | \ xargs -0 -I{} du -k "{}" 2>/dev/null | awk '$1 > 5120 {print}') if [[ -n "$big" ]]; then echo "FAIL: file(s) over 5MB staged -- game assets belong outside git history," echo " or need Git LFS if they truly must be tracked:" echo "$big" | sed 's/^/ /' fail=1 fi if grep -qE '^\.godot/$' <(git diff --cached --name-only) 2>/dev/null || \ git diff --cached --name-only | grep -qE '^\.godot/'; then echo "FAIL: .godot/ is generated (import cache + class cache) and must stay gitignored" fail=1 fi # --- GDScript-specific, only when a .gd file is staged ------------------ # addons/ is vendored (GUT) -- not ours to hold to our own style or to parse- # check on every commit; it never changes except on a deliberate upgrade. gd_files=$(echo "$staged" | grep -E '\.gd$' | grep -vE '^addons/' || true) if [[ -n "$gd_files" ]]; then # The Godot style guide (and every file in this repo) indents with tabs. # A stray space-indented line is almost always a paste from somewhere else # and silently breaks nothing today but fights every future diff. space_indented="" while IFS= read -r f; do [[ -f "$f" ]] || continue if grep -nP '^\t* ' "$f" | grep -qv '^\s*#'; then space_indented+="$f"$'\n' fi done <<< "$gd_files" if [[ -n "$space_indented" ]]; then echo "FAIL: space-indented line(s) in (Godot style is tabs):" echo "$space_indented" | sed 's/^/ /' fail=1 fi echo " running tools/check.sh (parse check)..." if ! tools/check.sh; then fail=1 fi echo " running tools/test.sh (GUT suite)..." if ! tools/test.sh; then fail=1 fi fi if [[ $fail -ne 0 ]]; then echo echo "pre-commit FAILED. Fix the above, or skip deliberately with --no-verify." exit 1 fi echo "pre-commit OK"