diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index 60cef3186..d9e8812f1 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -1847,6 +1847,25 @@ jobs: if [ "$RUNNER_OS" = Windows ]; then launcher="${launcher}.cmd"; fi echo "SOCKET_PATCH_MAVEN_E2E_MVN=$launcher" >> "$GITHUB_ENV" + - name: Restore the Gradle ${{ matrix.gradle }} distribution + # Both of install-gradle.sh's origins are served by github.com + # releases (services.gradle.org redirects there). On 2026-11-09 + # those returned 504 for minutes at a time, longer than curl's + # ~30 s of retries, and failed 9 gradle legs of the nightly (run + # 42568829044); the 9.8.0 legs run in the merge queue too. The zip + # is pinned by sha256, which the script checks on a restored copy + # as well, so cache it per version. Saved from main only. + id: gradle-dist-cache + if: matrix.gradle != '' + uses: actions/cache/restore@caa296126883cff596d87d8935842f9db880ef25 # v5.1.0 + # A miss only means downloading the zip. + timeout-minutes: 5 + continue-on-error: true + with: + path: ${{ runner.temp }}/gradle-${{ matrix.gradle }}-bin.zip + # The script holds the pins: a changed pin starts a fresh key. + key: gradle-dist-${{ matrix.gradle }}-${{ runner.os }}-${{ hashFiles('scripts/install-gradle.sh') }} + - name: Install Gradle ${{ matrix.gradle }} if: matrix.gradle != '' shell: bash @@ -1855,6 +1874,19 @@ jobs: # Pinned digest, GitHub-release origin: see the script. run: scripts/install-gradle.sh "$GRADLE_VERSION" "$RUNNER_TEMP" >> "$GITHUB_ENV" + - name: Save the Gradle ${{ matrix.gradle }} distribution + if: >- + matrix.gradle != '' + && github.ref == 'refs/heads/main' + && steps.gradle-dist-cache.outputs.cache-hit != 'true' + && steps.gradle-dist-cache.outcome == 'success' + uses: actions/cache/save@caa296126883cff596d87d8935842f9db880ef25 # v5.1.0 + # Several legs share a version: the first save of a key wins and + # the others only log a warning, as the action does for any taken key. + with: + path: ${{ runner.temp }}/gradle-${{ matrix.gradle }}-bin.zip + key: ${{ steps.gradle-dist-cache.outputs.cache-primary-key }} + - name: Setup .NET SDK if: matrix.dotnet != '' # Installs next to the runner's preinstalled SDKs; the suite writes diff --git a/.github/workflows/gradle-compatibility.yml b/.github/workflows/gradle-compatibility.yml index a3a555035..98a85e546 100644 --- a/.github/workflows/gradle-compatibility.yml +++ b/.github/workflows/gradle-compatibility.yml @@ -345,6 +345,19 @@ jobs: echo "SOCKET_PATCH_MAVEN_E2E_REQUIRED=1" } >> "$GITHUB_ENV" + - name: Restore the Gradle ${{ matrix.gradle }} distribution + # ci.yml's e2e legs save this pinned zip from main (every version + # on Linux, 8.14.3 on Windows); restoring it keeps a github.com + # release outage from failing these legs. See the matching step + # there. Restore only: saving every OS x version here would add + # ~1 GB of near-duplicate zips to the repo's cache. + uses: actions/cache/restore@caa296126883cff596d87d8935842f9db880ef25 # v5.1.0 + timeout-minutes: 5 + continue-on-error: true + with: + path: ${{ runner.temp }}/gradle-${{ matrix.gradle }}-bin.zip + key: gradle-dist-${{ matrix.gradle }}-${{ runner.os }}-${{ hashFiles('scripts/install-gradle.sh') }} + - name: Install Gradle ${{ matrix.gradle }} shell: bash env: diff --git a/scripts/install-gradle.sh b/scripts/install-gradle.sh index d0285d180..0dfc44bed 100755 --- a/scripts/install-gradle.sh +++ b/scripts/install-gradle.sh @@ -9,14 +9,16 @@ # alone answering HTTP 500 for ~30 s used to fail a merge-queue leg. It is # only tried after the release download fails. The sha256 is pinned below # (from https://gradle.org/release-checksums/), so no checksum fetch can fail -# either; a version without a pin fails closed. +# either; a version without a pin fails closed. A zip already at +# /gradle--bin.zip (CI restores one from the actions cache) +# is used without any download when it matches that pin. # # Prints (stdout): # SOCKET_PATCH_GRADLE_E2E_GRADLE= set -euo pipefail if [ $# -ne 2 ]; then - sed -n '2,15p' "$0" | sed 's/^# \{0,1\}//' >&2 + sed -n '2,17p' "$0" | sed 's/^# \{0,1\}//' >&2 exit 2 fi VERSION="$1" @@ -36,26 +38,41 @@ esac mkdir -p "$DIR" zip="$DIR/gradle-$VERSION-bin.zip" file="gradle-$VERSION-bin.zip" + +# python, not sha256sum: the macOS runners have only shasum. +verify() { + python -c 'import hashlib, sys; d = hashlib.sha256(open(sys.argv[1], "rb").read()).hexdigest(); sys.exit(0 if d == sys.argv[2] else "sha256 mismatch: got " + d)' "$zip" "$sha" +} + fetched="" -# --ssl-revoke-best-effort: Windows curl (schannel) otherwise fails when the -# CA's revocation endpoint is unreachable. -for url in \ - "https://github.com/gradle/gradle-distributions/releases/download/v$VERSION/$file" \ - "https://services.gradle.org/distributions/$file"; do - if curl -fsSL --retry 5 --retry-all-errors --ssl-revoke-best-effort "$url" -o "$zip"; then +if [ -f "$zip" ]; then + if verify; then + echo "install-gradle.sh: using the cached $file" >&2 fetched=1 - break + else + rm -f "$zip" fi - echo "install-gradle.sh: download from $url failed" >&2 -done +fi +# --ssl-revoke-best-effort: Windows curl (schannel) otherwise fails when the +# CA's revocation endpoint is unreachable. +if [ -z "$fetched" ]; then + for url in \ + "https://github.com/gradle/gradle-distributions/releases/download/v$VERSION/$file" \ + "https://services.gradle.org/distributions/$file"; do + if curl -fsSL --retry 5 --retry-all-errors --ssl-revoke-best-effort "$url" -o "$zip"; then + fetched=1 + break + fi + echo "install-gradle.sh: download from $url failed" >&2 + done +fi if [ -z "$fetched" ]; then echo "install-gradle.sh: every origin failed for Gradle $VERSION" >&2 exit 1 fi -# python, not sha256sum: the macOS runners have only shasum. -python -c 'import hashlib, sys; d = hashlib.sha256(open(sys.argv[1], "rb").read()).hexdigest(); sys.exit(0 if d == sys.argv[2] else "sha256 mismatch: got " + d)' "$zip" "$sha" -unzip -q "$zip" -d "$DIR" +verify +unzip -oq "$zip" -d "$DIR" launcher="$DIR/gradle-$VERSION/bin/gradle" case "$(uname -s)" in MINGW*|MSYS*|CYGWIN*) launcher="$launcher.bat" ;; esac echo "SOCKET_PATCH_GRADLE_E2E_GRADLE=$launcher"