OpenRouter 402: "Insufficient credits" and "Free BYOK request cap exceeded for this month"
OpenRouter documents 402 in one line: "Your account or API key has insufficient credits. Add more credits and retry." The reports on GitHub are longer because the account that ran out is often not the one the user can see. On April 30, 2026, opencode users on the Go subscription got "Free BYOK request cap exceeded for this month" on Kimi, MiniMax and MiMo in the middle of their sessions; none of them had an OpenRouter account. On July 1, 2026, every Pieces user got "openrouter rejected (402): Insufficient credits" on every model until the vendor topped up. This entry covers both shapes and the plain one.
Last verified September 18, 2026 against OpenRouter error reference, OpenRouter BYOK docs, OpenRouter limits page (limit_source, /api/v1/key), opencode issue #25148 (👍14, 16 comments), opencode issue #25151, Pieces issue #1086, Traycer issue #1074 · 5 min read
| Provider | OpenRouter (openrouter.ai/api/v1), including tools that use it behind the scenes |
| HTTP status | 402 Payment Required; inside a stream it arrives as an error chunk with finish_reason: "error" after a 200 |
| Messages | Insufficient credits. Add more using https://openrouter.ai/settings/credits · Free BYOK request cap exceeded for this month. Purchase credits at … |
| Models | Any. Every report names whichever model the tool had selected; the model is not the cause |
| When it happens | The OpenRouter account that owns the key has no credits to charge, or the key's own spending limit is used up. With BYOK the charge is OpenRouter's 5% fee, so it happens with a fully funded upstream key |
| Can you wait it out? | Only for limit_source: openrouter_in_flight_budget (wait for Retry-After) or when the account is somebody else's. Your own empty balance or key limit stays at 402 until credits are added |
- Your key, your account: add credits. If the balance is not zero, the per-key limit is; check with the two curl calls.
- Your key with BYOK: OpenRouter charges a 5% fee to your OpenRouter credits even though your own provider key pays for the tokens. Zero credits means zero requests once the free allowance is used.
- Somebody else's key (OpenCode Go, Pieces, a hosted agent): wait for the vendor, or add a provider you control. The opencode block takes a minute.
What the error looks like
{
"error": {
"code": 402,
"message": "Insufficient credits. Add more using https://openrouter.ai/settings/credits",
"metadata": null
}
}Free BYOK request cap exceeded for this month. Purchase credits at https://openrouter.ai/settings/credits{
"id": "gen-...", "object": "chat.completion.chunk", "model": "...", "provider": "...",
"error": { "code": 402, "message": "Insufficient credits. Add more using https://openrouter.ai/settings/credits", "metadata": { "error_type": "..." } },
"choices": [{ "index": 0, "delta": { "content": "" }, "finish_reason": "error" }]
}{
"error": {
"code": 402,
"message": "This request would exceed your available credits given your current in-flight requests. Retry after in-flight requests settle, or add credits.",
"metadata": { "reason": "in_flight_budget_exhausted", "limit_source": "openrouter_in_flight_budget", "remedy_hint": "Retry after your in-flight requests settle (see the Retry-After header)..." }
}
}Three things trip people up in the threads:
- The 200 with an error inside. When the refusal happens after streaming starts, the HTTP status is 200 and the error sits on the choice. A client that only checks the status code shows an empty reply. OpenRouter documents this; most SDKs do not handle it.
- "Insufficient credits" with money in the account. A per-key spending limit (
limiton the key) produces the same message as an empty balance. So does a workspace guardrail. - The BYOK wording. "Free BYOK request cap" refers to OpenRouter's monthly allowance of bring-your-own-key traffic before its fee applies. The message in April counted requests; the docs as of September 18, 2026 state the allowance as list-price inference cost per month ($25,000 on pay-as-you-go, $200,000 on Enterprise). Either way, past the allowance a 5% fee is charged to OpenRouter credits, and with none on the account the request is refused.
Whose account is empty?
Newer OpenRouter errors say which limit was hit in error.metadata.limit_source; read that before anything else.
error.metadata.limit_source | Meaning (OpenRouter's wording) | Retry? |
|---|---|---|
openrouter_in_flight_budget | Your running and recently completed requests already fill the budget | Yes, after the Retry-After header |
openrouter_key_limit | The API key's credit limit is exhausted | No. Raise the key limit or use another key |
openrouter_credits | Your balance cannot cover the request, or the single request is too expensive for your in-flight budget | No. Add credits or shrink the request |
| absent | Older wording, BYOK cap, or the error was produced by a tool in front of OpenRouter | No |
Then work out whose account it is, because two of the four cases cannot be fixed from your side.
| Where the key lives | Who can fix it | What to do |
|---|---|---|
| Your own OpenRouter account, using OpenRouter credits | You | Top up at openrouter.ai/settings/credits. A negative balance also 402s, including on free models. If the balance is fine, check the per-key limit with the call below; a key with limit_remaining: 0 returns the same 402, and a burst of parallel requests can hit the in-flight budget, which clears by itself |
| Your own OpenRouter account, BYOK (your Anthropic, OpenAI, DeepSeek… key attached) | You | OpenRouter still bills a 5% fee against your OpenRouter credits, and a monthly free allowance applies before the fee starts. With no credits on the account the fee cannot be charged, so the request is refused even though your upstream key is fine. A small top-up clears it |
| A tool vendor's account (OpenCode Go, Pieces, a hosted agent) that calls OpenRouter on your behalf | The vendor | Nothing on your side changes it. The April 30 wave in opencode was Go's own OpenRouter account hitting the cap; it cleared within the hour once the vendor topped up. Wait, or point the tool at a provider you control |
| A shared team key with a spending limit set by an admin | Your admin | The key's limit was reached. Ask for a higher limit or a separate key |
curl -s https://openrouter.ai/api/v1/key -H "Authorization: Bearer $OPENROUTER_API_KEY"
# limit credit limit for this key, or null if unlimited
# limit_remaining what is left of that limit, or null
# usage credits used by this key, all time
# is_free_tier whether the account has ever bought creditsIf you never made an OpenRouter key, you are in the third row. The tool's vendor is paying OpenRouter for you, usually with BYOK so they can use their own provider contracts, and their fee balance or cap ran out. The opencode thread has a dozen "same here" replies the same day and then "it seems to be back"; nobody in it could have done anything sooner.
Fix 1: add credits or raise the key limit
For your own account, openrouter.ai/settings/credits. For a key with a limit, edit the key or make a new one without a limit. Retry the same request; there is no cooldown. If you use BYOK and want to stop thinking about the fee balance, keep a few dollars of credits on the account; the fee on a month of typical coding-agent traffic is small, but it must be chargeable or nothing goes through.
Fix 2: wait, if the account is the vendor's
Both vendor incidents we found cleared in under an hour once someone at the vendor topped up. Restarting the tool does not help by itself; two commenters restarted and it "seemed gone" because the top-up had landed in the meantime. If the tool has a status page, that is where the vendor will say so. Some tools retry a 402 as if it were a 429 and burn your time before showing the message.
Fix 3: keep the agent running on a provider you control
The lasting fix for the vendor case is a provider that is not shared with everyone else on the plan. Any OpenAI-compatible host works; ours serves the same open models Go was routing when it failed (Kimi K2.7 Code, MiniMax M3, DeepSeek V4 Flash) from a prepaid balance that only you draw on. For opencode:
{
"$schema": "https://opencode.ai/config.json",
"provider": {
"inferenceapis": {
"npm": "@ai-sdk/openai-compatible",
"name": "Inference APIs",
"options": { "baseURL": "https://api.inferenceapis.com/v1", "apiKey": "{env:INFERENCE_API_KEY}" },
"models": {
"moonshotai/Kimi-K2.7-Code": { "name": "Kimi K2.7 Code", "limit": { "context": 262144, "output": 32768 } },
"MiniMaxAI/MiniMax-M3": { "name": "MiniMax M3", "limit": { "context": 1000000, "output": 32768 } },
"deepseek-ai/DeepSeek-V4-Flash": { "name": "DeepSeek V4 Flash", "limit": { "context": 1000000, "output": 32768 } }
}
}
}
}Export INFERENCE_API_KEY, start opencode, and pick inferenceapis/moonshotai/Kimi-K2.7-Code in /models. Go stays configured; you can switch back per session. Our per-million-token prices as of September 18, 2026: Kimi K2.7 Code $0.89 in / $4.42 out, MiniMax M3 $0.39 / $1.56, DeepSeek V4 Flash $0.19 / $0.38, with repeated context billed at the cached rate automatically. OpenRouter's price for the same models depends on which upstream it picks; for pure token cost it can be equal or lower. What you are paying for here is a balance nobody else can empty, and a host that does not route to a second company.
When our balance runs out you get the same status, 402, with code: "insufficient_balance" and a link to /billing. There is no cap besides the balance and no fee for using your own anything. The opencode guide and the list of tools that accept a custom endpoint cover the other clients.
Handling 402 in code
Read error.metadata.limit_source. Only openrouter_in_flight_budget is worth retrying, and OpenRouter tells you when in Retry-After. Everything else is a billing answer: retrying with backoff, which many agent loops do for anything 4xx that is not 400 or 401, turns a five-second failure into a five-minute one. Treat those like 401: stop the run, surface the message with the link, and let a human add credits or switch provider. If you stream, also check every chunk for an error object or finish_reason: "error", since OpenRouter reports mid-stream failures inside a 200.
Frequently asked questions
I attached my own DeepSeek key on OpenRouter and have $0 in credits. Why is that a 402?
OpenRouter charges 5% of what the request would have cost at its list price, deducted from your OpenRouter credits, once you are past the monthly free allowance. With nothing to deduct from, it refuses the request. Your DeepSeek key is never the problem in that case.
The balance page shows money. Why "Insufficient credits"?
Keys can carry their own spending limit, and workspaces can carry guardrails. Call /api/v1/key with the failing key and look at limit_remaining. The Traycer report in the sources is an example of a funded account where the request never reached OpenRouter at all; when the request is missing from the OpenRouter activity log, the 402 was generated by the tool, not by OpenRouter.
Does the "for this month" cap reset on the first?
The message implies a calendar month. OpenRouter's docs describe the allowance as monthly without stating the reset day. Do not plan around it; keep credits on the account instead.
Why did OpenCode Go users get a BYOK error when they never used OpenRouter?
Go sends some models through OpenRouter using OpenCode's own provider keys. Users in the thread worked this out from the error text; OpenCode did not comment before the bot closed the issue. The error is about OpenCode's account, and it was gone within the hour.
Is OpenRouter down when this happens?
No. 402 is a billing answer from a working service. Outages come back as 502 (model down or bad upstream response) or 503 (no provider meets the routing requirements).
Where Inference APIs fits
We are a direct host, not a router: one prepaid balance, billed per token, no fee for using your own keys because there are none to bring. If the 402 came from a tool vendor's pooled account, adding us as a custom provider is the one fix that does not depend on the vendor. If it came from your own OpenRouter account, topping it up is quicker than switching; the cost comparison below is honest about that.
Something changed or wrong? Tell us and we will re-verify the entry.
