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

# Rate Limits

> Rate limiting details and best practices.

PolyNode uses per-key rate limiting to ensure fair usage. Limits scale with your plan and with the endpoint class.

## Tier limits

<Info>
  **Firehose** = a WebSocket subscription with no filters applied. It receives every event (all settlements, trades, blocks, etc.) at full throughput. Filtered subscriptions — where you specify wallets, tokens, slugs, or size thresholds — use far less bandwidth and don't count toward your firehose limit.
</Info>

|                                      | Free             | Starter (\$50/mo)        | Growth (\$200/mo)        | Enterprise (\$750/mo)                      |
| ------------------------------------ | ---------------- | ------------------------ | ------------------------ | ------------------------------------------ |
| **Standard V3 REST data**            | Not available    | 1,000 req/min (\~16 QPS) | 2,000 req/min (\~33 QPS) | 4,000 req/min default; custom by agreement |
| **Heavy V3 trade-history endpoints** | Not available    | 1,000 req/min            | 1,500 req/min            | 1,500 req/min default; custom by agreement |
| **Event WebSocket connections**      | 1                | 10                       | 50                       | Unlimited                                  |
| **Orderbook WebSocket connections**  | 1                | 10                       | 50                       | Unlimited                                  |
| **Filter items per subscription**    | 10,000           | 10,000                   | 10,000                   | Custom                                     |
| **Orderbook market subs**            | Unlimited        | Unlimited                | Unlimited                | Unlimited                                  |
| **WebSocket session**                | 1 hour/day       | Unlimited                | Unlimited                | Unlimited                                  |
| **API keys**                         | 1                | 3                        | 10                       | 25                                         |
| **Snapshot size** (`snapshot_count`) | 20               | 100                      | 200                      | 500                                        |
| **Snapshot lookback** (`since`)      | 30 seconds       | 2 minutes                | 5 minutes                | 5 minutes                                  |
| **Key generation**                   | 1 per IP per day | Via dashboard            | Via dashboard            | Via dashboard                              |
| **Support**                          | Community        | Email                    | Priority                 | Dedicated + Slack                          |

<Info>
  **Snapshot size vs snapshot lookback** — these are two separate snapshot modes controlled by different parameters. `snapshot_count` returns the last N events (capped by your tier). `since` returns all events after a UNIX-ms timestamp within your tier's lookback window. If you pass both, `since` takes priority and `snapshot_count` is ignored. See [subscribing](/websocket/subscribing#param-since) for details.
</Info>

<Note>
  **Enterprise** includes dedicated server infrastructure. Contact [josh@quantish.live](mailto:josh@quantish.live) before activation.
</Note>

