1use serde::{Deserialize, Serialize};
6
7#[derive(Debug, Clone, Serialize, Deserialize)]
9pub struct OrderSummary {
10 pub price: String,
12 pub size: String,
14}
15
16#[derive(Debug, Clone, Serialize, Deserialize)]
18pub struct BookMessage {
19 pub event_type: String,
21 pub asset_id: String,
23 pub market: String,
25 pub timestamp: String,
27 pub hash: String,
29 pub bids: Vec<OrderSummary>,
31 pub asks: Vec<OrderSummary>,
33 pub last_trade_price: Option<String>,
35}
36
37#[derive(Debug, Clone, Serialize, Deserialize)]
39pub struct PriceChange {
40 pub asset_id: String,
42 pub price: String,
44 pub size: String,
46 pub side: String,
48 pub hash: String,
50 pub best_bid: Option<String>,
52 pub best_ask: Option<String>,
54}
55
56#[derive(Debug, Clone, Serialize, Deserialize)]
58pub struct PriceChangeMessage {
59 pub event_type: String,
61 pub market: String,
63 pub price_changes: Vec<PriceChange>,
65 pub timestamp: String,
67}
68
69#[derive(Debug, Clone, Serialize, Deserialize)]
71pub struct TickSizeChangeMessage {
72 pub event_type: String,
74 pub asset_id: String,
76 pub market: String,
78 pub old_tick_size: String,
80 pub new_tick_size: String,
82 pub side: String,
84 pub timestamp: String,
86}
87
88#[derive(Debug, Clone, Serialize, Deserialize)]
90pub struct LastTradePriceMessage {
91 pub event_type: String,
93 pub asset_id: String,
95 pub market: String,
97 pub price: String,
99 pub side: String,
101 pub size: String,
103 pub fee_rate_bps: Option<String>,
105 pub timestamp: String,
107}
108
109#[derive(Debug, Clone)]
111pub enum MarketMessage {
112 Book(BookMessage),
114 PriceChange(PriceChangeMessage),
116 TickSizeChange(TickSizeChangeMessage),
118 LastTradePrice(LastTradePriceMessage),
120}
121
122impl MarketMessage {
123 pub fn from_json(json: &str) -> Result<Self, serde_json::Error> {
125 if json.starts_with('[') {
127 let books: Vec<BookMessage> = serde_json::from_str(json)?;
128 if let Some(book) = books.into_iter().next() {
129 return Ok(MarketMessage::Book(book));
130 }
131 return Err(serde::de::Error::custom("Empty book array"));
132 }
133
134 #[derive(Deserialize)]
135 struct RawMessage {
136 event_type: String,
137 }
138
139 let raw: RawMessage = serde_json::from_str(json)?;
140 match raw.event_type.as_str() {
141 "book" => Ok(MarketMessage::Book(serde_json::from_str(json)?)),
142 "price_change" => Ok(MarketMessage::PriceChange(serde_json::from_str(json)?)),
143 "tick_size_change" => Ok(MarketMessage::TickSizeChange(serde_json::from_str(json)?)),
144 "last_trade_price" => Ok(MarketMessage::LastTradePrice(serde_json::from_str(json)?)),
145 _ => Err(serde::de::Error::custom(format!(
146 "Unknown market event type: {}",
147 raw.event_type
148 ))),
149 }
150 }
151}