OpenAI AuthenticationError: invalid API key — 6 causes in diagnostic order

If the OpenAI API just returned HTTP 401 with AuthenticationError: Incorrect API key provided, you're not hitting a rate limit and you're not being blocked — the server simply doesn't recognize your key. This page walks through the six most common causes in the order you should check them, plus a one-liner to verify the key is valid before touching any code.

The 30-second answer

What the error looks like

The raw HTTP response is always:

HTTP/1.1 401 Unauthorized
{
  "error": {
    "message": "Incorrect API key provided: sk-proj-...Abcd. You can find your API key at https://platform.openai.com/account/api-keys.",
    "type": "invalid_request_error",
    "param": null,
    "code": "invalid_api_key"
  }
}

In the Python SDK this surfaces as an openai.AuthenticationError exception. In the Node.js SDK it's an AuthenticationError from openai/error. The code field is always invalid_api_key — distinct from account_deactivated and other auth-adjacent codes.

Cause 1: Wrong key was copied

OpenAI's dashboard shows the full key exactly once, at creation time. After that it's masked. If you didn't save the key immediately, you cannot retrieve it — you need to create a new one. Check platform.openai.com/api-keys and look at the key prefixes listed there. If the prefix on the error message doesn't match any active key, the key you're using is simply gone.

Fix: generate a new API key, save it to your secrets manager or .env file immediately, and update all references.

Cause 2: The key was revoked or deleted

Keys get deleted in several non-obvious ways: an org admin rotates credentials, someone runs a security sweep, or the key was automatically revoked because it was committed to a public GitHub repo (OpenAI scans for leaked keys and auto-revokes them). A revoked key returns the exact same 401 as a wrong key.

Fix: check the keys list on the dashboard. If the key is absent or shown as "Revoked," create a new one. If you committed a key to git history, assume it's compromised regardless of revocation — create a new key and do a git filter-repo purge of the old one.

Cause 3: Project key used on an org-level endpoint

OpenAI introduced project-scoped API keys in 2024. They're prefixed sk-proj- instead of the old sk-. Project keys are bound to a specific project and may not have access to org-level resources. Some endpoints — particularly older ones and admin endpoints — expect an organization-level key or will return 401 for a project key that lacks the right scope.

Fix: if you need broad access, create a key outside of a project context (a "default project" key or a service account key). If you're using a project key intentionally, confirm the endpoint and model you're calling are within that project's scope.

Cause 4: Key not set in the environment correctly

This is by far the most common cause for people who swear the key is correct. The code is reading a different env var than you set, or the var is set in a shell session that's not the one running your process.

Check what your code actually sees:

# Python
python -c "import os; print(repr(os.environ.get('OPENAI_API_KEY')))"

# Node
node -e "console.log(JSON.stringify(process.env.OPENAI_API_KEY))"

If this prints None or undefined, the variable is not in scope for that process. Common causes: using export in one terminal tab but running the app in another; a Docker container not receiving the host env var; a CI runner that doesn't have the secret injected; a .env file that's not being loaded (check that python-dotenv / dotenv is actually called before the OpenAI client initializes).

Fix: confirm with the repr()/JSON.stringify trick above, then trace back to where the variable isn't propagating.

Cause 5: Whitespace or quotes in the key string

A trailing newline, a leading space, or wrapping quotes all produce a 401. This is a common result of:

The repr() trick from Cause 4 will reveal this — you'll see 'sk-proj-abc...\n' or '"sk-proj-abc..."' instead of the clean key.

Fix: strip the key at read time: key = os.environ["OPENAI_API_KEY"].strip() and ensure your .env parser handles trailing whitespace.

Cause 6: Wrong organization specified

If your account belongs to multiple OpenAI organizations, you can pass an OpenAI-Organization header (or set organization= on the client) to select which org's billing and limits apply. If you pass an org ID that doesn't match the key's org, you'll get a 401 or 403.

Fix: remove the organization parameter entirely and let OpenAI use the key's default org, or confirm the org ID matches at platform.openai.com/account/organization.

How to verify a key with curl

Before touching application code, confirm the key itself is valid with a single API call:

curl https://api.openai.com/v1/models \
  -H "Authorization: Bearer $OPENAI_API_KEY"

A valid key returns HTTP 200 and a JSON list of models. A 401 here means the key is definitively invalid — causes 1–3 apply. A 200 here but 401 in your app almost always means causes 4–6: the key your app is reading is not the same key you tested.

To test a specific key string rather than the env var:

curl https://api.openai.com/v1/models \
  -H "Authorization: Bearer sk-proj-YOUR_KEY_HERE"

OpenAI error codes reference

HTTP statusError codeMeaning
401invalid_api_keyKey not recognized — wrong, revoked, or malformed
401account_deactivatedThe account associated with this key has been deactivated
403model_not_foundKey valid, but key lacks access to that model or org
429insufficient_quotaKey valid, but billing quota exhausted

The code field in the JSON error body is what tells you which 401 variant you're dealing with. Log it explicitly — don't just log the HTTP status.

FAQ

Can I reactivate a revoked key? No — once a key is revoked or deleted, it cannot be restored. You must generate a new one.

Is there a way to test a key without making a billed request? Yes — GET /v1/models lists available models and is not a generative call, so it does not consume tokens or incur per-request charges beyond normal API overhead.

My key works in curl but fails in my Python code. What's wrong? Your code is almost certainly reading the key from a different source than your shell env. Add print(repr(openai.api_key)) right before the failing call to see exactly what the client is using.


Related

Last updated June 2, 2026. Error codes verified against OpenAI's API reference documentation. OpenAI may change error formats over time — confirm specifics in the current docs before relying on them in production.