Exchange Wire Formats

Hyperliquid Futures wire format

How Hyperliquid perpetuals messages become rows in our Parquet files. Each data type below shows a real message next to the rows we publish for it, with the source and the rule for every column. Hover a line or a column to see how they connect.

Checked against our pipeline

These messages were captured from Hyperliquid perpetuals on 2026-10-05. Our test suite replays each one through the production collector parser and postprocessor, and fails if the published rows differ from the rows on this page. Files written before a change to the pipeline can differ; see Known Gaps & Corrections.

The collector covers every listed perpetual market, including builder-deployed dexes, whose coins carry a dex prefix such as xyz:XYZ100. All examples use BTC.

  • Public WebSocket: wss://api.hyperliquid.xyz/ws
  • Info REST (market metadata): https://api.hyperliquid.xyz/info

Exchange API reference: hyperliquid.gitbook.io. Conventions shared by every exchange are on the wire formats overview.

Trades

One row per fill from the trades subscription for each coin.

  • WebSocket trades

Trade

WebSocket message · tradesreceived 2026-10-05 19:16:37.523305 UTC
{
"channel": "trades",
"data": [
{
"coin": "BTC",
"side": "A",
"px": "85628.0",
"sz": "0.00046",
"time": 1791227797187,
"hash": "0x2e861874c0b73d972fff0445ea12f4020157005a5bba5c69d24ec3c77fbb1781",
"tid": 910713520736797,
"users": ["0x368a9c423d0ce3d9887950125b1db4bb306c1b7d", "0x2332a66e6bdf9606d2fd63eed619357536612d4d"]
}
]
}

Published row

received_time1791227797523305000—Our collector's clock when the message arrived, in nanoseconds since the Unix epoch. Not sent by Hyperliquid.
event_time1791227797187data[].timeCopied. Milliseconds. Hyperliquid sends one time per trade, so event_time equals trade_time.
symbolBTCdata[].coinCopied. Main-dex coins are uppercased (kPEPE is published as KPEPE); builder-dex coins such as xyz:XYZ100 keep their case.
trade_id910713520736797data[].tidCopied. Hyperliquid's tid is a hash of the buyer's and seller's order IDs, not a sequence number: it does not increase and cannot reveal gaps.
price85628.0data[].pxCopied as the exact decimal string Hyperliquid sent.
quantity0.00046data[].szCopied as the exact decimal string. Base asset units.
trade_time1791227797187data[].timeCopied. Milliseconds.
is_buyer_makertruedata[].sideside is the aggressor: A (ask, seller aggressed) gives true, B (bid, buyer aggressed) gives false.
order_typemarket—Always market. Hyperliquid does not send an order type; the constant marks the row as a taker fill.

One taker order, several fills

A taker order that fills against several resting orders arrives as one message with one element per fill.

Abridged: The message held 39 fills; the first three are shown.

WebSocket message · tradesreceived 2026-10-05 19:16:39.732583 UTC
{
"channel": "trades",
"data": [
{
"coin": "BTC",
"side": "B",
"px": "85629.0",
"sz": "0.0009",
"time": 1791227799116,
"hash": "0x55b2f804bb3995b3572c0445ea130d02030200ea563cb485f97ba3577a3d6f9d",
"tid": 590087756771268,
"users": ["0xe60a6f40ad907263441fe89236bb67b1a47683dc", "0x4c6988b39fc0904628c2959e7606ef5f8518c152"]
},
{
"coin": "BTC",
"side": "B",
"px": "85629.0",
"sz": "0.00064",
"time": 1791227799116,
"hash": "0x55b2f804bb3995b3572c0445ea130d02030200ea563cb485f97ba3577a3d6f9d",
"tid": 775060480000248,
"users": ["0xe60a6f40ad907263441fe89236bb67b1a47683dc", "0x338e1b3dbdd72c6601a99e34f2ec6881b89d9c8d"]
},
{
"coin": "BTC",
"side": "B",
"px": "85629.0",
"sz": "0.00064",
"time": 1791227799116,
"hash": "0x55b2f804bb3995b3572c0445ea130d02030200ea563cb485f97ba3577a3d6f9d",
"tid": 146242069110799,
"users": ["0xe60a6f40ad907263441fe89236bb67b1a47683dc", "0xf86a91bda299b36c7d4fc8a7b57f5e32c34e748f"]
}
]
}

Published rows · 3

