Start with the request
| Symptom | What to check |
|---|---|
| 404 at /api/ | Use https://formalengines.com/inference/v1/chat/completions for raw HTTP. |
| 401 invalid_api_key | Use the complete key after “Bearer ”, not a masked value or fingerprint. |
| Malformed JSON / shell error | Use a single JSON object. A single quote inside a shell single-quoted payload ends that string. Use the quickstart heredoc. |
| No visible answer | Check finish_reason, reasoning output, and max_tokens. A very small budget can be exhausted before the answer. |
| Unknown model | Copy an exact model ID from GET /models. |
| SDK sends extra_body as a JSON field | With raw HTTP, put model-specific options at the top level. The SDK merges extra_body for you. |
HTTP status codes
| Status | Meaning | Action |
|---|---|---|
| 400 / 422 | Invalid input, unsupported parameter, or context overflow | Inspect error.code and message; correct the request. |
| 401 | Missing, invalid, expired, or revoked key | Check credentials or create a new key. |
| 402 | Insufficient available credit for the request reservation | Check balance and holds; add credit or reduce the output reservation. |
| 403 | Account not permitted to make the request | Contact support; key rotation alone will not help. |
| 404 | Unknown model or incorrect endpoint | Check the URL and model ID. |
| 413 | Request body too large | Reduce the body size. |
| 429 | Rate, concurrency, daily-spend, or admission limit | Inspect the error. Honor Retry-After when provided; reduce concurrency. A daily-spend limit needs a reset or limit change. |
| 502 / 503 / 504 | Upstream or capacity failure / timeout | Retry transient failures with bounded exponential backoff and jitter. |
{
"error": {
"message": "The request exceeds the model context window.",
"type": "invalid_request_error",
"param": null,
"code": "context_length_exceeded"
}
}Retry deliberately
Do not retry authentication errors, malformed JSON, or an unchanged oversized request. For transient capacity errors, use a finite retry budget, exponential backoff with jitter, and Retry-After when supplied. Many SDKs already retry certain failures; account for that before adding another retry loop.
After a network timeout, a request may already have reached the model. There is no documented inference idempotency guarantee. Repeated requests may be separately billed. Streaming clients must also handle errors after the initial HTTP headers.
Include a request ID
Keep the HTTP status, model ID, timestamp, and response x-request-id when present. Send those details and a sanitized request to vatsal@formalengines.com. Never include your API key. Some rejections occur before a request ID is assigned.