Skip to main content
Use this page to understand what A Phaseo error means and what to do next. Every error response follows the same JSON format, so your app can handle failures consistently across models and providers.

Example error response

{
  "generation_id": "G-abc123",
  "status_code": 502,
  "error": "upstream_error",
  "error_type": "system",
  "error_origin": "upstream",
  "reason": "all_candidates_failed",
  "description": "Provider \"google-ai-studio\" failed with HTTP 403 for endpoint \"responses\" on model \"google/gemini-2.5-pro\".",
  "attempt_count": 1,
  "failed_providers": ["google-ai-studio"],
  "failed_statuses": [403],
  "provider_failure_diagnostics": {
    "category": "provider_access_missing",
    "hint": "The provider account appears not to have access to this model or feature yet. Verify account entitlements and provider-side access.",
    "provider": "google-ai-studio"
  },
  "upstream_error": {
    "code": "PERMISSION_DENIED",
    "message": "The caller does not have permission.",
    "description": null,
    "param": null
  },
  "failure_sample": [
    {
      "provider": "google-ai-studio",
      "type": "upstream_non_2xx",
      "status": 403,
      "upstream_error_code": "PERMISSION_DENIED",
      "upstream_error_message": "The caller does not have permission.",
      "upstream_error_description": null,
      "upstream_error_param": null,
      "upstream_payload_preview": "{\"error\":{\"status\":\"PERMISSION_DENIED\"}}",
      "retryable": false
    }
  ]
}

Fields you will always get

  • generation_id: a stable request ID you can share with support.
  • status_code: mirrors the HTTP status code.
  • error: a machine-readable error code, such as validation_error.
  • error_type: a high-level class, usually user or system.
  • error_origin: whether the problem was mainly caused by the caller, Phaseo, or an upstream provider.
  • description: a plain-language explanation of what happened.
  • details (optional): structured validation details when the error is a request-validation problem.

Extra fields you may see

Some errors include more detail to help you fix the issue faster:
  • reason: a more specific subreason such as all_candidates_failed or pricing_not_configured.
  • provider_candidate_diagnostics and provider_enablement: explain why a model could not be used with the requested endpoint.
  • routing_diagnostics: extra detail about how routing or availability checks narrowed the request.
  • provider_failure_diagnostics: hints for missing credentials, missing access, region restrictions, rate limits, and similar provider-side failures.
  • upstream_error and failure_sample: best-effort summaries of the first provider failure when the request reached a provider.
  • failed_providers, failed_statuses, and attempt_count: extra retry and failover context.

Status class guidance

StatusMeaningRecommended action
400-499Request, auth, or permission problemFix the request or credentials before retrying.
429Provider or route-level throttlingRetry with backoff and respect Retry-After.
500-599Phaseo or upstream provider failureRetry with jittered backoff and log the request ID.

Common error codes

TypeHTTP StatusDescription
authentication_error401Missing or invalid API key.
authorization_error403The key does not have access to this resource.
not_found_error404The endpoint or resource could not be found.
rate_limit_error429Too many requests. Retry after the specified delay.
validation_error400Invalid parameters or request body.
provider_error502The upstream model provider failed to respond correctly.
server_error500An unexpected issue happened inside Phaseo.

When a provider fails

If Phaseo reached a provider but the request still failed, you may see:
  • provider_failure_diagnostics.category
  • provider_failure_diagnostics.hint
  • provider_failure_diagnostics.provider
Current categories include:
  • credentials_not_configured
  • credentials_invalid_or_forbidden
  • provider_access_missing
  • region_or_project_restriction
  • model_unavailable_for_endpoint
  • rate_limited
  • server_error
These fields are meant to help you fix the problem without turning on full debug mode.

When a model or endpoint is not available

For unsupported_model_or_endpoint responses, Phaseo may include:
  • provider_candidate_diagnostics
  • provider_enablement
  • missing_pricing_providers
  • routing_diagnostics
