polymarket_rs_client/
data.rs

1use crate::Decimal;
2
3use crate::SignedOrderRequest;
4use alloy_primitives::U256;
5use serde::{Deserialize, Deserializer, Serialize};
6use std::fmt::Display;
7use std::str::FromStr;
8
9const ZERO_ADDRESS: &str = "0x0000000000000000000000000000000000000000";
10
11pub enum AssetType {
12    COLLATERAL,
13    CONDITIONAL,
14}
15
16#[allow(clippy::to_string_trait_impl)]
17impl ToString for AssetType {
18    fn to_string(&self) -> String {
19        match self {
20            AssetType::COLLATERAL => "COLLATERAL".to_string(),
21            AssetType::CONDITIONAL => "CONDITIONAL".to_string(),
22        }
23    }
24}
25
26#[derive(Default)]
27pub struct BalanceAllowanceParams {
28    pub asset_type: Option<AssetType>,
29    pub token_id: Option<String>,
30    pub signature_type: Option<u8>,
31}
32
33impl BalanceAllowanceParams {
34    pub fn to_query_params(&self) -> Vec<(&str, String)> {
35        let mut params = Vec::with_capacity(3);
36
37        if let Some(x) = &self.asset_type {
38            params.push(("asset_type", x.to_string()));
39        }
40
41        if let Some(x) = &self.token_id {
42            params.push(("token_id", x.to_string()));
43        }
44
45        if let Some(x) = &self.signature_type {
46            params.push(("signature_type", x.to_string()));
47        }
48        params
49    }
50}
51
52impl BalanceAllowanceParams {
53    pub fn set_signature_type(&mut self, s: u8) {
54        self.signature_type = Some(s);
55    }
56}
57
58#[derive(Debug)]
59pub struct TradeParams {
60    pub id: Option<String>,
61    pub maker_address: Option<String>,
62    pub market: Option<String>,
63    pub asset_id: Option<String>,
64    pub before: Option<u64>,
65    pub after: Option<u64>,
66}
67
68impl TradeParams {
69    pub fn to_query_params(&self) -> Vec<(&str, String)> {
70        let mut params = Vec::with_capacity(4);
71
72        if let Some(x) = &self.id {
73            params.push(("id", x.clone()));
74        }
75
76        if let Some(x) = &self.asset_id {
77            params.push(("asset_id", x.clone()));
78        }
79
80        if let Some(x) = &self.market {
81            params.push(("market", x.clone()));
82        }
83        if let Some(x) = &self.before {
84            params.push(("before", x.to_string()));
85        }
86        if let Some(x) = &self.after {
87            params.push(("after", x.to_string()));
88        }
89        params
90    }
91}
92
93#[derive(Debug, Deserialize)]
94pub struct OpenOrder {
95    pub associate_trades: Vec<String>,
96    pub id: String,
97    pub status: String,
98    pub market: String,
99
100    #[serde(with = "rust_decimal::serde::str")]
101    pub original_size: Decimal,
102    pub outcome: String,
103    pub maker_address: String,
104    pub owner: String,
105
106    #[serde(with = "rust_decimal::serde::str")]
107    pub price: Decimal,
108    pub side: Side,
109
110    #[serde(with = "rust_decimal::serde::str")]
111    pub size_matched: Decimal,
112    pub asset_id: String,
113    #[serde(deserialize_with = "deserialize_number_from_string")]
114    pub expiration: u64,
115    #[serde(rename = "type")]
116    pub order_type: OrderType,
117    #[serde(deserialize_with = "deserialize_number_from_string")]
118    pub created_at: u64,
119}
120
121#[derive(Debug)]
122pub struct OpenOrderParams {
123    pub id: Option<String>,
124    pub asset_id: Option<String>,
125    pub market: Option<String>,
126}
127
128impl OpenOrderParams {
129    pub fn to_query_params(&self) -> Vec<(&str, &String)> {
130        let mut params = Vec::with_capacity(4);
131
132        if let Some(x) = &self.id {
133            params.push(("id", x));
134        }
135
136        if let Some(x) = &self.asset_id {
137            params.push(("asset_id", x));
138        }
139
140        if let Some(x) = &self.market {
141            params.push(("market", x));
142        }
143        params
144    }
145}
146
147fn deserialize_number_from_string<'de, T, D>(deserializer: D) -> Result<T, D::Error>
148where
149    D: Deserializer<'de>,
150    T: FromStr + serde::Deserialize<'de>,
151    <T as FromStr>::Err: Display,
152{
153    #[derive(Deserialize)]
154    #[serde(untagged)]
155    enum StringOrInt<T> {
156        String(String),
157        Number(T),
158    }
159
160    match StringOrInt::<T>::deserialize(deserializer)? {
161        StringOrInt::String(s) => s.parse::<T>().map_err(serde::de::Error::custom),
162        StringOrInt::Number(i) => Ok(i),
163    }
164}
165
166#[derive(Debug, Serialize)]
167#[serde(rename_all = "camelCase")]
168pub struct PostOrder {
169    order: SignedOrderRequest,
170    owner: String,
171    order_type: OrderType,
172}
173
174impl PostOrder {
175    pub fn new(order: SignedOrderRequest, owner: String, order_type: OrderType) -> Self {
176        PostOrder {
177            order,
178            owner,
179            order_type,
180        }
181    }
182}
183
184#[derive(Debug)]
185pub struct OrderArgs {
186    pub token_id: String,
187    pub price: Decimal,
188    pub size: Decimal,
189    pub side: Side,
190}
191
192#[derive(Debug, Deserialize)]
193pub struct OrderBookSummary {
194    pub market: String,
195    pub asset_id: String,
196    pub hash: String,
197    #[serde(deserialize_with = "deserialize_number_from_string")]
198    pub timestamp: u64,
199    pub bids: Vec<OrderSummary>,
200    pub asks: Vec<OrderSummary>,
201}
202
203#[derive(Debug)]
204pub struct MarketOrderArgs {
205    pub token_id: String,
206    pub amount: Decimal,
207}
208
209#[derive(Debug, Deserialize)]
210pub struct OrderSummary {
211    #[serde(with = "rust_decimal::serde::str")]
212    pub price: Decimal,
213    #[serde(with = "rust_decimal::serde::str")]
214    pub size: Decimal,
215}
216
217impl OrderArgs {
218    pub fn new(token_id: &str, price: Decimal, size: Decimal, side: Side) -> Self {
219        OrderArgs {
220            token_id: token_id.to_owned(),
221            price,
222            size,
223            side,
224        }
225    }
226}
227
228#[derive(Debug)]
229pub struct ExtraOrderArgs {
230    pub fee_rate_bps: u32,
231    pub nonce: U256,
232    pub taker: String,
233}
234
235impl Default for ExtraOrderArgs {
236    fn default() -> Self {
237        ExtraOrderArgs {
238            fee_rate_bps: 0,
239            nonce: U256::ZERO,
240            taker: ZERO_ADDRESS.into(),
241        }
242    }
243}
244
245#[derive(Debug, Default)]
246pub struct CreateOrderOptions {
247    pub tick_size: Option<Decimal>,
248    pub neg_risk: Option<bool>,
249}
250
251#[derive(Debug, Deserialize)]
252pub struct ApiKeysResponse {
253    #[serde(rename = "apiKeys")]
254    pub api_keys: Vec<String>,
255}
256
257#[derive(Debug, Deserialize, Serialize)]
258pub struct MidpointResponse {
259    #[serde(with = "rust_decimal::serde::str")]
260    pub mid: Decimal,
261}
262
263#[derive(Debug, Deserialize)]
264pub struct PriceResponse {
265    #[serde(with = "rust_decimal::serde::str")]
266    pub price: Decimal,
267}
268
269#[derive(Debug, Deserialize)]
270pub struct SpreadResponse {
271    #[serde(with = "rust_decimal::serde::str")]
272    pub spread: Decimal,
273}
274
275#[derive(Debug, Deserialize)]
276pub struct TickSizeResponse {
277    pub minimum_tick_size: Decimal,
278}
279
280#[derive(Debug, Deserialize)]
281pub struct NegRiskResponse {
282    pub neg_risk: bool,
283}
284
285#[derive(Debug, Serialize, Deserialize, Clone, Copy, Hash, Eq, PartialEq)]
286pub enum OrderType {
287    GTC,
288    FOK,
289    GTD,
290}
291
292impl OrderType {
293    pub fn as_str(&self) -> &'static str {
294        match self {
295            OrderType::GTC => "GTC",
296            OrderType::FOK => "FOK",
297            OrderType::GTD => "GTD",
298        }
299    }
300}
301
302#[derive(Debug, Serialize, Deserialize, Clone, Copy, Hash, Eq, PartialEq)]
303pub enum Side {
304    BUY = 0,
305    SELL = 1,
306}
307
308impl Side {
309    pub fn as_str(&self) -> &'static str {
310        match self {
311            Side::BUY => "BUY",
312            Side::SELL => "SELL",
313        }
314    }
315}
316
317#[derive(Debug, Serialize, Deserialize)]
318pub struct BookParams {
319    pub token_id: String,
320    pub side: Side,
321}
322
323#[derive(Default, Debug, Serialize, Deserialize)]
324pub struct ApiCreds {
325    #[serde(rename = "apiKey")]
326    pub api_key: String,
327    pub secret: String,
328    pub passphrase: String,
329}