From f7a84178c28fafef2cf9818cdc0dc8a047f995f1 Mon Sep 17 00:00:00 2001 From: samuelburnham <45365069+samuelburnham@users.noreply.github.com> Date: Wed, 2 Sep 2026 14:45:21 -0400 Subject: [PATCH] Authenticate CI git fetches of GitHub repos GitHub throttles anonymous git HTTPS traffic per source IP, and Warp runners share egress IPs across tenants. Starting 2026-09-02 ~12:30 UTC that pool was throttled, so unauthenticated clones of public repos began failing with 401s ("could not read Username for 'https://github.com'"): Nix's eval-time builtins.fetchGit of Lake manifest dependencies broke Nix CI, and Lake's own dependency clone broke cuda-compile, across unrelated PRs. Add an authenticate-github-fetches composite action that rewrites github.com URLs via `url.insteadOf` to carry the job's ephemeral GITHUB_TOKEN, moving every git-CLI fetch (Lake dependencies, eval-time fetchGit, script clones) off the shared anonymous IP pool and onto per-token limits. Wire it into: - setup-rust-toolchain, alongside CARGO_NET_GIT_FETCH_WITH_CLI=true so cargo's git dependencies fetch through the git CLI and pick up the rewrite (cargo's built-in fetcher ignores insteadOf); - both nix.yml jobs, which don't use that wrapper (install-nix-action's github_access_token covers only `github:` flake inputs, not git+https fetchGit); - the bench compile jobs in bench-main and bench-pr, whose `lake build Compile` clones mathlib and friends without the wrapper. In bench-pr this puts the token in ~/.gitconfig where checked-out PR code can read it, which persist-credentials: false previously kept off disk. That is acceptable: the workflow's permissions block pins the token to read-only on a public repo (the dispatch job's actions:write never runs PR code), so the exposure matches an ordinary pull_request run. Toolchain-only lean-action jobs (build: false) clone nothing and are left alone, as is CodeQL, which manages its own fetches. --- .../authenticate-github-fetches/action.yml | 20 +++++++++++++++++++ .../actions/setup-rust-toolchain/action.yml | 13 ++++++++++++ .github/workflows/bench-main.yml | 2 ++ .github/workflows/bench-pr.yml | 2 ++ .github/workflows/nix.yml | 6 ++++++ 5 files changed, 43 insertions(+) create mode 100644 .github/actions/authenticate-github-fetches/action.yml diff --git a/.github/actions/authenticate-github-fetches/action.yml b/.github/actions/authenticate-github-fetches/action.yml new file mode 100644 index 000000000..72d60e811 --- /dev/null +++ b/.github/actions/authenticate-github-fetches/action.yml @@ -0,0 +1,20 @@ +name: Authenticate git fetches of GitHub repos +description: >- + Rewrite github.com URLs so git-CLI fetches carry the job's ephemeral token. + GitHub throttles anonymous git HTTPS traffic per source IP, and Warp runners + share egress IPs across tenants, so unauthenticated clones of public repos + can fail with a 401 ("could not read Username"). The rewrite covers every + fetch that goes through the git CLI: Lake dependency clones, Nix's eval-time + `builtins.fetchGit`, script clones, and cargo git dependencies when + CARGO_NET_GIT_FETCH_WITH_CLI is set. + +runs: + using: composite + steps: + - shell: bash + env: + GH_TOKEN: ${{ github.token }} + run: >- + git config --global + url."https://x-access-token:${GH_TOKEN}@github.com/".insteadOf + "https://github.com/" diff --git a/.github/actions/setup-rust-toolchain/action.yml b/.github/actions/setup-rust-toolchain/action.yml index db4211710..420414345 100644 --- a/.github/actions/setup-rust-toolchain/action.yml +++ b/.github/actions/setup-rust-toolchain/action.yml @@ -27,6 +27,19 @@ runs: exit 1 fi + - uses: ./.github/actions/authenticate-github-fetches + + # Cargo's built-in git fetcher ignores `url.insteadOf`, so it would bypass + # the token rewrite above; fetching with the git CLI routes cargo's git + # dependencies through it. Set before the caching action below, which + # keys on the environment. + - name: Fetch cargo git dependencies with the git CLI + shell: bash + run: | + if [[ ! -v CARGO_NET_GIT_FETCH_WITH_CLI ]]; then + echo "CARGO_NET_GIT_FETCH_WITH_CLI=true" >> "$GITHUB_ENV" + fi + - uses: actions-rust-lang/setup-rust-toolchain@v1 with: rustflags: ${{ inputs.native-codegen == 'true' && '-Ctarget-cpu=native -Dwarnings' || '-Dwarnings' }} diff --git a/.github/workflows/bench-main.yml b/.github/workflows/bench-main.yml index cbedc5d1b..4312e8ec4 100644 --- a/.github/workflows/bench-main.yml +++ b/.github/workflows/bench-main.yml @@ -142,6 +142,8 @@ jobs: # - { env: FC, cache_pkg: formal_conjectures, mathlib: true } steps: - uses: actions/checkout@v7 + # `lake build` below clones this package's Lake dependencies. + - uses: ./.github/actions/authenticate-github-fetches - uses: actions/cache/restore@v6 with: path: ~/.local/bin diff --git a/.github/workflows/bench-pr.yml b/.github/workflows/bench-pr.yml index 8db31799e..bd5cb24b1 100644 --- a/.github/workflows/bench-pr.yml +++ b/.github/workflows/bench-pr.yml @@ -342,6 +342,8 @@ jobs: ref: ${{ needs.build.outputs.revision }} # The job runs PR code; never leave the token in .git. persist-credentials: false + # `lake build` below clones this package's Lake dependencies. + - uses: ./.github/actions/authenticate-github-fetches # Apply the allowlisted KEY=VALUE lines from the !benchmark comment, # so IX_COMPILE_* knobs reach the measured compile. Delivered via an # env var, not inline `${{ }}` — inlining would risk shell injection. diff --git a/.github/workflows/nix.yml b/.github/workflows/nix.yml index f8401b25c..51b38c363 100644 --- a/.github/workflows/nix.yml +++ b/.github/workflows/nix.yml @@ -27,6 +27,11 @@ jobs: with: name: argumentcomputer authToken: ${{ secrets.CACHIX_AUTH_TOKEN }} + # Covers `builtins.fetchGit` of the Lake manifest's `git+https` + # dependencies, which runs at flake eval time as this user; + # `install-nix-action`'s github_access_token covers only `github:` + # flake inputs, which fetch via the API. + - uses: ./.github/actions/authenticate-github-fetches # Ix CLI - run: nix build --print-build-logs --accept-flake-config - run: nix run .#ix -- --help @@ -47,6 +52,7 @@ jobs: with: name: argumentcomputer authToken: ${{ secrets.CACHIX_AUTH_TOKEN }} + - uses: ./.github/actions/authenticate-github-fetches # Builds and runs tests using Lake as a Nix package - run: nix develop --accept-flake-config --command bash -c "lake build && lake test" # Realize the zkVM shells so they're verified and pushed to the cache,