Skip to main content

polyfill_rs/
lib.rs

1//! Polyfill-rs: High-performance Rust client for Polymarket
2//!
3//! # Features
4//!
5//! - **High-performance order book management** with optimized data structures
6//! - **Real-time market data streaming** with WebSocket support
7//! - **Trade execution simulation** with slippage protection
8//! - **Detailed error handling** with specific error types
9//! - **Rate limiting and retry logic** for robust API interactions
10//! - **Ethereum integration** with EIP-712 signing support
11//! - **Benchmarking tools** for performance analysis
12//!
13//! # Quick Start
14//!
15//! ```rust,no_run
16//! use polyfill_rs::{ClientConfig, ClobClient, OrderArgs, Side};
17//! use rust_decimal::Decimal;
18//! use std::str::FromStr;
19//!
20//! #[tokio::main]
21//! async fn main() -> Result<(), Box<dyn std::error::Error>> {
22//!     let bootstrap = ClobClient::from_config(ClientConfig {
23//!         base_url: "https://clob.polymarket.com".to_string(),
24//!         chain: 137,
25//!         private_key: Some("your_private_key".to_string()),
26//!         ..ClientConfig::default()
27//!     })?;
28//!
29//!     let api_creds = bootstrap.create_or_derive_api_key(None).await?;
30//!     let client = ClobClient::from_config(ClientConfig {
31//!         base_url: "https://clob.polymarket.com".to_string(),
32//!         chain: 137,
33//!         private_key: Some("your_private_key".to_string()),
34//!         api_credentials: Some(api_creds),
35//!         ..ClientConfig::default()
36//!     })?;
37//!
38//!     // Create and post order
39//!     let order_args = OrderArgs::new(
40//!         "token_id",
41//!         Decimal::from_str("0.75").unwrap(),
42//!         Decimal::from_str("100.0").unwrap(),
43//!         Side::BUY,
44//!     );
45//!
46//!     let result = client.create_and_post_order(&order_args, None, None).await?;
47//!     println!("Order posted: {:?}", result);
48//!
49//!     Ok(())
50//! }
51//! ```
52//!
53//! # Advanced Usage
54//!
55//! ```rust,no_run
56//! use polyfill_rs::{ClobClient, OrderBookImpl};
57//! use rust_decimal::Decimal;
58//!
59//! #[tokio::main]
60//! async fn main() -> Result<(), Box<dyn std::error::Error>> {
61//!     // Create a basic client
62//!     let client = ClobClient::new("https://clob.polymarket.com");
63//!
64//!     // Get market data
65//!     let markets = client.get_sampling_markets(None).await.unwrap();
66//!     println!("Found {} markets", markets.data.len());
67//!
68//!     // Create an order book for high-performance operations
69//!     let mut book = OrderBookImpl::new("token_id".to_string(), 100); // 100 levels depth
70//!     println!("Order book created for token: {}", book.token_id);
71//!
72//!     Ok(())
73//! }
74//! ```
75
76use tracing::info;
77
78// Global constants
79pub const DEFAULT_CHAIN_ID: u64 = 137; // Polygon
80pub const DEFAULT_BASE_URL: &str = "https://clob.polymarket.com";
81pub const DEFAULT_TIMEOUT_SECS: u64 = 30;
82pub const DEFAULT_MAX_RETRIES: u32 = 3;
83pub const DEFAULT_RATE_LIMIT_RPS: u32 = 100;
84
85// Initialize logging
86pub fn init() {
87    tracing_subscriber::fmt::init();
88    info!("Polyfill-rs initialized");
89}
90
91// Re-export main types
92pub use crate::types::{
93    ApiCredentials,
94    // Additional compatibility types
95    ApiKeysResponse,
96    AssetType,
97    Balance,
98    BalanceAllowance,
99    BalanceAllowanceParams,
100    BatchMidpointRequest,
101    BatchMidpointResponse,
102    BatchPriceRequest,
103    BatchPriceResponse,
104    BookParams,
105    ClientConfig,
106    ClientResult,
107    FeeRateResponse,
108    FillEvent,
109    Market,
110    MarketSnapshot,
111    MarketsResponse,
112    MidpointResponse,
113    NegRiskResponse,
114    NotificationParams,
115    OpenOrder,
116    OpenOrderParams,
117    Order,
118    OrderBook,
119    OrderBookSummary,
120    OrderDelta,
121    OrderRequest,
122    OrderStatus,
123    OrderSummary,
124    OrderType,
125    PriceResponse,
126    PricesHistoryInterval,
127    PricesHistoryResponse,
128    Rewards,
129    RfqApproveOrderResponse,
130    RfqCancelQuote,
131    RfqCancelRequest,
132    RfqCreateQuote,
133    RfqCreateQuoteResponse,
134    RfqCreateRequest,
135    RfqCreateRequestResponse,
136    RfqListResponse,
137    RfqOrderExecutionRequest,
138    RfqQuoteData,
139    RfqQuotesParams,
140    RfqRequestData,
141    RfqRequestsParams,
142    Side,
143    SimplifiedMarket,
144    SimplifiedMarketsResponse,
145    SpreadResponse,
146    StreamMessage,
147    TickSizeResponse,
148    Token,
149    TokenPrice,
150    TradeParams,
151    WssAuth,
152    WssChannelType,
153    WssSubscription,
154};
155
156// Re-export client
157pub use crate::client::{ClobClient, PolyfillClient};
158
159// Re-export compatibility types (for easy migration from polymarket-rs-client)
160pub use crate::types::OrderArgs;
161
162// Re-export error types
163pub use crate::errors::{PolyfillError, Result};
164
165// Re-export advanced components
166pub use crate::book::{OrderBook as OrderBookImpl, OrderBookManager};
167pub use crate::decode::Decoder;
168pub use crate::fill::{FillEngine, FillResult};
169pub use crate::stream::{MarketStream, StreamManager, WebSocketBookApplier, WebSocketStream};
170pub use crate::ws_hot_path::{WsBookApplyStats, WsBookUpdateProcessor};
171
172// Re-export utilities
173pub use crate::utils::{crypto, math, rate_limit, retry, time, url};
174
175// Module declarations
176pub mod auth;
177pub mod book;
178pub mod buffer_pool;
179pub mod client;
180pub mod connection_manager;
181pub mod decode;
182pub mod dns_cache;
183pub mod errors;
184pub mod fill;
185pub mod http_config;
186pub mod orders;
187pub mod stream;
188pub mod types;
189pub mod utils;
190pub mod ws_hot_path;
191
192// Benchmarks
193#[cfg(test)]
194mod benches {
195    use crate::{OrderBookManager, OrderDelta, Side};
196    use chrono::Utc;
197    use criterion::{criterion_group, criterion_main};
198    use rust_decimal::Decimal;
199    use std::str::FromStr;
200
201    #[allow(dead_code)]
202    fn order_book_benchmark(c: &mut criterion::Criterion) {
203        let book_manager = OrderBookManager::new(100);
204
205        c.bench_function("apply_order_delta", |b| {
206            b.iter(|| {
207                let delta = OrderDelta {
208                    token_id: "test_token".to_string(),
209                    timestamp: Utc::now(),
210                    side: Side::BUY,
211                    price: Decimal::from_str("0.75").unwrap(),
212                    size: Decimal::from_str("100.0").unwrap(),
213                    sequence: 1,
214                };
215
216                let _ = book_manager.apply_delta(delta);
217            });
218        });
219    }
220
221    criterion_group!(benches, order_book_benchmark);
222    criterion_main!(benches);
223}
224
225#[cfg(test)]
226mod tests {
227    use super::*;
228    use rust_decimal::Decimal;
229    use std::str::FromStr;
230
231    #[test]
232    fn test_client_creation() {
233        let _client = ClobClient::new("https://test.example.com");
234        // Test that the client was created successfully
235        // We can't test private fields, but we can verify the client exists
236        // Client creation successful
237    }
238
239    #[test]
240    fn test_order_args_creation() {
241        let args = OrderArgs::new(
242            "test_token",
243            Decimal::from_str("0.75").unwrap(),
244            Decimal::from_str("100.0").unwrap(),
245            Side::BUY,
246        );
247
248        assert_eq!(args.token_id, "test_token");
249        assert_eq!(args.side, Side::BUY);
250    }
251
252    #[test]
253    fn test_order_args_default() {
254        let args = OrderArgs::default();
255        assert_eq!(args.token_id, "");
256        assert_eq!(args.price, Decimal::ZERO);
257        assert_eq!(args.size, Decimal::ZERO);
258        assert_eq!(args.side, Side::BUY);
259    }
260}