diff --git a/docs/3-development.md b/docs/3-development.md index 13b5f09..8fffb9f 100644 --- a/docs/3-development.md +++ b/docs/3-development.md @@ -24,7 +24,10 @@ Every tool and hook has a `--self-test` that runs offline: no network, no `gh` l in temporary repos, `gh` stubbed where a command needs it, and fixtures from `scripts/fixtures/`. A change to a script extends its self-test first and watches it fail, then makes it pass. A new script goes into `tests/self-tests.sh`'s `sh_tests` or `py_tests` list, which is the one list -both `just quality` and the flake's `self-tests` check read. +both `just quality` and the flake's `self-tests` check read. A fake script a self-test writes +starts with `#!$BASH` (a Python one runs under `sys.executable`), never `#!/usr/bin/env`: the +flake's sandbox has no `/usr/bin/env`, so such a fake passes locally and fails in CI, and +`tests/self-tests.sh` refuses it. A self-test that creates git repos starts with `unset GIT_DIR GIT_WORK_TREE GIT_INDEX_FILE GIT_PREFIX GIT_COMMON_DIR` and diff --git a/tests/self-tests.sh b/tests/self-tests.sh index 4a5ee6e..a2071b3 100755 --- a/tests/self-tests.sh +++ b/tests/self-tests.sh @@ -27,5 +27,18 @@ t() { # /dev/null | grep -vE '^[^:]+:1:'; } +fx="$(mktemp -d)"; trap 'rm -rf "$log" "$fx"' EXIT +printf '#!/usr/bin/%s bash\ncat >fake <"$fx/red.sh" +printf '#!/usr/bin/%s bash\ncat >fake <"$fx/green.sh" +if [ "$(env_shebangs "$fx/red.sh" | wc -l)" -eq 1 ] && [ -z "$(env_shebangs "$fx/green.sh")" ]; then + echo "ok env-shebang check (fixtures)" +else failed=$((failed + 1)); echo "FAIL env-shebang check: its fixtures were judged wrong"; fi +if offenders="$(env_shebangs scripts plugins tests)"; then + failed=$((failed + 1)); echo "FAIL a fake with an env shebang (use #!\$BASH, or sys.executable in Python):"; sed 's/^/ /' <<<"$offenders" +else echo "ok no env-shebang fakes"; fi [ "$failed" -eq 0 ] || { echo "self-tests: $failed failed" >&2; exit 1; } echo "self-tests: all ok"