Room ID:
Endpoint:
Rate: 0.1 credits per message
polymarket_trader_pnl Endpoint:
wss://api.struct.to/ws Rate: 0.1 credits per message
global (the whole portfolio), market (per condition), and category (per market category). Each grain is tracked over four windows: 1d, 7d, 30d, and lifetime.
Event families
Each grain emits three families of events. A given dirty row goes to exactly one family per block, so the families are disjoint.
Updates are batched per block. Each envelope is shaped
{ type, room_id, block, [timeframe,] data: [ ...rows ] }, with one envelope per grain, family, and (for full-row batches) timeframe per block. Empty batches are not sent. Every row carries a dirty_kinds array naming what triggered it.
Tick and resolution rows are window-agnostic and carry boundary snapshots, so any per-window delta is recoverable client-side without waiting for a full-row batch.
dirty_kinds
Subscribe
Thetraders filter is required. The remaining filters are optional and narrow the stream.
Filters
An unknown value in
update_types, timeframes, or dirty_kinds rejects the whole subscription with an error.
Example
Response
The subscribe response (trader_pnl_stream_subscribe_response) echoes the resolved configuration.
Events
trader_global_pnl_batch
Full-row PnL across the whole portfolio. Carries a top-level timeframe.
trader_market_pnl_batch
Full-row PnL for a single market (condition). Carries a top-level timeframe.
trader_category_pnl_batch
Full-row PnL for a market category. Carries a top-level timeframe.
Price tick batches
trader_global_tick_batch, trader_market_tick_batch, and trader_category_tick_batch carry mark-to-market refreshes. They are window-agnostic and their dirty_kinds is always ["price"].
Resolution batches
trader_global_resolution_batch, trader_market_resolution_batch, and trader_category_resolution_batch fire when an owning market resolves without a trade. They are window-agnostic and their dirty_kinds is always ["market_resolved"].