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

# Cross-venue book

> Consolidated best bid and offer across every venue we collect, with the venue named on each side, plus how far apart venues are quoting the same contract.

Best bid and best offer for each contract across **every venue we collect**,
with the venue named on each side, plus how far apart those venues are quoting
the same contract.

This is not what [`/options/chain`](/api/v2/options/chain) returns. The chain's
`bid` and `ask` come from the aggregated row, which is based on a single venue.
This endpoint is the genuine best-of, and by construction its spread is never
wider than any individual venue's.

<Note>
  Read this as **execution quality**, not as a dislocation scanner. Across the
  liquid band, cross-venue implied-vol dispersion sits *inside* the tightest
  single venue's own spread roughly 70% of the time, so for the typical contract
  there is nothing to capture. What the endpoint answers well is where to execute
  and what it costs.
</Note>

## Scope

Computed only for contracts inside the liquid band: **0.85 to 1.15 moneyness,
2 or more days to expiry**.

Outside that band implied vol stops carrying information. Deep-ITM contracts
have almost no vega, so a trivial price difference reads as tens of vol points.
Before the band was applied, the widest apparent "dislocation" in a live run was
52 vol points on a 60,000 strike with spot at 77,600, which is an artefact
rather than a signal.

Contracts quoted by a single venue are omitted, since every field here is a
comparison. A symbol with no multi-venue coverage returns `404` rather than an
empty list, because an empty list reads as "spreads are zero".

## Units

All prices are **coin-denominated**, and the response states this in
`price_unit`.

Most venues publish option premium in USD or USDT; those are converted at
ingest. Deribit quotes its linear (USDC-settled) assets in USD and is converted
the same way, while its BTC and ETH options are inverse and already coin-
denominated. Do not infer the unit from magnitude: comparing an unconverted USD
premium against a coin premium is exactly how a spread of -195% gets published.

## Reading the fields

<ResponseField name="consolidated" type="boolean">
  `true` only when **two different venues** make the top of book. When `false`,
  one venue is best on both sides, so the spread shown is that venue's own and
  there is no consolidation benefit to report.
</ResponseField>

<ResponseField name="top_of_book_liquid" type="boolean">
  `true` when both sides come from a deep venue (Deribit, Bybit, OKX, Binance).
  When `false` the best price is coming from a thinner venue. Still worth
  seeing, but not a number to lean on.
</ResponseField>

<ResponseField name="book_crossed" type="boolean">
  A negative spread: one venue bidding above another's offer. Reported, never
  hidden, but excluded from `median_spread_pct` so the headline is not dragged
  below what trading actually costs.
</ResponseField>

<ResponseField name="crossed" type="boolean">
  The same idea on the implied-vol axis: best bid vol above best ask vol,
  evaluated only between deep venues.
</ResponseField>

<ResponseField name="mixed_settlement" type="boolean">
  The comparison spans both settlement conventions. Deribit's BTC and ETH
  options are inverse (coin-settled); the USDC venues are linear. Implied vol
  is comparable across the two to first order, but part of any gap flagged this
  way is numeraire rather than volatility.
</ResponseField>

<Warning>
  **A crossed market is an observation, not an opportunity.** Venue quote
  timestamps are collection times rather than exchange quote times, so a stale
  quote on the thinner venue cannot be ruled out. Measured crossings are small,
  short-dated and consistently one-directional, which points at structural causes
  (settlement, index, funding) rather than anything capturable. Treat `crossed`
  and `book_crossed` as venue-quality signals.
</Warning>

## Coverage

Venue coverage is not uniform, and the response tells you which venues actually
contributed via `venues` per contract and `coverage.venues` overall.

|                |                                 |
| -------------- | ------------------------------- |
| Deribit        | Prices, no per-side implied vol |
| OKX            | Per-side implied vol, no prices |
| Bybit, Binance | Both                            |
| Thalex, Delta  | Prices, single mark vol         |

A venue takes part in whichever comparison it actually supplied inputs for.
Venues missing an input are omitted rather than zero-filled, since a zero would
read as a dislocation.

BTC and ETH have the deepest coverage. SOL is thinner. Single-venue markets
return no rows at all.

## See also

<CardGroup cols={2}>
  <Card title="Options chain" href="/api/v2/options/chain" icon="table" />

  <Card title="Venues" href="/concepts/venues" icon="building-columns" />
</CardGroup>


## OpenAPI

