Skip to main content

Hyperliquid Order Book API (L3)

Get the full Hyperliquid order book at order level, with the order id and wallet behind every change. This page covers the Orders, BookUpdates and Twaps cubes: the full order lifecycle, order-book deltas you can rebuild the book from, and TWAP order execution.

Data window

Orders and BookUpdates keep a rolling ~7 days of row-level data on the API; Twaps and Trades keep ~30 days. A query for an older date returns [] with HTTP 200, not an error. Data Store exports carry order and book updates older than the API window; the Blockchain Data Lake holds the raw HyperCore feed from 17 July 2026, which you decode and parse your own way. Per-cube windows: Data Coverage & Retention.

L2 vs L3: what you get here​

Most order-book feeds — including Hyperliquid's own public l2Book websocket channel and the L2 snapshots in its s3://hyperliquid-archive bucket — are L2: resting size aggregated per price level. You see that 40 BTC sits at $95,000. You cannot see whether that is one order or twenty, whose it is, or which one was pulled a moment later.

BookUpdates is L3 (market-by-order). Every delta is a single order, and it carries:

L2 (aggregated)L3 (market-by-order) — Bitquery
GrainTotal size per price levelOne event per individual order
Order identity—Oid, joinable to Orders and Trades
Who placed it—Trader { Address } — the wallet itself
Size changeNet level change onlySize and SizeBefore on that specific order
DepthHyperliquid's l2Book returns 5–20 levelsUnlimited

Because Hyperliquid settles on a transparent L1, the wallet behind each order is public. That makes this L3 with named attribution — something that does not exist on centralised venues, where L3 feeds are anonymised by the exchange. Hyperliquid's own API exposes order-level detail only per address (orderUpdates, userFills for an address you already know, at most 10 users per IP); market-wide, it serves aggregated L2.

This is what makes wallet-level analysis possible: watching a market maker quote and pull, reconstructing a trader's full order flow rather than just their fills, or spotting orders that were never intended to trade. See Track Hyperliquid Order Flow by Wallet for worked examples.

API Key Required

To query or stream data outside the Bitquery IDE, you need an API access token.

Follow the steps here: How to generate Bitquery API token ➤

Set the time window

A query on Orders or BookUpdates without a Block: {Time: ...} filter covers only the last 30 minutes — set the window explicitly for anything longer, and add a market filter (Market: {CoinRaw: ...}) when you look back more than an hour or two.

Order updates​

Every order event carries Status, OrderType (Limit, Market, Stop Market, Stop Limit, Take Profit Market, Take Profit Limit, Trailing Stop Market), time-in-force Tif (Alo, Ioc, Gtc, FrontendMarket, LiquidationMarket; empty on a trigger order that has not fired), the limit price, the current and original size, and trigger settings for conditional orders.

Status is open, filled, canceled, triggered, or a specific reason such as badAloPxRejected, iocCancelRejected, perpMarginRejected, reduceOnlyCanceled or selfTradeCanceled. IsReject is true on every rejected status — rejects are a large share of the feed, and public APIs drop them.

Run it in the IDE: Hyperliquid Recent Orders ➤

query {
Hyperliquid {
Orders(
limit: {count: 50}
orderBy: {descending: [Block_Time, Order_Index]}
where: {Block: {Time: {since_relative: {minutes_ago: 1}}}}
) {
Block { Time }
Order {
Market { Symbol Kind }
Index Oid Status IsReject OrderType Tif Side LimitPx Size OrigSz
IsTrigger TriggerPx TriggerCondition ReduceOnly Cloid
Trader { Address }
}
}
}
}
  • Oid links order events to fills (Trade.Execution.Oid) and book updates (BookUpdate.Oid); Cloid is the client-assigned order id.
  • Index is the status update's place in its block, from 1. All updates of a block share Block.Time (and EventTime), so Index is the only way to put them in order — for example several statuses of one order in the same block. Rows written before about 09:40 UTC on 2026-10-13 have Index 0.
  • Size is the remaining size, OrigSz the original size.
  • IsTrigger, TriggerPx, TriggerCondition describe stop / take-profit orders; IsPositionTpsl marks position-attached TP/SL.

Real-time order stream​

Run it in the IDE: Hyperliquid Orders Stream ➤

subscription {
Hyperliquid {
Orders(where: {Order: {Market: {Symbol: {is: "ETH"}}}}) {
Block { Time }
Order {
Market { Symbol }
Index Oid Status OrderType Tif Side LimitPx Size OrigSz IsTrigger ReduceOnly
Trader { Address }
}
}
}
}

Order book updates​

BookUpdates streams deltas of the on-chain order book, one per order. Kind is new (order added to the book), update (its resting size changed, e.g. a partial fill) or remove (order left the book: canceled or fully filled); with Px, Size (size after the change, empty on remove), SizeBefore (on update), the order Oid and the trader behind the order. Consume the stream and apply the deltas in (Block.Number, Index) order to maintain a live book — Index is the delta's place in its block, and every delta of a block shares Block.Time.

Run it in the IDE: Hyperliquid Order Book Stream ➤

subscription {
Hyperliquid {
BookUpdates(where: {BookUpdate: {Market: {Symbol: {is: "BTC"}}}}) {
Block { Number Time }
BookUpdate {
Index Kind Side Px Size SizeBefore Oid
Market { Symbol }
Trader { Address }
}
}
}
}

This is the L3 grain described above: unlike an aggregated L2 feed, each delta is attributable to an individual order and trader address — you can watch a specific market maker's quoting in real time by filtering on BookUpdate: {Trader: {Address: {is: "0x..."}}}.

The whole book at a snapshot​

SnapshotOrders lists the entire book, order by order with its owner and its place in the queue (QueuePosition), at each snapshot, about every 12.5 minutes, kept 7 days: a starting point for a book you then keep with BookUpdates. It also lists every waiting trigger order (IsTrigger: true), stop-losses and take-profits that are not in the book yet and so never appear in BookUpdates until they fire. See the stop-loss and take-profit map.

TWAP orders​

Twaps tracks the lifecycle of TWAP orders: State.Status moves from activated (or waitingForTrigger) to finished, terminated, stopped or error (StatusError carries the reason), with executed size and notional so far.

Run it in the IDE: Hyperliquid TWAP Orders ➤

query {
Hyperliquid {
Twaps(limit: {count: 50}, orderBy: {descending: Block_Time}) {
Block { Time }
Twap {
TwapId
Market { Symbol }
Order { Side Size ReduceOnly Randomize }
Interval { DurationMinutes StartTime EventTime }
State { Status StatusError ExecutedSize ExecutedNotional }
Trader { Address }
}
}
}
}

TwapId matches Trade.TwapId on fills with IsTwap: true, so you can join a TWAP to its individual child fills. Hyperliquid TWAP Orders & Child Fills walks through that join, with per-wallet TWAP history and an execution summary.

Build with Bitquery

Ready to run this in production?

Get an API key and run these queries in minutes, or talk to us about plans and enterprise delivery.