diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index fe4940c570d..3114305a37f 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -1319,8 +1319,9 @@ jobs: NODE_EXTRA_CA_CERTS: /tmp/gh-aw/proxy-logs/proxy-tls/ca.crt run: | echo "Testing gh CLI through DIFC proxy (GH_HOST=${GH_HOST})..." - repo_name=$(gh api /repos/${{ github.repository }} --jq '.full_name') - echo "✅ gh CLI works through DIFC proxy (repo: $repo_name)" + # Use /rate_limit which is exempt from rate limits and proves proxy routing works + rate_limit=$(gh api /rate_limit --jq '.rate.limit') + echo "✅ gh CLI works through DIFC proxy (rate limit: ${rate_limit})" - name: Test actions/github-script with proxy env uses: actions/github-script@3a2844b7e9c422d3c10d287c895573f7108da1b3 # v9 diff --git a/actions/setup/js/frontmatter_hash_github_api.test.cjs b/actions/setup/js/frontmatter_hash_github_api.test.cjs index b74c8118a36..990b0fdd79f 100644 --- a/actions/setup/js/frontmatter_hash_github_api.test.cjs +++ b/actions/setup/js/frontmatter_hash_github_api.test.cjs @@ -3,26 +3,26 @@ import { describe, it, expect, beforeAll, vi } from "vitest"; const path = require("path"); const fs = require("fs"); const { computeFrontmatterHash, createGitHubFileReader } = require("./frontmatter_hash_pure.cjs"); -const { withRetry, isTransientError } = require("./error_recovery.cjs"); - -// Retry configuration for live API tests -const LIVE_API_RETRY_CONFIG = { - maxRetries: 3, - initialDelayMs: 1000, - shouldRetry: isTransientError, -}; +const { withRetry, RATE_LIMIT_RETRY_CONFIG } = require("./error_recovery.cjs"); /** - * Wraps a file reader function with retry logic for transient GitHub API errors + * Wraps a file reader function with retry logic for transient GitHub API errors. + * Uses RATE_LIMIT_RETRY_CONFIG (5 retries, ~30 s initial delay) so that installation-level + * rate limit bursts during busy CI windows don't cause spurious test failures. * @param {Function} fileReader - The original file reader function * @returns {Function} File reader with retry logic */ function createRetryableFileReader(fileReader) { return async function (filePath) { - return withRetry(async () => fileReader(filePath), LIVE_API_RETRY_CONFIG, `fetch file ${filePath}`); + return withRetry(async () => fileReader(filePath), RATE_LIMIT_RETRY_CONFIG, `fetch file ${filePath}`); }; } +// Maximum time to allow the live API test to run. Must accommodate RATE_LIMIT_RETRY_CONFIG's +// worst-case retry sequence (~30 s + ~60 s + ~120 s + ~240 s + ~240 s = ~11.5 min) plus +// network and processing overhead. The CI job itself times out at 20 minutes. +const LIVE_API_TEST_TIMEOUT_MS = 18 * 60 * 1000; // 18 minutes + /** * Tests for frontmatter hash computation using GitHub's API to fetch real workflows. * This validates that the JavaScript hash algorithm correctly computes hashes @@ -371,7 +371,7 @@ describe("frontmatter_hash with GitHub API", () => { }); describe("live GitHub API integration", () => { - it("should compute hash using real GitHub API (no mocks)", { timeout: 30000 }, async () => { + it("should compute hash using real GitHub API (no mocks)", { timeout: LIVE_API_TEST_TIMEOUT_MS }, async () => { // Skip this test if no GitHub token is available // Check multiple possible token environment variables const token = process.env.GITHUB_TOKEN || process.env.GH_TOKEN;