decolua/9router · error · Error

${callbackParams.error_description || callbackParams.error}

Error message

${callbackParams.error_description || callbackParams.error}

What it means

During the Codex (OpenAI) OAuth flow in CodexService.connect(), the local callback server (port 1455) received a redirect from OpenAI's authorization endpoint carrying error/error_description query parameters instead of an authorization code. This means the authorization server itself rejected the user's consent/login attempt, and the library re-throws the provider's message verbatim. It is thrown before any code exchange happens.

Source

Thrown at src/lib/oauth/services/codex.js:120

      await new Promise((resolve, reject) => {
        const timeout = setTimeout(() => {
          reject(new Error("Authentication timeout (5 minutes)"));
        }, 300000);

        const checkInterval = setInterval(() => {
          if (callbackParams) {
            clearInterval(checkInterval);
            clearTimeout(timeout);
            resolve();
          }
        }, 100);
      });

      close();

      if (callbackParams.error) {
        throw new Error(callbackParams.error_description || callbackParams.error);
      }

      if (!callbackParams.code) {
        throw new Error("No authorization code received");
      }

      spinner.start("Exchanging code for tokens...");

      // Exchange code for tokens (Codex uses form-urlencoded)
      const tokens = await this.exchangeCode(callbackParams.code, redirectUri, codeVerifier, "application/x-www-form-urlencoded");

      spinner.text = "Saving tokens to server...";

      // Save tokens to server
      await this.saveTokens(tokens);

      spinner.succeed("Codex connected successfully!");
      return true;

View on GitHub (pinned to 90b52e06ff)

Solutions

  1. Read the thrown message — it is the raw OAuth error_description (e.g. 'access_denied', 'unauthorized_client') and states exactly why the provider refused.
  2. Re-run connect() and complete (do not cancel) the OpenAI consent screen in the browser that opens.
  3. Verify CODEX_CONFIG (clientId, authorizeUrl, scope, extraParams) in src/lib/oauth/constants/oauth.js still matches OpenAI's current OAuth client registration.
  4. Confirm the redirect_uri (http://localhost:1455/auth/callback) is what OpenAI expects and that nothing else is bound to port 1455.

Example fix

// before: flow throws raw provider error
if (callbackParams.error) {
  throw new Error(callbackParams.error_description || callbackParams.error);
}
// after: give actionable context
if (callbackParams.error) {
  throw new Error(
    `OpenAI authorization failed (${callbackParams.error}): ${callbackParams.error_description || "no description"}. Re-run connect() and approve the consent screen.`
  );
}
Defensive patterns

Strategy: validation

Validate before calling

// after receiving callback params, before proceeding:
if (callbackParams.error) {
  console.error("Provider refused authorization:", callbackParams.error, callbackParams.error_description);
  process.exitCode = 1;
} else if (!callbackParams.code) {
  console.error("Callback missing authorization code");
}

Type guard

function hasOAuthCode(params) {
  return !!params && typeof params === "object" && typeof params.code === "string" && params.code.length > 0 && !params.error;
}

Try / catch

try {
  await codexService.connect();
} catch (err) {
  if (/access_denied|unauthorized_client|invalid_request/.test(err.message)) {
    console.error("Authorization was rejected by OpenAI. Re-run connect() and approve the consent screen.", err.message);
  } else throw err;
}

Prevention

When it happens

Trigger: Calling connect() (src/lib/oauth/services/codex.js:120) when the browser redirect back to http://localhost:1455/auth/callback contains error params — e.g. user clicked 'Cancel'/'Deny' on the OpenAI consent screen (access_denied), the client_id in CODEX_CONFIG is no longer valid, the redirect_uri doesn't match a registered one, or the state/PKCE parameters were rejected.

Common situations: Users deny the consent dialog or close it in a way that redirects back with an error; the bundled OpenAI client ID/authorize URL changed upstream; a proxy or hosts override breaks the localhost redirect; running the flow on a machine where the fixed port 1455 is used by another tool and the callback lands on the wrong server.

Related errors


AI-assisted analysis of decolua/9router@90b52e06ff (2026-08-30). Data as JSON: /api/errors/30876d9e7763259c. Report an issue: GitHub.