<Info>
  V3 REST data endpoints require a paid plan. Heavy trade-history endpoints have a separate per-key bucket in addition to your standard V3 REST data limit. See [V3 REST data limits](#v3-rest-data-limits) below.
</Info>

## How it works

* Rate limits are tracked per API key using a sliding window.
* V3 REST data endpoints require a paid API key. Free-tier keys receive `402 Payment Required`.
* Heavy V3 trade-history endpoints check both your standard V3 REST data limit and the heavy endpoint bucket. The stricter remaining limit applies.
* When you exceed the limit, you'll receive a `429 Too Many Requests` response.
* The error message includes a Unix timestamp for when you can retry.
* Successful REST responses include `x-ratelimit-limit`, `x-ratelimit-remaining`, and `x-ratelimit-reset` headers.

## Best practices

### Use WebSocket for real-time data

Instead of polling REST endpoints, connect via WebSocket for live updates:

```javascript theme={null}
// Instead of polling /v3/trades every 5 seconds (12 req/min)...
// Use WebSocket (1 connection, unlimited events)
const ws = new WebSocket("wss://ws.polynode.dev/ws?key=pn_live_YOUR_KEY");
ws.send(JSON.stringify({
  action: "subscribe",
  type: "settlements",
}));
```

### Cache metadata locally

Market metadata (question, slug, outcomes) changes infrequently. Cache it and only refresh periodically:

```javascript theme={null}
// Fetch full market list once
const markets = await fetch("/v3/markets/search?q=bitcoin&limit=100", { headers })
  .then((r) => r.json());

// Cache by token_id
const cache = new Map(markets.data.map((m) => [m.condition_id, m]));

// Use cache for lookups, refresh every 5 minutes
```

### Batch where possible

Use `POST /v3/wallets/batch` instead of many individual wallet summary requests when you need P\&L for multiple wallets.

### Use filtered subscriptions

WebSocket subscriptions with filters reduce message volume and processing overhead:

```json theme={null}
{
  "action": "subscribe",
  "type": "settlements",
  "filters": {
    "tokens": ["specific-token-id"],
    "min_size": 100
  }
}
```

## Expected WebSocket throughput

WebSocket subscriptions are not rate-limited by requests/min, but message volume varies significantly by subscription type:

| Subscription          | Typical messages/sec | Notes                           |
| --------------------- | -------------------- | ------------------------------- |
| Firehose (no filters) | 50–150               | \~0.5–1.5 Mbps uncompressed     |
| Filtered (1 market)   | 1–20                 | Depends on market activity      |
| Filtered (1 wallet)   | 0–5                  | Most wallets trade infrequently |
| Blocks only           | \~0.5                | One per Polygon block (\~2s)    |

<Tip>
  `status_update` events arrive in bursts (30–80 per block). If you don't need confirmation tracking, exclude them from your `event_types` filter to reduce volume.
</Tip>

## V3 REST data limits

Standard V3 REST reads count against your plan's V3 REST data limit.

| Plan       |                      Standard V3 REST data |           Heavy V3 trade-history endpoints |
| ---------- | -----------------------------------------: | -----------------------------------------: |
| Free       |                              Not available |                              Not available |
| Starter    |                              1,000 req/min |                              1,000 req/min |
| Growth     |                              2,000 req/min |                              1,500 req/min |
| Enterprise | 4,000 req/min default; custom by agreement | 1,500 req/min default; custom by agreement |

Heavy V3 trade endpoints have a separate per-key bucket because trade-history scans are the highest-throughput REST surface:

* `/v3/trades`
* `/v3/wallets/{address}/trades`
* `/v3/wallets/{address}/combos/trades`
* `/v3/markets/{token_id}/trades`
* `/v3/markets/slug/{slug}/trades`
* `/v3/builders/{code}/trades`

When the heavy bucket is exceeded, you'll receive a `429` response with:

```json theme={null}
{
  "error": "rate limit exceeded",
  "scope": "v3_heavy",
  "reset_at": 1774108000
}
```

<Tip>
  For real-time trades, use the [WebSocket stream](/websocket/overview) instead of polling trade-history endpoints.
</Tip>

## Pagination limits

Most V3 list endpoints default to `limit=100` and clamp `limit` to a maximum of `300` rows per page. If you request more than the page cap, PolyNode normalizes `limit` to the maximum allowed value. Responses include the actual `limit`, `offset`, `rows_returned`, and `has_more` values.

`/v3/markets/condition/{condition_id}/positions` supports tiered page sizes for holder lists: Starter keys can request up to `300` rows, Growth keys up to `1000`, and Enterprise keys up to `2000`.

`/v3/wallets/{address}/pnl/events` is the exception: it defaults to `limit=5000` and clamps to a maximum of `10000` buckets.

For deep trade-history walks, prefer `after` and `before` time windows instead of very large offsets.

## Higher limits

Upgrade your plan at [polynode.dev/pricing](https://polynode.dev/pricing) for higher rate limits and more WebSocket connections. Contact [josh@quantish.live](mailto:josh@quantish.live) for Enterprise capacity above the default V3 REST limits.
