Errors and troubleshooting
Errors use one normalized envelope. Preserve request_id in logs and support tickets.
{
"error": {
"message": "The requested model is temporarily unavailable.",
"type": "model_unavailable",
"param": null,
"code": "model_unavailable",
"retryable": true,
"charged": "no"
},
"request_id": "req_…"
}
| Surface | Status | Notes |
|---|---|---|
401 | unsupported | invalid_api_key, key_revoked, key_expired. Fix credentials; do not retry unchanged. |
402 | gated | insufficient_balance or budget_exceeded. Add credit or lower the conservative maximum. |
429 | gated | rate_limit_exceeded. Honor Retry-After and reduce request/token concurrency. |
503 | gated | model_unavailable or route_unavailable. Refresh the catalogue and retry safe non-streaming requests. |
504 | gated | provider_timeout. A request may have been charged if usage was served; inspect usage before retrying. |
Recovery matrix
- Insufficient balance: add purchased credit, confirm the wallet is open, then retry with a new request ID. A failed preflight is not billed.
- Unavailable model: use
GET /v1/models, select an operational model permitted by the project, and keep the original request ID for diagnosis. - Throttling: honor
Retry-Afterand apply bounded exponential backoff with jitter. Do not retry a stream after output. - Timeout: use a bounded timeout; retry only when the error is documented retryable and no customer-visible output was emitted.
- Unsupported feature: remove the offending field or choose a model with affirmative capability evidence.
- Provider degradation: keep the safe error, request ID, and retry metadata. The gateway may fail over only within its documented route policy.