WebSocket API

Real-time market data and account updates via WebSocket.

Connection

EnvironmentURL
Testnetwss://ws.testnet.rise.trade/ws
Mainnetwss://ws.rise.trade/ws

Authentication

Authentication is required before subscribing to private channels (orders, positions). Public channels (orderbook) can be subscribed without authentication.

Authentication Request

{
  "method": "auth",
  "params": {
    "account": "0x1234567890123456789012345678901234567890",
    "signer": "0xabcdefabcdefabcdefabcdefabcdefabcdefabcd",
    "message": "Please sign in with your wallet to access rise.trade. You are signing in on 2025-01-15 12:00:00 (GMT). This message is exclusively signed with rise.trade for security.",
    "nonce": 1736942400,
    "signature": "0x..."
  }
}
ParameterTypeRequiredDescription
accountstringYesYour main Ethereum wallet address
signerstringYesSession key address (must be registered on-chain)
messagestringYesHuman-readable message that was signed
noncenumberYesUnix timestamp in seconds (must be within ±60 seconds of server time)
signaturestringYesEIP-712 signature in hex format

Authentication Response

Success:

{
  "method": "auth",
  "status": "success",
  "message": "Authentication successful",
  "data": {
    "account": "0x1234567890123456789012345678901234567890",
    "signer": "0xabcdefabcdefabcdefabcdefabcdefabcdefabcd"
  }
}

Error:

{
  "method": "auth",
  "status": "error",
  "message": "session key not active (status: 0)"
}

Subscription Format

Subscribe

{
  "method": "subscribe",
  "params": {
    "channel": "<channel_name>",
    "market_ids": [1, 2],
    "makers": ["0x..."]
  }
}
ParameterTypeRequiredDescription
channelstringYesChannel name: orders, orderbook, positions, trades, or oracle
market_idsnumber[]NoFilter by market IDs. Empty or omitted = all markets
makersstring[]NoFilter by account addresses. Empty or omitted = all accounts

Unsubscribe

{
  "method": "unsubscribe",
  "params": {
    "channel": "<channel_name>"
  }
}

Subscription Response

{
  "method": "subscribe",
  "status": "success",
  "message": "Subscribed to orders",
  "channel": "orders",
  "data": {
    "market_ids": [1, 2],
    "makers": ["0x1234567890123456789012345678901234567890"]
  }
}

Available Channels

ChannelAuth RequiredDescriptionFilters
orderbookNoReal-time orderbook updates with snapshotsmarket_ids
tradesNoEvery trade as it is matchedmarket_ids
oracleNoMark and index prices, once per blockmarket_ids
ordersYesReal-time order updates with snapshotsmarket_ids, makers
positionsYesReal-time position updates with snapshotsmarket_ids, makers
fundingYesFunding payments as they settlemarket_ids, makers
fillsYesYour own fills, always scoped to your accountmarket_ids

Message Types

Channel data carries a type field: snapshot (full state at subscription time) or update (incremental change).

Replies to your own requests are shaped differently and carry a status field instead — including one trap worth knowing: a rejected subscribe still comes back as "type": "subscribed" with "status": "error". See Messages for every envelope shape.

Common Fields

Channel messages share one envelope:

FieldTypePresent onDescription
channelstringevery messageChannel name
typestringevery messagesnapshot or update
market_idstringupdatesMarket ID. Omitted on orders / positions snapshots, null on oracle
dataarray | objectevery messageChannel-specific payload
block_numbernumberupdatesBlock that produced the event
log_indexnumberupdatesLog index within that block
tx_hashstringupdates, when the event came from a transactionTransaction hash. positions updates do not carry one
worker_timestampstringevery messageServer time in nanoseconds when the message was built

Snapshots add method: "snapshot" plus a count field: level_count (orderbook), order_count (orders), position_count (positions).

🚧

There is no timestamp and no block_timestamp

Older revisions of this page listed both. Neither is on the wire — the only server clock in a channel message is worker_timestamp, in nanoseconds. Block time must be read from the REST API by block_number.

Re-subscription Behavior

Re-subscribing to the same channel replaces the previous subscription filters. To receive events from multiple markets, specify all market IDs in a single subscription.

Price and Size Format

Numbers are strings on every channel, but the scale is not the same everywhere:

ChannelFormatExample
orderbook, trades, orders, positions, fills, fundingDecimal, human-readable"63250.4", "0.00079"
oracleInteger wei (18 decimals)"63126084821834306372811"

Do not divide a decimal channel by 1018orderbook and oracle quote the same market in different scales in the same session.

Market IDs

Market IDSymbol
1BTC-PERP
2ETH-PERP

Error Handling

{
  "method": "subscribe",
  "status": "error",
  "message": "authentication required",
  "channel": "orders"
}

Health Checks

The server sends ping messages every 30 seconds. Respond with pong to keep the connection alive. Connections timeout after 60 seconds of inactivity.