Skip to main content
When something goes wrong, the Predexy API always returns a structured error response with a machine-readable status code and a human-readable message. This consistent format means you can handle errors programmatically using the status field while surfacing useful context to your users or logs via the message field. Internal server details are never exposed — only safe, descriptive messages reach your client.

Error response format

Every error from the Predexy API follows this envelope:
{
  "status": "MACHINE_CODE",
  "message": "Human-readable description of what went wrong."
}
  • Use status for programmatic branching in your code — it never changes for a given error condition.
  • Use message for logging and user-facing display — it may include dynamic context like a countdown or a field name.

Error codes

The table below covers every status code defined in the API. HTTP status codes are listed alongside each to help you triage at the transport layer before parsing the body.
Status codeHTTP statusWhen it occursHow to handle it
INVALID_REQUEST400Malformed or missing request parametersValidate inputs before sending; check message for the offending field
UNAUTHORIZED401Missing, expired, or invalid authentication credentialsRe-authenticate or check that your token/key is being sent correctly
FORBIDDEN403Valid credentials but insufficient permissions for this endpointCheck your API key’s permission scopes in the Developer Console
NOT_FOUND404The requested resource does not existVerify the ID or path in your request
RATE_LIMITED429Request rate exceeds your tier’s limitBack off and retry after X-RateLimit-Reset; see rate limits
INTERNAL_ERROR500An unexpected error occurred on the serverRetry with backoff; contact support if persistent
SERVICE_UNAVAILABLE503The service is temporarily down or under maintenanceRetry with backoff; monitor status page
MARKET_NOT_FOUND404The specific market ID does not existConfirm the market ID is valid and still active
QUESTION_NOT_FOUND404The canonical question ID does not existConfirm the question UUID; it may have been removed
EMBEDDING_FAILED502The semantic matching service returned an errorRetry; this is a transient upstream error
PLATFORM_UNAVAILABLE502Upstream platform data is temporarily unavailableRetry later; the specific platform may be experiencing downtime
INVALID_API_KEY401The API key does not exist or has been revokedCheck the key in your Developer Console; generate a new one if revoked
API_KEY_REQUIRED403The endpoint requires API key authenticationAdd your X-API-Key: pdx_... header
QUOTA_EXCEEDED429Your usage quota for the billing period has been reachedUpgrade your plan or wait for the quota to reset
MATCH_NOT_FOUND404No cross-platform match exists for the requested marketThe market may not yet be indexed or matched
INVALID_PRICE400A price value is outside the valid range (0–1)Ensure all price values are probabilities between 0 and 1
EMAIL_EXISTS409The email address is already registeredUse a different email or log in with the existing account

Example error responses

{
  "status": "INVALID_REQUEST",
  "message": "Invalid request parameters"
}

Handling errors in Python

The pattern below covers the most common error categories you’ll encounter in production:
python
import requests

def handle_response(response: requests.Response) -> dict:
    if response.ok:
        return response.json()

    body = response.json()
    status = body.get("status")
    message = body.get("message", "Unknown error")

    if status == "RATE_LIMITED":
        reset_at = response.headers.get("X-RateLimit-Reset")
        raise Exception(f"Rate limited. Reset at Unix timestamp {reset_at}. {message}")

    if status == "QUOTA_EXCEEDED":
        raise Exception(f"Quota exceeded. Upgrade your plan or wait for reset.")

    if status in ("UNAUTHORIZED", "INVALID_API_KEY"):
        raise Exception(f"Authentication error: {message}")

    if status == "FORBIDDEN":
        raise Exception(f"Permission denied: {message}")

    if status in ("NOT_FOUND", "MARKET_NOT_FOUND", "QUESTION_NOT_FOUND", "MATCH_NOT_FOUND"):
        raise Exception(f"Resource not found: {message}")

    if status in ("INTERNAL_ERROR", "SERVICE_UNAVAILABLE", "EMBEDDING_FAILED", "PLATFORM_UNAVAILABLE"):
        raise Exception(f"Server error (retryable): {message}")

    raise Exception(f"API error [{status}]: {message}")
The message field is always safe to log and display to end users. It never contains internal stack traces, database details, or secrets.
For automated retries, treat INTERNAL_ERROR, SERVICE_UNAVAILABLE, EMBEDDING_FAILED, and PLATFORM_UNAVAILABLE as transient — they typically resolve within seconds. Treat UNAUTHORIZED, FORBIDDEN, INVALID_API_KEY, and QUOTA_EXCEEDED as permanent until you take corrective action.