{"record":{"id":"dd10bbfc5912d71b","repo":"mastra-ai/mastra","slug":"failed-to-refresh-the-xai-token","errorCode":null,"errorMessage":"Failed to refresh the xAI token.","messagePattern":"Failed to refresh the xAI token\\.","errorType":"exception","errorClass":"ProviderAuthRequiredError","httpStatus":null,"severity":"error","filePath":"mastracode/sdk/src/providers/xai.ts","lineNumber":54,"sourceCode":"/**\n * Build a fetch wrapper that authenticates with xAI OAuth.\n * Injects the access token (auto-refreshed by AuthStorage) as a bearer token,\n * preserving non-auth headers from the caller.\n */\nexport function buildXAIOAuthFetch(opts: { authStorage?: CredentialStore } = {}): typeof fetch {\n  return (async (url: string | URL | Request, init?: Parameters<typeof fetch>[1]) => {\n    const storage = opts.authStorage ?? getAuthStorage();\n    storage.reload();\n\n    const cred = storage.get(XAI_PROVIDER_ID);\n    if (!cred || cred.type !== 'oauth') {\n      throw new ProviderAuthRequiredError('Not logged in to xAI.');\n    }\n\n    // getApiKey() refreshes the access token if it has expired.\n    const accessToken = await storage.getApiKey(XAI_PROVIDER_ID);\n    if (!accessToken) {\n      throw new ProviderAuthRequiredError('Failed to refresh the xAI token.');\n    }\n\n    // Preserve existing headers, strip auth-related ones. Explicit init\n    // headers override headers carried by an incoming Request.\n    const headers = new Headers(url instanceof Request ? url.headers : undefined);\n    if (init?.headers) {\n      new Headers(init.headers).forEach((value, key) => headers.set(key, value));\n    }\n    headers.delete('authorization');\n    headers.delete('x-api-key');\n\n    headers.set('Authorization', `Bearer ${accessToken}`);\n\n    try {\n      return await fetch(url, { ...init, headers });\n    } catch (error) {\n      if (error && typeof error === 'object') {\n        Object.assign(error as Record<string, unknown>, {","sourceCodeStart":36,"sourceCodeEnd":72,"githubUrl":"https://github.com/mastra-ai/mastra/blob/75dd419e613fe9c39f846ffc500716141b74fda6/mastracode/sdk/src/providers/xai.ts#L36-L72","documentation":"After validating the 'xai' oauth credential, buildXAIOAuthFetch calls storage.getApiKey('xai') to obtain the access token, refreshing it if expired. If that returns nothing, it throws ProviderAuthRequiredError('Failed to refresh the xAI token.') because the request cannot be authorized.","triggerScenarios":"A request through the xAI OAuth fetch when the stored credential is a valid oauth entry but storage.getApiKey('xai') returns null/undefined — the token refresh failed or no token material is stored.","commonSituations":"Expired/revoked refresh token; network or proxy failure during the refresh call; credentials file missing the refresh token; clock skew making tokens seem expired; xAI revoking sessions after re-login on another device.","solutions":["Re-run the xAI OAuth login to obtain fresh tokens.","Check network connectivity to the xAI/OAuth token endpoint.","Confirm the stored credential includes refresh token material.","Catch ProviderAuthRequiredError and trigger re-login then retry."],"exampleFix":"// before\nconst res = await fetchWithOAuth(url, init); // refresh fails, throws\n// after\ntry {\n  return await fetchWithOAuth(url, init);\n} catch (e) {\n  if (e instanceof ProviderAuthRequiredError) await xaiLogin(); // re-auth then retry\n  throw e;\n}","handlingStrategy":"retry","validationCode":"const token = await storage.getApiKey('xai');\nif (!token) console.warn('xAI token unavailable; re-login required before requests');","typeGuard":"null","tryCatchPattern":"try {\n  return await fetchWithOAuth(url, init);\n} catch (e) {\n  if (e instanceof ProviderAuthRequiredError && /refresh/.test(e.message)) {\n    await xaiLogin(); // refresh token dead; re-auth then retry\n    return await fetchWithOAuth(url, init);\n  }\n  throw e;\n}","preventionTips":["Refresh tokens proactively during long sessions.","Ensure stable network access to the xAI token endpoint.","Re-authenticate fully when refresh fails; don't loop retries."],"tags":["auth","oauth","xai","token-refresh"],"backgroundTag":"oauth-token-refresh-failed","analyzedSha":"75dd419e613fe9c39f846ffc500716141b74fda6","analyzedAt":"2026-08-30T00:15:31.844Z","schemaVersion":2},"datasetVersion":"2026-08-30T03:17:51.788Z"}