mastra-ai/mastra · error · ProviderAuthRequiredError

Failed to refresh the GitHub Copilot token.

Error message

Failed to refresh the GitHub Copilot token.

What it means

After confirming an OAuth credential exists, the Copilot wrapper calls storage.getApiKey(), which transparently refreshes an expired Copilot bearer token. If the refresh fails and no access token can be produced, ProviderAuthRequiredError('Failed to refresh the GitHub Copilot token.') is thrown. Unlike error 768, the user did log in, but their token could not be renewed.

Source

Thrown at mastracode/sdk/src/providers/github-copilot.ts:133

 * - Adds the VS Code-like Copilot headers required by the API.
 * - Rewrites the request URL onto the per-token API base when `rewriteUrl` is true.
 */
export function buildGitHubCopilotOAuthFetch(
  opts: { authStorage?: CredentialStore; rewriteUrl?: boolean } = {},
): typeof fetch {
  return (async (url: string | URL | Request, init?: Parameters<typeof fetch>[1]) => {
    const storage = opts.authStorage ?? getAuthStorage();
    storage.reload();

    const cred = storage.get(COPILOT_PROVIDER_ID);
    if (!cred || cred.type !== 'oauth') {
      throw new ProviderAuthRequiredError('Not logged in to GitHub Copilot.');
    }

    // getApiKey() refreshes the Copilot bearer if it has expired.
    const accessToken = await storage.getApiKey(COPILOT_PROVIDER_ID);
    if (!accessToken) {
      throw new ProviderAuthRequiredError('Failed to refresh the GitHub Copilot token.');
    }
    storage.reload();

    const enterpriseUrl = (cred as GitHubCopilotCredentials).enterpriseUrl;

    let parsedBody: unknown;
    if (typeof init?.body === 'string') {
      try {
        parsedBody = JSON.parse(init.body);
      } catch {
        parsedBody = undefined;
      }
    }
    const isAgent = detectIsAgent(parsedBody);
    const isVision = detectIsVision(parsedBody);

    // Preserve non-auth headers from caller.
    const headers = new Headers();

View on GitHub (pinned to 75dd419e61)

Solutions

  1. Re-run the GitHub Copilot login/device flow to obtain fresh tokens
  2. Check network reachability to GitHub's token endpoints and retry
  3. Inspect auth storage for a corrupt/expired refresh token and delete it so a clean login is forced
  4. Verify the GitHub account still has Copilot access and no revoked sessions (github.com/settings/security)

Example fix

// before
const provider = copilot(); // throws on expired, unrefreshable token
// after
try {
  return copilot();
} catch (e) {
  if (e instanceof ProviderAuthRequiredError) {
    storage.remove?.('github-copilot');
    await copilotDeviceFlowLogin(); // fresh tokens
    return copilot();
  }
  throw e;
}
Defensive patterns

Strategy: try-catch

Validate before calling

// Refreshability is only observable by calling getApiKey; pre-check the stored credential age
const cred = storage.get('github-copilot');
if (cred?.type === 'oauth' && 'expiresAt' in cred && Date.now() > (cred as { expiresAt: number }).expiresAt) {
  console.warn('Copilot token expired; a refresh will be attempted on next use.');
}

Type guard

function isFreshToken(c: { type: string; expiresAt?: number } | null): boolean {
  return !!c && c.type === 'oauth' && (c.expiresAt == null || c.expiresAt > Date.now());
}

Try / catch

try {
  await runWithCopilot();
} catch (err) {
  if (err instanceof ProviderAuthRequiredError && err.message.includes('refresh')) {
    await copilotDeviceFlowLogin(); // re-authenticate to get fresh tokens, then retry
  } else throw err;
}

Prevention

When it happens

Trigger: Using `copilot` or `fetchWithOAuth` when the stored Copilot bearer token has expired and `storage.getApiKey(COPILOT_PROVIDER_ID)` cannot obtain a new one (refresh endpoint fails, refresh token revoked, GitHub session invalidated).

Common situations: Long-lived CI cache holding an expired token; GitHub password change or session revocation invalidating refresh tokens; network failure or GitHub outage during the refresh exchange; GitHub Copilot access removed from the account, making refresh return 4xx.

Related errors


AI-assisted analysis of mastra-ai/mastra@75dd419e61 (2026-08-30). Data as JSON: /api/errors/1b51c977a567796f. Report an issue: GitHub.