Errors
Synthient uses HTTP status codes to identify failures. API errors normally include a JSON problem body; edge and infrastructure errors may return plain text or no body.
HTTP error shape
API errors use application/problem+json. The type, title, and status describe the error, detail explains the failure, and instance identifies the request.
Generic error
{
"type": "https://docs.synthient.com/errors/unauthorized",
"title": "Unauthorized",
"status": 401,
"detail": "Invalid API Key",
"instance": "4f1c2a9e7b3d4e5f8a6b9c0d1e2f3a4b"
}
Validation failures return 422 with an errors map of field names to messages instead of detail:
Validation error
{
"type": "https://docs.synthient.com/errors/validation-failed",
"title": "One or more validation errors occurred.",
"status": 422,
"errors": {
"ip_address": ["Invalid IP address format."]
},
"instance": "9a8b7c6d5e4f40312a1b2c3d4e5f6a7b"
}
The edge rejects missing or malformed (non-UUID) keys with 401 text/plain and the body 401 invalid api key. Infrastructure failures may return HTML or an empty body. Read the HTTP status before parsing JSON, and handle missing problem fields. An empty body alone is not a reason to retry a billed lookup.
Capture the X-Request-Id response header, or the problem's instance, when available. Include it when contacting support.
Status code reference
| Status | Meaning | What to do |
|---|---|---|
| 400 Bad Request | Bad export date or hour, or invalid pagination cursor. | Fix the request before retrying. |
| 401 Unauthorized | Missing or invalid x-api-key header. | Verify the key is loaded from the environment and not truncated. See Authentication. |
| 402 Payment Required | Lookup credit balance is exhausted. | Add credits, upgrade your plan, or wait for lookup_quota.resets_in to elapse. See Rate Limits. |
| 403 Forbidden | API key lacks the scope required for this endpoint. | Check granted scopes via /account/me; reach out to support to add the missing one. |
| 404 Not Found | Snapshot or other resource is absent. | Check the identifier. A daily snapshot still being rolled up can return Retry-After; wait before requesting it again. |
| 422 Unprocessable Content | Malformed, private, or reserved IP; empty batch, over 1,000 entries, or no usable addresses. | Correct the input using the field-level errors. |
| 429 Too Many Requests | Team request rate, key monthly request budget, or concurrent-stream limit reached. | Retry only with a valid Retry-After. Without it, resolve the budget or stream limit before trying again. |
| 500 Internal Server Error | Unexpected server error. | Account/feed calls may retry with backoff. Surface lookup and health failures. |
| 502 / 503 / 504 Gateway or service error | Gateway, streaming, or downstream backend temporarily unavailable. | Account/feed calls may retry with backoff. Surface lookup and health failures. |
Per-status examples
400 Bad Request
Check the export date, hour, or cursor. For example, a listing cursor must be copied unchanged from the previous response's next_cursor.
401 Unauthorized
Check that the key is non-empty and sent in the x-api-key header. The edge's plain-text rejection and the API's JSON problem response both use 401.
402 Payment Required
Inspect lookup_quota.credits and lookup_quota.resets_in on /account/me. Streaming and export endpoints do not consume lookup credits.
403 Forbidden
The key is valid but lacks the scope for this endpoint or feed. For example, a key with only PROXY_FIREHOSE cannot call /feeds/anonymizers/stream.
404 Not Found
A snapshot may be absent or still being rolled up. For a pending daily rollup, the API can include Retry-After; the SDKs surface this 404 so the caller can schedule another attempt. An unseen domain returns 200 with status: "inactive" and zeroed counts.
422 Unprocessable Content
Malformed, private, and reserved IP addresses produce 422. A batch also fails validation if it is empty, exceeds 1,000 entries, or contains no usable addresses. The SDKs reject some invalid inputs locally before sending a request.
429 Too Many Requests
Request-rate buckets are shared by a team. The key's monthly request budget and concurrent-stream allowance can also produce 429.
Retry only when Retry-After is valid. It can contain seconds or an HTTP date. Wait at least that long after applying jitter to your backoff. Without the header, check the monthly budget and open streams instead of retrying in a loop. The SDKs also stop when the requested wait exceeds 60 seconds.
500 / 503 Server errors
A 500 indicates an unexpected server fault; 502, 503, and 504 indicate gateway or service failures. Account and feed requests can retry these transient failures with bounded exponential backoff and jitter. The SDKs do not retry billed lookups on these statuses or on transport failures because the lookup may already have been processed. Health failures are also surfaced immediately. See Rate Limits for the complete policy and a lookup example.
Recovery checklist
- Read the status code first. Parse the problem body when present, while accepting plain-text and empty responses.
- Apply the endpoint's retry policy. Lookups and health retry only
429with a validRetry-After. Account and feed requests can also retry transient server and connection failures. - Preserve the requested wait. Apply jitter to the backoff first, then take the larger of that delay and
Retry-After. Stop after a bounded number of attempts. - Correct permanent failures. Fix invalid input, credentials, scopes, or exhausted budgets before trying again. Handle a pending-rollup
404separately. - Keep the request identifier. Record the status and
X-Request-Idorinstance, and inspectdetailorerrorsfor diagnostics.
Next steps
- Authentication: fixing
401and403errors. - Rate Limits: handling
402and429correctly. - Support: diagnosing persistent failures.