````yaml GET /options/venue-book
openapi: 3.1.0
info:
  title: BackQuant API v2
  description: >-

    # BackQuant API v2


    Options + gamma-exposure focused public API. Built on the same data the

    BackQuant Pro Terminal renders - pre-computed every 30s, served from cache.


    ## What's in v2


    * **Discovery**: `/v2/symbols` (universe + per-symbol freshness + supported
      endpoint list), `/v2/expiries` (active expiry tokens with DTE), `/v2/status`
      (per-symbol-per-category health with thresholds + overall classification).
    * **GEX**: composable levels (HVL / call wall / put support / max-pain /
      expected move / gamma-flip zones), strike profile with typed expiry
      filter, expiry profile, strike × expiry heatmap with downsampling,
      greek time-heatmap with DTE/OI/IV filters, history (cursor-paginated),
      Postgres-backed stress history, **per-expiry max-pain with pain curve**.
    * **Options**: filtered options chain with two-layer projection (top-level
      `?fields=` and per-contract `?include=oi,iv,greeks,bid_ask,volume,gex`)
      plus moneyness filter (`?moneyness_min=0.9&moneyness_max=1.1`), expiry
      summary table, full IV suite (surface / term structure / 25Δ-10Δ skew /
      curves / **single-expiry smile** / IV-RV history / VRP), expected move,
      **Breeden-Litzenberger probability density and surface**, typed greek
      profiles (delta / theta / vanna / charm / vega), strike × time charm/vega
      surfaces, strike × expiry 3D greek surface, OI by expiry + history,
      put/call ratio (intraday or daily), 0DTE & weekly premium tide,
      dated-futures term structure.
    * **Liquidation**: heatmap + leverage-tiered distribution.

    * **Multi**: `/v2/multi/gex/levels` - bundled multi-symbol read across the
      universe in one round-trip, with the same `?include=` model as the
      single-symbol endpoint.

    ## Authentication


    Every v2 route (except `/v2/openapi.json`, `/v2/docs`, `/v2/redoc`, and

    `/v2/health`) requires the `X-API-Key` header.


    ```

    X-API-Key: bq_live_your_api_key_here

    ```


    **Get your API key at
    [backquant.com/api-access](https://backquant.com/api-access).**


    The same key works across v1 and v2 - if you already have a v1 key, no

    re-issuance is needed.


    ## Rate limits


    Two budgets, both derived from your subscription tier: a **monthly request

    allowance** per account, and a **per-minute burst** per key. Size your

    integration against the monthly figure - sustained polling at the burst rate

    exhausts the month early.


    | Plan                      | Monthly allowance | Burst    | Sustained   |

    |---------------------------|-------------------|----------|-------------|

    | Starter (Terminal Yearly) | 10,000 req/month  | 10/min   | ~333/day    |

    | Standard (Crypto API)     | 250,000 req/month | 60/min   | ~8,300/day  |

    | Pro (Terminal + API)      | 1,000,000/month   | 120/min  | ~33,000/day |

    | Enterprise                | custom            | 600/min  | custom      |


    Headers `X-RateLimit-Limit / -Remaining / -Reset` (burst) and

    `X-Quota-Limit / -Used / -Remaining / -Period` (monthly) are included in

    every response; the rate-limit triple is echoed inside `meta.rate_limit`

    when populated by middleware. Exceeding either budget returns `429`.


    The live ladder is served at `GET /v2/meta` under `rate_limits`.


    ## Response envelope


    ```json

    {
      "success": true,
      "data": { ... },
      "meta": {
        "version": "2.0",
        "timestamp": "2026-04-29T12:00:00.000Z",
        "request_id": "req_…",
        "symbol": "BTCUSDT",
        "spot_price": 67213.5,
        "computed_at": "2026-04-29T11:59:48.000Z",
        "freshness_seconds": 12.0,
        "source": ["deribit","bybit","okx","binance","derive","thalex","delta_india","delta"],
        "exchanges_filtered": ["deribit","bybit"]
      }
    }

    ```


    ## Errors


    ```json

    {
      "success": false,
      "error": {
        "code": "NOT_FOUND",
        "message": "No data for BTCUSDT"
      },
      "meta": { "version": "2.0", "timestamp": "..." }
    }

    ```


    | Code                  | When |

    |-----------------------|------|

    | `UNAUTHORIZED`        | Missing or invalid API key |

    | `FORBIDDEN`           | Subscription doesn't allow API access |

    | `NOT_FOUND`           | Symbol/expiry/etc. not present in cache |

    | `VALIDATION_ERROR`    | Bad query parameters |

    | `RATE_LIMIT_EXCEEDED` | Per-tier limit hit |

    | `UPSTREAM_ERROR`      | Cache or DB temporarily unreachable |

    | `INTERNAL_ERROR`      | Anything else |
        
  version: '2.6'
servers: []
security: []
tags:
  - name: Meta
    description: Unauthenticated metadata + endpoint catalog (planning your integration)
  - name: Discovery
    description: Symbol catalog, active expiries, and service status
  - name: GEX
    description: Gamma exposure analytics
  - name: Options
    description: Options chain, IV, greeks, probability, premium tide
  - name: Liquidation
    description: Liquidation heatmap and distribution
  - name: Multi
    description: Bundled multi-symbol endpoints (single round-trip across the universe)
paths:
  /options/venue-book:
    get:
      tags:
        - Options
      summary: Consolidated cross-venue book and quote dispersion
      description: >-
        Best bid and best offer for each contract **across every venue we
        collect**, with the venue named on each side, plus how far apart those
        venues are quoting the same contract.


        This is not what `/options/chain` returns. The chain's `bid`/`ask` come
        from the aggregated row, which is based on a single venue; this endpoint
        is the genuine best-of, and by construction its spread is never wider
        than any individual venue's.


        **Scope.** Computed only for liquid contracts (0.85-1.15 moneyness, 2+
        DTE). Outside that band implied vol stops carrying information: deep-ITM
        contracts have almost no vega, so a trivial price difference reads as
        tens of vol points. Contracts quoted by a single venue are omitted,
        since every field here is a comparison.


        **On `crossed`.** A crossed market (best bid vol above best ask vol) is
        reported as an observation, not an opportunity. Venue quote timestamps
        are collection times rather than exchange quote times, so a stale quote
        on the thinner venue cannot be ruled out, and measured crossings are
        small, short-dated and consistently one-directional - which points at
        structural causes (settlement, index, funding) rather than anything
        capturable.


        **On `mixed_settlement`.** Deribit's BTC/ETH options are inverse
        (coin-settled); the USDC venues are linear. Implied vol is comparable
        across the two to first order, but part of any gap flagged this way is
        numeraire rather than volatility.
      operationId: get_venue_book_options_venue_book_get
      parameters:
        - name: symbol
          in: query
          required: false
          schema:
            enum:
              - BTCUSDT
              - ETHUSDT
              - SOLUSDT
              - HYPEUSDT
            type: string
            description: 'Trading symbol: BTCUSDT, ETHUSDT, SOLUSDT, or HYPEUSDT.'
            default: BTCUSDT
            title: Symbol
          description: 'Trading symbol: BTCUSDT, ETHUSDT, SOLUSDT, or HYPEUSDT.'
        - name: expiries
          in: query
          required: false
          schema:
            anyOf:
              - type: string
              - type: 'null'
            description: Comma-separated expiry tokens, e.g. `26DEC25,27MAR26`.
            title: Expiries
          description: Comma-separated expiry tokens, e.g. `26DEC25,27MAR26`.
        - name: option_type
          in: query
          required: false
          schema:
            anyOf:
              - type: string
                enum:
                  - call
                  - put
              - type: 'null'
            description: Restrict to calls or puts.
            title: Option Type
          description: Restrict to calls or puts.
        - name: crossed_only
          in: query
          required: false
          schema:
            type: boolean
            description: >-
              Return only contracts where best bid vol exceeds best ask vol.
              Read the note on `crossed` above before acting on this.
            default: false
            title: Crossed Only
          description: >-
            Return only contracts where best bid vol exceeds best ask vol. Read
            the note on `crossed` above before acting on this.
        - name: sort
          in: query
          required: false
          schema:
            enum:
              - spread
              - spread_pct
              - dispersion
              - strike
            type: string
            description: Ordering for the returned contracts.
            default: spread_pct
            title: Sort
          description: Ordering for the returned contracts.
        - name: limit
          in: query
          required: false
          schema:
            type: integer
            maximum: 1000
            minimum: 1
            description: Max contracts returned.
            default: 200
            title: Limit
          description: Max contracts returned.
        - name: X-API-Key
          in: header
          required: false
          schema:
            anyOf:
              - type: string
              - type: 'null'
            title: X-Api-Key
      responses:
        '200':
          description: Successful Response
          content:
            application/json:
              schema: {}
        '401':
          description: Invalid or missing API key
          content:
            application/json:
              example:
                success: false
                error:
                  code: UNAUTHORIZED
                  message: Invalid API key
                meta:
                  version: '2.0'
                  timestamp: '2026-04-29T12:00:00Z'
        '404':
          description: No data available for the requested resource
          content:
            application/json:
              example:
                success: false
                error:
                  code: NOT_FOUND
                  message: No data for BTCUSDT
                meta:
                  version: '2.0'
                  timestamp: '2026-04-29T12:00:00Z'
        '422':
          description: Validation error on query parameters
          content:
            application/json:
              example:
                success: false
                error:
                  code: VALIDATION_ERROR
                  message: Invalid request parameters
                  details:
                    errors: []
                meta:
                  version: '2.0'
                  timestamp: '2026-04-29T12:00:00Z'
        '429':
          description: Rate limit exceeded
          content:
            application/json:
              example:
                success: false
                error:
                  code: RATE_LIMIT_EXCEEDED
                  message: Rate limit exceeded. Try again later.
                meta:
                  version: '2.0'
                  timestamp: '2026-04-29T12:00:00Z'
      security:
        - ApiKeyAuth: []
components:
  securitySchemes:
    ApiKeyAuth:
      type: apiKey
      in: header
      name: X-API-Key
      description: Your BackQuant API key (same key as v1)

````