This helps you distinguish between:
  • a known model that is not active yet
  • a model that does not support the endpoint you asked for
  • missing pricing data
  • rollout or internal availability restrictions
Common fields:
  • provider_candidate_diagnostics.totalProviders: how many providers were known for the model before endpoint filtering.
  • provider_candidate_diagnostics.supportsEndpointCount: how many of those providers support the requested endpoint.
  • provider_candidate_diagnostics.candidateCount: how many providers remained after adapter checks.
  • provider_candidate_diagnostics.droppedUnsupportedEndpoint: providers dropped because they do not support the endpoint.
  • provider_candidate_diagnostics.droppedMissingAdapter: provider/endpoint pairs dropped because there is no gateway adapter for that endpoint yet.
  • provider_enablement.capability: the capability gate being enforced, such as video_generation.
  • provider_enablement.providersBefore / provider_enablement.providersAfter: providers before and after capability or enablement filtering.
  • provider_enablement.dropped[].reason: machine-readable reasons such as pricing_missing.
  • routing_diagnostics.filterStages[].stage: the routing stage, for example capability, rollout, or routing-status filtering.
  • routing_diagnostics.filterStages[].beforeCount / routing_diagnostics.filterStages[].afterCount: provider counts before and after each stage.
  • routing_diagnostics.filterStages[].droppedProviders[].reason: machine-readable reasons such as rollout or routing restrictions.

Example

{
  "generation_id": "G-unsupported123",
  "status_code": 400,
  "error": "unsupported_model_or_endpoint",
  "description": "No provider is currently routable for endpoint \"responses\" on model \"example/model\".",
  "provider_candidate_diagnostics": {
    "totalProviders": 3,
    "supportsEndpointCount": 2,
    "candidateCount": 1,
    "droppedUnsupportedEndpoint": ["provider-a"],
    "droppedMissingAdapter": [
      {
        "providerId": "provider-b",
        "endpoint": "responses"
      }
    ]
  },
  "provider_enablement": {
    "capability": "responses",
    "providersBefore": ["provider-b", "provider-c"],
    "providersAfter": ["provider-c"],
    "dropped": [
      {
        "providerId": "provider-b",
        "reason": "pricing_missing"
      }
    ]
  },
  "routing_diagnostics": {
    "filterStages": [
      {
        "stage": "provider_routing_status",
        "beforeCount": 1,
        "afterCount": 0,
        "droppedProviders": [
          {
            "providerId": "provider-c",
            "reason": "provider_status_not_ready"
          }
        ]
      }
    ]
  }
}

Optional debug mode

Most request schemas support a debug object for controlled troubleshooting:
{
  "debug": {
    "enabled": true,
    "return_upstream_request": true,
    "return_upstream_response": false,
    "trace": true,
    "trace_level": "summary"
  }
}
Available fields:
  • enabled
  • return_upstream_request
  • return_upstream_response
  • trace
  • trace_level (summary or full)
Use debug mode in development or tightly controlled environments only.

Retry strategy

  • 400-series errors: Fix your request before retrying.
  • 429: Implement exponential backoff and honor the Retry-After header.
  • 500-series errors: Retry safely after a short delay.
Example:
if (error.error === "rate_limit_error") {
  await sleep(retryAfterMs);
  return retryRequest();
}

Streaming-specific notes

  • If the request fails before streaming begins, you get a standard JSON error payload.
  • If it fails mid-stream, treat the partial stream as incomplete and show a retry option.
  • Always capture generation_id and endpoint/model metadata in logs.

Troubleshooting tips

  • Check the Gateway status page for ongoing incidents.
  • Review your request payload against the endpoint docs.
  • Share generation_id when contacting support.

Authentication

Authenticate with bearer API keys.

Limits

Handle provider-driven throttling and retries.

Streaming

Use SSE safely in production flows.
Last modified on July 9, 2026