How Big Is the OPRA Options Quote Feed?
How big is the options quote feed? We count one full day of OPRA-scale NBBO updates in our warehouse and measure it against the entire stock quote tape.
The options quote feed is the largest stream of market data in the US: every listed option contract carries its own best bid and best ask, and OPRA — the Options Price Reporting Authority, the consolidated tape for US listed options — publishes every update to every one of them. On 2026-07-02, a single ordinary session, our warehouse recorded 10.89 billion options quote updates — 18.2 times the size of the same day's entire stock quote tape. This page measures the firehose directly, with the exact query behind every number attached.
Why is the options quote feed so big?
A stock has one national best bid and offer — one bid-ask spread to keep current. An option chain multiplies that: each listed contract — every combination of expiration date, strike price, and call-or-put — quotes its own NBBO. On 2026-07-02, SPY alone kept 9236 distinct contracts quoting, counting its 2026 expiries only.
The multiplication does not stop at the contract count. An option's value moves with its underlying stock, and when the share price ticks, market makers refresh quotes across the chain — every strike, every expiry, at once, whether or not anyone trades those contracts. That is the shape of the arithmetic measured below: quote updates in the billions per session, and 828 quote updates for every executed options trade.
One day of the options tape, counted
How much data is that in practice? The panel below counts every options quote update our warehouse stored for 2026-07-02 — the most recent completed session at least five calendar days back, a rule explained in the scarcity section — and sets it against the same session's full stock quote tape, the same head-to-head the July 7 market recap ran on its Monday tape. Both counts cover the full calendar day, bounded in universal time (UTC), which spans the entire US options session.
The exact SQL behind every number
WITH (
SELECT max(toDate(toTimeZone(window_start, 'America/New_York')))
FROM global_markets.delayed_stocks_minute_aggs
WHERE ticker = 'SPY'
AND window_start >= toDateTime(today() - 10)
AND window_start < toDateTime(today() - 4)
) AS session_day,
(
SELECT (count(), uniqExact(ticker))
FROM global_markets.cache_stocks_quotes
WHERE sip_timestamp >= toDateTime(session_day)
AND sip_timestamp < toDateTime(session_day + 1)
) AS stock_tape,
(
SELECT (count(), uniqExact(ticker))
FROM global_markets.options_trades
WHERE sip_timestamp >= toDateTime(session_day)
AND sip_timestamp < toDateTime(session_day + 1)
) AS option_trades_t,
(
SELECT toUInt32(max(sip_timestamp)) - toUInt32(min(sip_timestamp))
FROM global_markets.cache_options_quotes
WHERE ticker >= 'O:SPY26' AND ticker < 'O:SPY27'
AND sip_timestamp >= toDateTime(session_day)
AND sip_timestamp < toDateTime(session_day + 1)
) AS spy_span_seconds
SELECT
toString(session_day) AS session_date,
round(count() / 1e9, 2) AS option_quote_updates_bn,
round(stock_tape.1 / 1e6, 0) AS stock_quote_updates_m,
stock_tape.2 AS stock_symbols_quoted,
round(count() / stock_tape.1, 1) AS option_to_stock_ratio,
round(option_trades_t.1 / 1e6, 1) AS option_trades_m,
round(option_trades_t.2 / 1e3, 0) AS option_contracts_traded_k,
round(count() / option_trades_t.1, 0) AS quote_updates_per_trade,
round(count() / spy_span_seconds / 1e3, 0) AS avg_updates_per_second_k
FROM global_markets.cache_options_quotes
WHERE sip_timestamp >= toDateTime(session_day)
AND sip_timestamp < toDateTime(session_day + 1)The whole options tape came to 10.89 billion NBBO updates. Only 374 thousand distinct contracts actually TRADED that day — the quote stream reprices vastly more of the chain than ever changes hands. The same day's stock tape — every consolidated quote update for every listed stock and ETF, premarket and after-hours included — measured 597 million updates across 12893 symbols. The ratio is the headline: the options quote stream ran 18.2 times the size of the stock quote stream.
Two more readings from the same scan give the feed its texture. Averaged across the session's quoting span (measured on SPY's chain, the deepest on the tape), updates arrived at 448 thousand per second. And the options market printed 13.1 million actual trades that day — 828 quote updates for every one of them. Quoting, not trading, is what fills the pipe.
One root's slice: SPY's option chain in a day
A whole-tape number is hard to feel, and the whole tape is also expensive to scan — so cut one slice. The panel below counts every quote update for SPY option contracts expiring in 2026, over the same session and the same UTC-bounded day: one underlying's chain, carved out of the firehose by a ticker range.
The exact SQL behind every number
WITH (
SELECT max(toDate(toTimeZone(window_start, 'America/New_York')))
FROM global_markets.delayed_stocks_minute_aggs
WHERE ticker = 'SPY'
AND window_start >= toDateTime(today() - 10)
AND window_start < toDateTime(today() - 4)
) AS session_day
SELECT
toString(session_day) AS session_date,
round(count() / 1e6, 1) AS spy_quote_updates_m,
uniqExact(ticker) AS spy_contracts_quoted,
round(count() / uniqExact(ticker) / 1e3, 1) AS avg_updates_per_contract_k,
uniqExactIf(ticker, substring(ticker, 6, 6) = formatDateTime(session_day, '%y%m%d')) AS same_day_expiry_contracts,
round(100.0 * countIf(substring(ticker, 6, 6) = formatDateTime(session_day, '%y%m%d')) / count(), 1) AS same_day_expiry_pct_of_updates,
quantileExactWeightedIf(0.5)(toInt32(round(toFloat64(ask_price - bid_price) * 100)), 1, bid_price > 0 AND ask_price >= bid_price AND substring(ticker, 6, 6) = formatDateTime(session_day, '%y%m%d')) AS same_day_median_width_cents,
quantileExactWeightedIf(0.5)(toInt32(round(toFloat64(ask_price - bid_price) * 100)), 1, bid_price > 0 AND ask_price >= bid_price) AS all_spy_median_width_cents,
round(countIf(NOT (bid_price > 0 AND ask_price >= bid_price)) / 1e3, 0) AS dropped_invalid_quotes_k,
formatDateTime(toTimeZone(min(sip_timestamp), 'America/New_York'), '%H:%i') AS spy_first_quote_et,
formatDateTime(toTimeZone(max(sip_timestamp), 'America/New_York'), '%H:%i') AS spy_last_quote_et,
toHour(toTimeZone(min(sip_timestamp), 'America/New_York')) * 60 + toMinute(toTimeZone(min(sip_timestamp), 'America/New_York')) AS spy_first_quote_et_minute,
toHour(toTimeZone(max(sip_timestamp), 'America/New_York')) * 60 + toMinute(toTimeZone(max(sip_timestamp), 'America/New_York')) AS spy_last_quote_et_minute
FROM global_markets.cache_options_quotes
WHERE ticker >= 'O:SPY26' AND ticker < 'O:SPY27'
AND sip_timestamp >= toDateTime(session_day)
AND sip_timestamp < toDateTime(session_day + 1)One underlying produced 471.7 million options quote updates in a single day: 9236 contracts quoting, an average of 51.1 thousand updates per contract. For scale, the entire stock tape in the panel above — every listed share and ETF combined — measured 597 million updates that session.
Same-day expiries tell the sharper story. 0DTE options — contracts trading on their own expiration day — dominate options trading, and the parsed table further down shows every one of the session's five busiest SPY contracts expiring that same day. In the quote stream they are a sliver: the 410 same-day contracts accounted for 5.3% of SPY's quote updates. Market makers keep the entire chain priced — December's strikes update all session long whether anyone trades them or not.
Width is the other measurement worth taking here. Among those same-day SPY contracts, the median quoted width — ask minus bid, taken across every valid NBBO update — measured 3¢; across the full 2026-expiry chain the same median measured 4¢. (270 thousand one-sided or crossed updates were excluded from the width medians and counted in the panel.)
How to read an option ticker (OCC symbology)
Every contract in these panels is identified by an OCC option symbol — the standard format administered by the Options Clearing Corporation. Our warehouse prefixes it with O:. Take O:SPY261218C00700000 as a worked example:
- Root —
SPY: the option root, up to six characters, usually the underlying's own ticker. - Expiration —
261218: the expiry date as YYMMDD — December 18, 2026. - Type —
Cfor a call,Pfor a put. - Strike —
00700000: the strike price multiplied by 1,000 and zero-padded to eight digits — $700.00.
That fixed format is what lets one root's chain be carved out with a plain ticker range: every SPY contract expiring in 2026 sorts between O:SPY26 and O:SPY27, the exact filter in the panel above. Here are the session's five busiest SPY contracts with the symbol unpacked:
The exact SQL behind every number
WITH (
SELECT max(toDate(toTimeZone(window_start, 'America/New_York')))
FROM global_markets.delayed_stocks_minute_aggs
WHERE ticker = 'SPY'
AND window_start >= toDateTime(today() - 10)
AND window_start < toDateTime(today() - 4)
) AS session_day
SELECT ticker AS occ_ticker,
any(underlying_symbol) AS root,
concat('20', substring(ticker, 6, 2), '-', substring(ticker, 8, 2), '-', substring(ticker, 10, 2)) AS expiry_parsed,
if(any(option_type) = 'C', 'call', 'put') AS call_or_put,
any(toFloat64(strike_price)) AS strike_usd,
round(sum(size) / 1e3, 1) AS contracts_traded_k,
if(substring(ticker, 6, 6) = formatDateTime(session_day, '%y%m%d'), 1, 0) AS expires_same_day
FROM global_markets.options_trades
WHERE sip_timestamp >= toDateTime(session_day)
AND sip_timestamp < toDateTime(session_day + 1)
AND ticker >= 'O:SPY26' AND ticker < 'O:SPY27'
GROUP BY ticker
ORDER BY contracts_traded_k DESC, ticker
LIMIT 5The top of the volume table is pure same-day traffic: all five contracts expired on 2026-07-02, the session's own date, and the busiest of them — O:SPY260702P00740000, a $740-strike put contract — traded 540.4 thousand contracts. Set that against the quote panel before it: trading concentrates at the front of the chain, quoting spreads across all of it.
Why options quote data is scarce
Storing this feed means adding a day like the one measured above — every session, indefinitely. That is the economics in one line. Most market-data products, retail and professional alike, carry stock prices and sometimes options trades; full options quote history is rare on any shelf, at any price. Our own warehouse holds equity quote history back to 2003 and options trade history back to 2014, while the options quote table starts in 2022 — the youngest tick history we keep, and by a wide margin the largest table we operate.
One disclosure belongs in plain sight: options quotes are also the slowest-arriving dataset we hold. New sessions typically land a day or two behind the calendar — sometimes more — while equity quotes usually settle within a day. Every panel on this page anchors to the most recent completed session at least five calendar days back (2026-07-02 in the current run), and the weekly refresh re-runs every query on that same rule, keeping each number measured over a fully ingested day rather than a half-loaded front edge.
FAQ
How big is the OPRA options feed per day?
Measured in our warehouse: 10.89 billion options quote updates on 2026-07-02 — an average of 448 thousand updates per second across the session's quoting span. The raw OPRA feed carries trade and administrative messages on top of quotes, and its official message counts run higher still.
Is the options quote feed bigger than the stock quote feed?
Yes — by multiples, not by percent. On the session measured above, options quote updates ran 18.2 times the count of stock quote updates: 10.89 billion against 597 million. Each stock keeps one NBBO current; its option chain keeps hundreds or thousands.
Why is options market data so expensive?
Scale is the visible part: a feed measured in billions of updates per session takes real infrastructure to receive, store, and query, and the bill repeats every trading day. Exchange licensing fees sit on top of the engineering. The panels above show exactly what a full options quote dataset has to carry.
How many option contracts quote on a normal day?
More than trade, by a wide margin. On 2026-07-02, 374 thousand distinct contracts printed at least one trade, while SPY's 2026-expiry chain alone kept 9236 contracts quoting — and the full quoted universe spans every root the way SPY's chain spans its strikes. (Counting every distinct contract in a day's quote stream is itself a scan so large we keep it out of a weekly-refreshed page — the one number here we deliberately do not publish.)
Do options quote after hours?
Listed US equity options keep exchange hours. In the session measured above, SPY's first option quote landed at 09:30 ET and its last at 16:15 ET — no overnight session. The stock tape, for comparison, quotes through premarket and after-hours.
Every panel above ships with the exact SQL that produced it — expand one, swap in a different root or day, and size the slice of the feed you actually trade on the Strasmore terminal.