received_time1791227799732583000—Our collector's clock when the message arrived, in nanoseconds since the Unix epoch. Not sent by Hyperliquid.
event_time1791227799116data[].timeCopied. Milliseconds. Hyperliquid sends one time per trade, so event_time equals trade_time.
symbolBTCdata[].coinCopied. Main-dex coins are uppercased (kPEPE is published as KPEPE); builder-dex coins such as xyz:XYZ100 keep their case.
trade_id590087756771268data[].tidCopied. Hyperliquid's tid is a hash of the buyer's and seller's order IDs, not a sequence number: it does not increase and cannot reveal gaps.
price85629.0data[].pxCopied as the exact decimal string Hyperliquid sent.
quantity0.0009data[].szCopied as the exact decimal string. Base asset units.
trade_time1791227799116data[].timeCopied. Milliseconds.
is_buyer_makerfalsedata[].sideside is the aggressor: A (ask, seller aggressed) gives true, B (bid, buyer aggressed) gives false.
order_typemarket—Always market. Hyperliquid does not send an order type; the constant marks the row as a taker fill.

Notes

  • hash and users (buyer and seller addresses) are not published. Some fills carry an all-zero hash.
  • One message can hold several fills of one taker order (same time, side and hash); each fill is its own row with its own tid.
  • After every subscribe, Hyperliquid first sends the market's most recent trades (about 30), however old, without marking them as a replay. On a reconnect the collector drops replayed trades it already wrote. The postprocessor drops trades timed more than 5 seconds before the start of the file's hour, exact duplicates, and trades already published in an earlier hour.
  • Before the 2026-09 data-integrity release, a replayed trade could be published again in a later hour's file. Deduplicate older history on (symbol, trade_id, trade_time): Hyperliquid documents tid as unique only together with the coin and the time.

Column types and descriptions: Trades schema.

Order Book

One row per price level of each l2Book snapshot.

  • WebSocket l2Book

Every l2Book message is a full snapshot of the top of the book, not a delta. Each one becomes one snapshot row per level.

Abridged: Hyperliquid sent 20 bid and 20 ask levels; the best 3 of each are shown.

WebSocket message · l2Bookreceived 2026-10-05 19:16:37.268427 UTC
{
"channel": "l2Book",
"data": {
"coin": "BTC",
"time": 1791227796735,
"levels": [
[
{
"px": "85628.0",
"sz": "5.71229",
"n": 19
},
{
"px": "85627.0",
"sz": "0.005",
"n": 1
},
{
"px": "85626.0",
"sz": "0.75919",
"n": 1
}
],
[
{
"px": "85629.0",
"sz": "4.37963",
"n": 39
},
{
"px": "85630.0",
"sz": "0.58198",
"n": 23
},
{
"px": "85631.0",
"sz": "3.85701",
"n": 9
}
]
]
}
}

Published rows · 6

received_time1791227797268427000—Our collector's clock when the message arrived, in nanoseconds since the Unix epoch. Not sent by Hyperliquid.
event_time1791227796735data.timeCopied. Milliseconds.
transaction_time1791227796735data.timeCopied from the same time. Milliseconds.
symbolBTCdata.coinCopied. Main-dex coins are uppercased (kPEPE is published as KPEPE); builder-dex coins such as xyz:XYZ100 keep their case.
event_typesnapshot—snapshot for every l2Book message.
first_update_idnull—Null. Hyperliquid books carry no update IDs.
final_update_id1791227796735data.timeThe snapshot's time. Hyperliquid has no update ID, so the time identifies the snapshot.
prev_final_update_idnull—Null. Snapshots do not chain.
last_update_id1791227796735data.timeThe snapshot's time, as in final_update_id.
sidebiddata.levels[0]data.levels[1]bid for levels in levels[0], ask for levels in levels[1]. One row per level.
price85628.0data.levels[0][].pxdata.levels[1][].pxCopied as the exact decimal string.
quantity5.71229data.levels[0][].szdata.levels[1][].szCopied as the exact decimal string: the total resting size at that price. Base asset units.
order_count19data.levels[0][].ndata.levels[1][].nCopied. Number of resting orders at that price.

Notes

  • Each snapshot replaces the whole book: rebuild your book from the rows of each final_update_id. A snapshot holds at most 20 levels per side at full price precision. Hyperliquid documents at most one push per 0.5 seconds; in October 2026 a market's snapshots arrive about every 5.4 seconds (about 670 per hour).
  • A snapshot with no levels on either side publishes one row with side noop and price and quantity 0, which clears the book. Files written before the October 2026 pipeline update have no row for an empty snapshot.
  • A snapshot holding a level with a zero, negative or unparsable price or size is withheld whole instead of being published as a partial book. Before the October 2026 pipeline update such a snapshot could be published as a partial or empty book.
  • Files can start with a checkpoint snapshot of the book carried over from the previous hour: its received_time is the hour start, transaction_time is null, and event_time, final_update_id and last_update_id are the time of the snapshot the book came from.

Column types and descriptions: Order Book schema.

Mark Price

One row per market per allDexsAssetCtxs message.

  • WebSocket allDexsAssetCtxs

One allDexsAssetCtxs subscription covers every perpetual market on every dex. The message has no market names: each dex's array is in the order of the allPerpMetas universe, which the collector reads at startup and on every symbol refresh to name each entry. Delisted markets are skipped.

