From 40c541f2b2ddcf55593cc865a7858cc6b791be76 Mon Sep 17 00:00:00 2001 From: Claude Date: Mon, 9 Nov 2026 09:43:13 +0000 Subject: [PATCH 1/2] Retry setup-ruby once after a release 504 ruby/setup-ruby fetches the prebuilt Ruby from a github.com release and gives up after about a minute of its own retries. On 2026-11-09 a ~4 minute release-CDN 504 outage failed the nightly CI run on main (run 42568829044) in hosted-e2e and two gem e2e legs at that step. Mirror the existing setup-python pattern: cap attempt 1 at 4 minutes with continue-on-error, pause 60 s, then run attempt 2, which fails the job if the download is still broken. Applied to the shared e2e-steps anchor (e2e, e2e-extended, e2e-windows, e2e-macos, e2e-full) and hosted-e2e. Job names and the ci-ok gate are unchanged. Co-Authored-By: Claude Opus 5.5 (1M context) Claude-Session: https://claude.ai/code/session_011f9aeRYC9ragXuhk4udbwz --- .github/workflows/ci.yml | 43 ++++++++++++++++++++++++++++++++++++++-- 1 file changed, 41 insertions(+), 2 deletions(-) diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index caa975203..cd940e481 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -1609,9 +1609,17 @@ jobs: if: matrix.pipenv != '' || matrix.pip != '' run: uv python install 3.8 3.11 3.12 - - name: Setup Ruby + - name: Setup Ruby (attempt 1) + # setup-ruby downloads the prebuilt Ruby from a github.com release + # and gives up after ~1 min of retries. On 2026-11-09 (nightly run + # 42568829044) a ~4 min release-CDN 504 outage failed two gem legs + # and hosted-e2e here. Pause and try once more; a second failure + # is not a blip. + id: setup-ruby if: matrix.suite == 'e2e_gem' || matrix.bundler != '' uses: ruby/setup-ruby@319994f95fa847cf3fb3cd3dbe89f6dcde9f178f # v1.295.0 + timeout-minutes: 4 + continue-on-error: true with: # setup-ruby does NOT support `3.2.x` wildcard pinning the # way setup-python does — it errors with "Unknown version @@ -1628,6 +1636,20 @@ jobs: bundler: 'none' bundler-cache: false + - name: Setup Ruby (pause before attempt 2) + if: (matrix.suite == 'e2e_gem' || matrix.bundler != '') && steps.setup-ruby.outcome != 'success' + shell: bash + run: sleep 60 + + - name: Setup Ruby (attempt 2) + if: (matrix.suite == 'e2e_gem' || matrix.bundler != '') && steps.setup-ruby.outcome != 'success' + uses: ruby/setup-ruby@319994f95fa847cf3fb3cd3dbe89f6dcde9f178f # v1.295.0 + timeout-minutes: 4 + with: + ruby-version: ${{ matrix.ruby || '3.2.10' }} + bundler: 'none' + bundler-cache: false + # The legs pin their bundler (`bundler:`) so a capstone never rides # whatever bundler the runner's Ruby ships; e2e_gem keeps the 2.5 # floor. A two-part version gets the `~> X.Y.0` requirement setup-ruby's @@ -2874,9 +2896,13 @@ jobs: if: steps.gate.outputs.run == 'true' run: scripts/pip-install-retry.sh uv && uv --version - - name: Setup Ruby + - name: Setup Ruby (attempt 1) + # Capped, paused and retried once, as in the e2e job. + id: setup-ruby if: steps.gate.outputs.run == 'true' uses: ruby/setup-ruby@319994f95fa847cf3fb3cd3dbe89f6dcde9f178f # v1.295.0 + timeout-minutes: 4 + continue-on-error: true with: ruby-version: '3.2.10' # Bundler comes from the next step, which retries rubygems.org @@ -2884,6 +2910,19 @@ jobs: bundler: 'none' bundler-cache: false + - name: Setup Ruby (pause before attempt 2) + if: (steps.gate.outputs.run == 'true') && steps.setup-ruby.outcome != 'success' + run: sleep 60 + + - name: Setup Ruby (attempt 2) + if: (steps.gate.outputs.run == 'true') && steps.setup-ruby.outcome != 'success' + uses: ruby/setup-ruby@319994f95fa847cf3fb3cd3dbe89f6dcde9f178f # v1.295.0 + timeout-minutes: 4 + with: + ruby-version: '3.2.10' + bundler: 'none' + bundler-cache: false + - name: Install Bundler if: steps.gate.outputs.run == 'true' # The gem hosted rewrite pins into the Gemfile.lock CHECKSUMS From fe2db1c3921a93e25002543c8d2a9a2b2b714ac7 Mon Sep 17 00:00:00 2001 From: Claude Date: Mon, 9 Nov 2026 10:39:39 +0000 Subject: [PATCH 2/2] Drop the pause between setup-ruby attempts test_merge_queue_fail_fast.py requires a continue-on-error attempt 1 to be retried by the very next step, so the sleep step in between failed lint-ecosystems. Attempt 2 now follows attempt 1 directly and gets setup-ruby's own ~1 min of backoff retries again. Co-Authored-By: Claude Opus 5.5 (1M context) Claude-Session: https://claude.ai/code/session_011f9aeRYC9ragXuhk4udbwz --- .github/workflows/ci.yml | 16 ++++------------ 1 file changed, 4 insertions(+), 12 deletions(-) diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index cd940e481..5734b65ea 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -1613,8 +1613,9 @@ jobs: # setup-ruby downloads the prebuilt Ruby from a github.com release # and gives up after ~1 min of retries. On 2026-11-09 (nightly run # 42568829044) a ~4 min release-CDN 504 outage failed two gem legs - # and hosted-e2e here. Pause and try once more; a second failure - # is not a blip. + # and hosted-e2e here. Try once more, with setup-ruby's own ~1 min + # of retries again; a second failure is not a blip. (Attempt 2 + # must be the very next step: test_merge_queue_fail_fast.py.) id: setup-ruby if: matrix.suite == 'e2e_gem' || matrix.bundler != '' uses: ruby/setup-ruby@319994f95fa847cf3fb3cd3dbe89f6dcde9f178f # v1.295.0 @@ -1636,11 +1637,6 @@ jobs: bundler: 'none' bundler-cache: false - - name: Setup Ruby (pause before attempt 2) - if: (matrix.suite == 'e2e_gem' || matrix.bundler != '') && steps.setup-ruby.outcome != 'success' - shell: bash - run: sleep 60 - - name: Setup Ruby (attempt 2) if: (matrix.suite == 'e2e_gem' || matrix.bundler != '') && steps.setup-ruby.outcome != 'success' uses: ruby/setup-ruby@319994f95fa847cf3fb3cd3dbe89f6dcde9f178f # v1.295.0 @@ -2897,7 +2893,7 @@ jobs: run: scripts/pip-install-retry.sh uv && uv --version - name: Setup Ruby (attempt 1) - # Capped, paused and retried once, as in the e2e job. + # Capped and retried once, as in the e2e job. id: setup-ruby if: steps.gate.outputs.run == 'true' uses: ruby/setup-ruby@319994f95fa847cf3fb3cd3dbe89f6dcde9f178f # v1.295.0 @@ -2910,10 +2906,6 @@ jobs: bundler: 'none' bundler-cache: false - - name: Setup Ruby (pause before attempt 2) - if: (steps.gate.outputs.run == 'true') && steps.setup-ruby.outcome != 'success' - run: sleep 60 - - name: Setup Ruby (attempt 2) if: (steps.gate.outputs.run == 'true') && steps.setup-ruby.outcome != 'success' uses: ruby/setup-ruby@319994f95fa847cf3fb3cd3dbe89f6dcde9f178f # v1.295.0