diff --git a/.gitea/workflows/checks.yml b/.gitea/workflows/checks.yml index 5db6bb5..4cffd72 100644 --- a/.gitea/workflows/checks.yml +++ b/.gitea/workflows/checks.yml @@ -286,8 +286,9 @@ jobs: run: | set -eu rm -rf "$WS" && mkdir -p "$WS/goodwe-addon" && cd "$WS/goodwe-addon" - git init -q . - git remote add origin "$(echo "$URL" | sed "s#://#://x-access-token:${TOKEN}@#")" + git init -q . && git remote add origin "$URL" + # Token as an env-set header: not in argv or .git/config (TOOL-9). + export GIT_CONFIG_COUNT=1 GIT_CONFIG_KEY_0=http.extraHeader GIT_CONFIG_VALUE_0="Authorization: token $TOKEN" if [ -n "$PRNUM" ]; then # Two fetches, not one, so that a failure to reach either ref fails # HERE with the ref in the message, rather than inside the merge @@ -498,7 +499,8 @@ jobs: TOKEN: ${{ secrets.INFRA_READ_TOKEN }} run: | set -eu - PIN=$(grep -v '^#' "$WS/goodwe-addon/.gitea/infra-pin" | tr -d '[:space:]') + # `|| true`: under pipefail a missing or comment-only pin would skip the FAIL line (TOOL-9). + PIN=$(grep -v '^#' "$WS/goodwe-addon/.gitea/infra-pin" | tr -d '[:space:]') || true echo "$PIN" | grep -Eq '^[0-9a-f]{40}$' || { echo "FAIL: .gitea/infra-pin holds '$PIN', not a full 40-hex SHA."; exit 1; } test -n "$TOKEN" || { echo "FAIL: secret INFRA_READ_TOKEN is not available to this run (a fork PR?)."; exit 1; } rm -rf "$WS/goodwe" && mkdir -p "$WS/goodwe" && cd "$WS/goodwe" diff --git a/.gitea/workflows/infra-pin.yml b/.gitea/workflows/infra-pin.yml index 133ef90..e39cd02 100644 --- a/.gitea/workflows/infra-pin.yml +++ b/.gitea/workflows/infra-pin.yml @@ -23,16 +23,20 @@ jobs: INFRA_TOKEN: ${{ secrets.INFRA_READ_TOKEN }} # admin/goodwe is private run: | set -eu - D=$(mktemp -d) && cd "$D" - git init -q . && git remote add origin "$(echo "$SELF" | sed "s#://#://x-access-token:${TOKEN}@#")" + D=$(mktemp -d) && trap 'cd / && rm -rf "$D"' EXIT && cd "$D" + git init -q . # The pin of the commit this event is about (the PR head, or the push). - git fetch -q --depth 1 origin "$GITHUB_SHA" - PIN=$(git show FETCH_HEAD:.gitea/infra-pin | grep -v '^#' | tr -d '[:space:]') + # Token as an env-set header: not in argv or .git/config (TOOL-9). + GIT_CONFIG_COUNT=1 GIT_CONFIG_KEY_0=http.extraHeader GIT_CONFIG_VALUE_0="Authorization: token $TOKEN" \ + git fetch -q --depth 1 "$SELF" "$GITHUB_SHA" || { echo "FAIL: could not fetch $GITHUB_SHA here."; exit 1; } + # `|| true`: under the runner's pipefail a missing or comment-only pin + # would stop here on git's error instead of the FAIL line below (TOOL-9). + PIN=$(git show FETCH_HEAD:.gitea/infra-pin | grep -v '^#' | tr -d '[:space:]') || true + test -n "$PIN" || { echo "FAIL: .gitea/infra-pin is missing at $GITHUB_SHA, or holds only comments."; exit 1; } test -n "$INFRA_TOKEN" || { echo "FAIL: secret INFRA_READ_TOKEN is not available to this run (a fork PR?)."; exit 1; } # Header via env, as in checks.yml: the token stays out of argv. HEAD=$(GIT_CONFIG_COUNT=1 GIT_CONFIG_KEY_0=http.extraHeader GIT_CONFIG_VALUE_0="Authorization: token $INFRA_TOKEN" \ - git ls-remote "$INFRA" refs/heads/release/1.0 | cut -f1) - cd / && rm -rf "$D" + git ls-remote "$INFRA" refs/heads/release/1.0 | cut -f1) || true test -n "$HEAD" || { echo "FAIL: could not read admin/goodwe release/1.0."; exit 1; } if [ "$PIN" != "$HEAD" ]; then echo "STALE: .gitea/infra-pin is $PIN but admin/goodwe release/1.0 is $HEAD." diff --git a/goodwe_controller/test_ci_gate.py b/goodwe_controller/test_ci_gate.py index 03c9d1a..1d88981 100644 --- a/goodwe_controller/test_ci_gate.py +++ b/goodwe_controller/test_ci_gate.py @@ -62,10 +62,9 @@ the step it wants: if checks.yml is restructured so that the step cannot be found, this file goes RED rather than quietly grading nothing. ⚠️ NEEDS `git`, which is why .gitea/ci/Dockerfile installs it. No network: the -fixtures are local repositories built in a temp directory, and the workflow's -`git remote add origin "$(echo "$URL" | sed "s#://#://x-access-token:...@#")"` -is a no-op substitution on a path with no `://` in it, which is what lets the -shipped line be used verbatim. +fixtures are local repositories built in a temp directory; the workflow's +token header (TOOL-9) is ignored for a local path, which is what lets the +shipped lines be used verbatim. ⚠️ This file writes only under a temporary directory. It must stay that way: CI mounts the checkout READ-ONLY.