{"record":{"id":"7688f677656a8fdd","repo":"mastra-ai/mastra","slug":"result-error-dynamic-message-from-device-login-po","errorCode":null,"errorMessage":"result.error (dynamic message from device-login poll failure)","messagePattern":"result\\.error \\(dynamic message from device-login poll failure\\)","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"error","filePath":"mastracode/sdk/src/auth/providers/openai-codex.ts","lineNumber":556,"sourceCode":"\n  options.onAuth({\n    url: pending.url,\n    instructions: pending.instructions,\n  });\n\n  await sleep(pending.intervalMs);\n\n  while (true) {\n    if (options.signal?.aborted) {\n      throw new Error('Login cancelled');\n    }\n\n    const result = await pollCodexDeviceLogin(pending, { signal: options.signal });\n    if (result.status === 'complete') {\n      return result.credentials;\n    }\n    if (result.status === 'failed') {\n      throw new Error(result.error);\n    }\n\n    options.onProgress?.('Waiting for OpenAI Codex device authorization...');\n    await sleep(result.nextPollMs);\n  }\n}\n\n/**\n * Login with OpenAI Codex OAuth\n *\n * @param options.onAuth - Called with URL and instructions when auth starts\n * @param options.onPrompt - Called to prompt user for manual code paste (fallback if no onManualCodeInput)\n * @param options.onProgress - Optional progress messages\n * @param options.onManualCodeInput - Optional promise that resolves with user-pasted code.\n *                                    Races with browser callback - whichever completes first wins.\n *                                    Useful for showing paste input immediately alongside browser flow.\n * @param options.originator - OAuth originator parameter (defaults to \"mastracode\")\n */","sourceCodeStart":538,"sourceCodeEnd":574,"githubUrl":"https://github.com/mastra-ai/mastra/blob/75dd419e613fe9c39f846ffc500716141b74fda6/mastracode/sdk/src/auth/providers/openai-codex.ts#L538-L574","documentation":"The device-login polling loop received a 'failed' result from pollCodexDeviceLogin and the library re-throws the dynamic error message contained in result.error. The message text varies with the underlying poll failure (e.g. token denial, expiry, or an HTTP error from the poll endpoint). It means OpenAI reported the device authorization as definitively failed rather than still pending.","triggerScenarios":"pollCodexDeviceLogin returns { status: 'failed', error } — typically because the user denied the request, the device code expired before approval, or the poll endpoint returned an unrecoverable error — and loginOpenAICodexDevice throws result.error verbatim.","commonSituations":"User clicked 'deny' or closed the browser page; user took too long and the device code expired; network hiccup converted to a hard failure by the endpoint; multiple competing login attempts invalidating each other.","solutions":["Restart the login flow to get a fresh device code if the previous one expired or was denied.","Complete the authorization promptly — approve in the browser before the code expires.","Inspect result.error's text to distinguish 'denied' vs 'expired' vs HTTP failure and message the user accordingly.","If the error indicates an endpoint/HTTP problem, check network access and OpenAI service status before retrying."],"exampleFix":"// before\ntry { await loginOpenAICodexDevice({}); } catch (e) { console.error(e); }\n\n// after: restart on denial/expiry\ntry {\n  await loginOpenAICodexDevice({});\n} catch (e) {\n  if (/denied|expired|slow_down/i.test(e.message)) {\n    console.log('Restarting device login...');\n    await loginOpenAICodexDevice({});\n  } else throw e;\n}","handlingStrategy":"try-catch","validationCode":null,"typeGuard":null,"tryCatchPattern":"try {\n  await loginOpenAICodexDevice({});\n} catch (e) {\n  if (/expired|denied/i.test(e.message)) {\n    // fresh code + prompt user to approve quickly\n    await loginOpenAICodexDevice({});\n  } else {\n    throw e;\n  }\n}","preventionTips":["Approve the device code promptly before it expires.","Avoid running multiple device logins concurrently.","Parse the error text to differentiate denial vs expiry vs HTTP failure.","Automatically restart the flow once on expiry-style errors."],"tags":["oauth","device-login","polling","auth-denied"],"backgroundTag":"oauth-device-flow-failed","analyzedSha":"75dd419e613fe9c39f846ffc500716141b74fda6","analyzedAt":"2026-08-30T00:15:31.844Z","schemaVersion":2},"datasetVersion":"2026-08-30T08:17:16.595Z"}