Abridged: The frame carried 534 markets across 11 perp dexes; only BTC, the first market of the main dex "", is shown. The collector splits every frame into one record per market.

WebSocket message · allDexsAssetCtxsreceived 2026-10-05 19:16:37.959116 UTC
{
"channel": "allDexsAssetCtxs",
"data": {
"ctxs": [
[
"",
[
{
"funding": "0.0000125",
"openInterest": "38976.50654",
"prevDayPx": "85366.0",
"dayNtlVlm": "2807065618.8274302483",
"premium": "-0.0001214394",
"oraclePx": "85639.4",
"markPx": "85623.0",
"midPx": "85628.5",
"impactPxs": ["85628.0", "85629.0"],
"dayBaseVlm": "32630.96689"
}
]
]
]
}
}

Published row

received_time1791227797959116000—Our collector's clock when the message arrived, in nanoseconds since the Unix epoch. Not sent by Hyperliquid.
event_time1791227797959—Our receive clock in milliseconds (received_time / 1,000,000). Asset contexts carry no exchange timestamp.
symbolBTCdata.ctxs[0][0]The market at this position of the dex's array in Hyperliquid's allPerpMetas metadata: BTC is the first market of the main dex "". Main-dex coins are uppercased; builder-dex coins such as xyz:XYZ100 keep their case.
mark_price85623.0data.ctxs[0][1][0].markPxCopied.
index_price85639.4data.ctxs[0][1][0].oraclePxCopied from oraclePx, the oracle price. For main-dex markets Hyperliquid computes it as a weighted median of prices on centralized exchanges.
estimated_settle_pricenull—Null. Hyperliquid perpetuals do not settle.
funding_rate0.0000125data.ctxs[0][1][0].fundingCopied. A fraction per hour: Hyperliquid pays funding every hour, and 0.0000125 is 0.00125 % per hour.
next_funding_timenull—Null. Hyperliquid does not send it; funding is paid every hour.

Notes

  • Hyperliquid does not document how often it pushes allDexsAssetCtxs. In October 2026 a push arrives about every 15 seconds, so a market has about 240 rows per hour. Every push becomes a row, whether or not a value changed.
  • The 24h fields (prevDayPx, dayNtlVlm, dayBaseVlm), midPx, premium and impactPxs are not published.
  • Files written before the October 2026 pipeline update have event_time in nanoseconds (the receive clock, equal to received_time). Divide those values by 1,000,000.

Column types and descriptions: Mark Price schema.

Open Interest

One row per market per allDexsAssetCtxs message, from the same entries as mark price.

  • WebSocket allDexsAssetCtxs

One allDexsAssetCtxs subscription covers every perpetual market on every dex. The message has no market names: each dex's array is in the order of the allPerpMetas universe, which the collector reads at startup and on every symbol refresh to name each entry. Delisted markets are skipped.

Abridged: The frame carried 534 markets across 11 perp dexes; only BTC, the first market of the main dex "", is shown. The collector splits every frame into one record per market.

WebSocket message · allDexsAssetCtxsreceived 2026-10-05 19:16:37.959116 UTC
{
"channel": "allDexsAssetCtxs",
"data": {
"ctxs": [
[
"",
[
{
"funding": "0.0000125",
"openInterest": "38976.50654",
"prevDayPx": "85366.0",
"dayNtlVlm": "2807065618.8274302483",
"premium": "-0.0001214394",
"oraclePx": "85639.4",
"markPx": "85623.0",
"midPx": "85628.5",
"impactPxs": ["85628.0", "85629.0"],
"dayBaseVlm": "32630.96689"
}
]
]
]
}
}

Published row

received_time1791227797959116000—Our collector's clock when the message arrived, in nanoseconds since the Unix epoch. Not sent by Hyperliquid.
symbolBTCdata.ctxs[0][0]The market at this position of the dex's array in Hyperliquid's allPerpMetas metadata: BTC is the first market of the main dex "". Main-dex coins are uppercased; builder-dex coins such as xyz:XYZ100 keep their case.
sum_open_interest38976.50654data.ctxs[0][1][0].openInterestCopied. Base asset units (BTC for BTC).
sum_open_interest_valuenull—Null. Hyperliquid does not send an open interest value; multiply by mark_price for a notional.
timestamp1791227797959—Our receive clock in milliseconds (received_time / 1,000,000). Asset contexts carry no exchange timestamp.

Notes

  • Negative or unparsable open interest values are not published; the mark price row of the same entry still is.
  • Files written before the October 2026 pipeline update have timestamp in nanoseconds (the receive clock, equal to received_time). Divide those values by 1,000,000.

Column types and descriptions: Open Interest schema.

Not published

  • Ticker: Hyperliquid has no 24h ticker channel; the 24h fields of the asset contexts are not published.
  • Liquidations: Hyperliquid has no public liquidation stream.