iOfficeAI/AionUi · error · Error

update.errors.githubApiFailed

update.errors.githubApiFailed

Error message

update.errors.githubApiFailed

What it means

Thrown by fetchGitHubReleases when the GitHub Releases API call to https://api.github.com/repos/{repo}/releases returns a non-OK HTTP status. The status code is interpolated into the message, and the request carries a User-Agent and a 30s AbortController timeout.

Source

Thrown at packages/desktop/src/process/bridge/updateBridge.ts:332

const fetchGitHubReleases = async (repo: string, timeoutMs = 30000): Promise<GitHubReleaseApi[]> => {
  const url = `https://api.github.com/repos/${repo}/releases`;

  // 添加超时控制,防止网络问题导致无限等待 / Add timeout to prevent infinite wait on network issues
  const controller = new AbortController();
  const timeoutId = setTimeout(() => controller.abort(), timeoutMs);

  try {
    const res = await fetch(url, {
      headers: {
        Accept: 'application/vnd.github+json',
        'User-Agent': DEFAULT_USER_AGENT,
      },
      signal: controller.signal,
    });

    if (!res.ok) {
      throw new Error((await getI18n()).t('update.errors.githubApiFailed', { status: res.status }));
    }

    const json = (await res.json()) as unknown;
    if (!Array.isArray(json)) {
      throw new Error((await getI18n()).t('update.errors.githubApiNotArray'));
    }
    return json as GitHubReleaseApi[];
  } catch (err: unknown) {
    if (err instanceof Error && err.name === 'AbortError') {
      throw new Error((await getI18n()).t('update.errors.githubApiTimeout'), { cause: err });
    }
    throw err;
  } finally {
    clearTimeout(timeoutId);
  }
};

const CDN_MANIFEST_TIMEOUT_MS = 15000;

View on GitHub (pinned to 711aa0550e)

Solutions

  1. Read the {status} in the message: 403/429 => rate limited, 404 => wrong repo slug, 401 => auth
  2. Fix the repo string if 404 ('owner/repo' with correct casing/spelling)
  3. For rate limits, wait or add a GITHUB_TOKEN-capable header and cache release results
  4. Check https://www.githubstatus.com for 5xx outages
  5. Verify network/proxy allows api.github.com over HTTPS

Example fix

// before
const releases = await fetchGitHubReleases('aionui/aionui ');

// after
const releases = await fetchGitHubReleases('aionui/aionui'.trim());
Defensive patterns

Strategy: try-catch

Validate before calling

// cheap pre-check that the repo slug is well-formed
const REPO_RE = /^[\w.-]+\/[\w.-]+$/;
if (!REPO_RE.test(repo)) throw new Error('bad repo slug');
await fetchGitHubReleases(repo);

Type guard

const isRepoSlug = (s: string): boolean => /^[\w.-]+\/[\w.-]+$/.test(s.trim());

Try / catch

try {
  const releases = await fetchGitHubReleases(repo);
} catch (err) {
  if (err instanceof Error && err.message.includes('githubApiFailed')) {
    const status = /* extract from message */ Number(err.message.match(/\b(\d{3})\b/)?.[1]);
    if (status === 403 || status === 429) await sleep(60_000); // rate limited, backoff
    else if (status === 404) throw new Error('repo not found');
    else await sleep(5_000);
  } else throw err;
}

Prevention

When it happens

Trigger: Calling fetchGitHubReleases for a repo that doesn't exist (404), hitting the rate limit (403/429), bad credentials (401), or a 5xx from GitHub. The message includes the numeric status so the cause is immediately readable.

Common situations: Unauthenticated GitHub API rate limiting (60 req/hr per IP) in CI or shared offices; typo'd owner/repo string; private repo without a token; GitHub incidents returning 5xx; proxy/firewall intercepting api.github.com.

Related errors


AI-assisted analysis of iOfficeAI/AionUi@711aa0550e (2026-08-28). Data as JSON: /api/errors/81e8802b41875290. Report an issue: GitHub.