---
title: "Errors"
description: "What the error body carries, and the closed list of codes to branch on."
---

> Documentation Index
> Fetch the complete documentation index at: https://agents.wego.com/llms.txt
> Use this file to discover all available pages before exploring further.

# Errors

Every error is an RFC 9457 Problem Details body (`application/problem+json`), the `Problem` schema every endpoint shares. Branch on `code` (a closed enum), never on the human `title` or `detail`. `trace_id` equals the `x-trace-id` response header; quote it when reporting an issue.

## Codes

The list is closed, so a value your client does not recognise means the client is older than the API: fall back to the HTTP status.

| `code` | Status | Means | What to do |
|---|---|---|---|
| `validation_failed` | 400 | A parameter or body field was rejected before any work happened. | Read `detail`, which names the field and the fix. Do not retry the same request unchanged. |
| `invalid_token` | 401 | No bearer token, or one that is expired or not accepted. | Get a fresh access token and retry once. With the CLI, `wego login`. |
| `insufficient_scope` | 403 | The token is valid but lacks a scope this operation needs. | Re-authorize asking for the required scope, then retry. |
| `not_found` | 404 | On a search-scoped id, usually an expired id rather than a wrong one: every `searchId`, trip id, fare id and rate id is opaque, context-bound and short-lived. On a `hotelId`, which does not expire, it means the hotel is unknown. | For a search-scoped id, create a new search and rethread the ids from it; retrying the same id never recovers. For a `hotelId`, check the id: searching again will not help. |
| `rates_require_hotel_search` | 409 | `getHotelRates` was given a `searchId` from a city or geo search. Only a search created with `hotelId` prices a hotel's full room list; a city search holds a sample of it, and re-reading never deepens that sample. | Create a search with `hotelId` plus the same dates and occupancy, then read its rates. With the CLI, `wego hotels rooms <hotelId> <checkIn> <checkOut>`. |
| `rate_limited` | 429 | You exceeded a quota. | Wait `Retry-After` seconds; it takes precedence over the reset in `RateLimit`. Creating a search is the costly step, so thread one `searchId` through `results` rather than re-creating. |
| `bad_gateway` | 502 | A travel provider answered with something the API could not use. | Retry once. If it persists, quote `trace_id`. |
| `upstream_unavailable` | 503 | A travel provider is temporarily unreachable. | Honor `Retry-After` and retry. |
| `upstream_rate_limited` | 503 | A travel provider's own rate limit rejected the call. That quota is shared across callers, so you can hit it without having sent much yourself. | Wait the full `Retry-After` (60 seconds). If the retry gets the same error, wait the new `Retry-After` again: the provider also enforces a longer window, so one wait is not always enough. Pace search creation rather than bursting. |
| `internal_error` | 500 | A fault on the API side. | Retry once, then quote `trace_id` if it persists. |

`status` repeats the HTTP status and `title` is fixed per code, so neither carries information `code` does not. Only `detail` varies per occurrence, and it is written for a human reader.

Source: https://agents.wego.com/api/errors/index.mdx
