> ## Documentation Index
> Fetch the complete documentation index at: https://docs.rialto.xyz/llms.txt
> Use this file to discover all available pages before exploring further.

# Complete Supported Tokens Universe

> Cache Rialto's complete supported-token universe and report genuine demand for unsupported tokens.

This guide describes how a Partner should cache Rialto's current quote-admission
list, avoid unnecessary quote work, and report genuine demand for tokens that
are not yet supported so Rialto can auto-enable them once genuine demand is established.

## Endpoints

Production API:

```text theme={null}
https://rialto-trade-api.rialto.xyz
```

Supported-token snapshot:

```http theme={null}
GET /tokens/supported-tokens?chain_id=4663
```

The snapshot endpoint does not require an API key. It is public-rate-limited,
so the Partner should maintain one shared cache rather than polling it independently
for every quote request or worker.

## Initial Snapshot: `200 OK`

Request:

```bash theme={null}
curl --compressed \
  'https://rialto-trade-api.rialto.xyz/tokens/supported-tokens?chain_id=4663'
```

Response:

```http theme={null}
HTTP/2 200
Content-Type: application/json
Content-Encoding: gzip
ETag: W/"4663-<snapshot-hash>"
Cache-Control: public, max-age=15, stale-while-revalidate=60
```

```json theme={null}
{
  "schema_version": 1,
  "chain_id": 4663,
  "snapshot_id": "0x...",
  "count": 75486,
  "addresses": [
    "0x...",
    "0xeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeee"
  ]
}
```

On `200 OK`, the Partner should:

1. Parse the response into a new lowercase address `HashSet`.
2. Verify `chain_id`, `schema_version`, and `count`.
3. Save the response `ETag`.
4. Atomically replace the previous `HashSet` only after parsing succeeds.

The body is prebuilt by Rialto and gzip-compressed in transit. Local hash-set
membership is constant-time and does not require another Rialto request.

## Conditional Refresh: `304 Not Modified`

Poll once every 15-60 seconds using the last ETag:

```bash theme={null}
curl --compressed -i \
  -H 'If-None-Match: W/"4663-<snapshot-hash>"' \
  'https://rialto-trade-api.rialto.xyz/tokens/supported-tokens?chain_id=4663'
```

If the list is unchanged, Rialto returns:

```http theme={null}
HTTP/2 304
ETag: W/"4663-<snapshot-hash>"
```

The `304` response has no JSON body. The Partner should keep its existing `HashSet`.
This avoids repeatedly downloading and parsing the full address list.

If the list changed, Rialto returns `200 OK` with a new body and ETag. The Partner
should build and atomically publish a replacement `HashSet`.

## Quote Flow

For each genuine user quote request:

```text theme={null}
Normalize sell and buy addresses
        |
        v
Check both addresses in the Partner's local cache or snapshot HashSet
        |
        +-- both supported --> call /quote normally
        |
        +-- either unsupported --> optionally send one genuine demand probe
```

Snapshot inclusion means Rialto accepts the token for routing. It does not
guarantee that every pair, amount, or market state has a viable route.

Normal quote request:

```bash theme={null}
curl --get 'https://rialto-trade-api.rialto.xyz/quote' \
  -H "Authorization: Bearer $RIALTO_API_KEY" \
  --data-urlencode 'chain_id=4663' \
  --data-urlencode 'sell_token=0x...' \
  --data-urlencode 'buy_token=0x...' \
  --data-urlencode 'sell_amount=10' \
  --data-urlencode 'taker=0x...' \
  --data-urlencode 'slippage_bps=50'
```

## Unsupported Demand Probes

The Partner may send a `/quote` request for a token missing from its local snapshot
when that request represents real user demand. Rialto returns an explicit
unsupported-token response quickly.

The response is an explicit unsupported-token error, for example:

```http theme={null}
HTTP/2 400
```

```json theme={null}
{
  "error": "unsupported buy_token"
}
```

## Probe and Quote Limits

The Partner authenticates `/quote` with its existing API key and `quote:read` scope.
There is no additional API-key scope to configure.

Internally, Rialto uses two independent rate-limit buckets:

| Bucket        | Purpose                                                                                |
| ------------- | -------------------------------------------------------------------------------------- |
| `quote_probe` | Authentication, parsing, in-memory token admission, and unsupported-demand observation |
| `quote:read`  | Expensive routing and quote execution after both tokens pass admission                 |

The probe allowance is configured at up to 10 times the Partner's normal quote
allowance over the same limiter interval. An unsupported request consumes the
probe bucket but returns before consuming the expensive `quote:read` bucket.
A supported request passes admission and then consumes the ordinary quote
allowance as well.

The probe bucket is still bounded and rate-limited. The Partner should send only
genuine user demand, not synthetic loops or repeated requests intended only to
force promotion.

## Recommended Client Behavior

1. Maintain one shared full snapshot per chain.
2. Fetch the full universe on startup.
3. Poll every 15-60 seconds with `If-None-Match`.
4. Keep the current `HashSet` on `304` or transient refresh failure.
5. Atomically replace it after a valid `200` response.
6. Call `/quote` normally when both addresses are present.
7. For genuine demand involving a missing address, send the quote once as an
   unsupported-demand probe and handle the explicit rejection.
8. Do not repeatedly probe the same unsupported request inside a retry loop.
9. After a later snapshot includes the token, process it through the normal
   supported quote path.

Continue with the [Python reference implementation](/developers/partner-supported-tokens-python)
for a complete cache, refresh, admission-check, and demand-probe example.
