use serde::{Deserialize, Serialize};
use crate::error::Result;
#[derive(Debug, Clone)]
pub struct WebSocketConfig {
pub url: String,
pub exchange: String,
pub symbol: String,
pub subscription_msg: Option<String>,
pub ping_interval_secs: u64,
pub reconnect_delay_secs: u64,
pub max_reconnect_attempts: u32,
}
#[derive(Debug, Clone, Copy, PartialEq, Eq, Serialize, Deserialize)]
#[serde(rename_all = "lowercase")]
pub enum TradeSide {
Buy,
Sell,
}
#[derive(Debug, Clone, Serialize, Deserialize)]
pub struct TradeData {
pub symbol: String,
pub exchange: String,
pub side: TradeSide,
pub price: f64,
pub amount: f64,
pub exchange_ts: i64,
pub receipt_ts: i64,
pub trade_id: String,
}
#[derive(Debug, Clone, Serialize, Deserialize)]
pub struct TickerData {
pub symbol: String,
pub exchange: String,
pub price: f64,
pub best_bid: f64,
pub best_ask: f64,
pub exchange_ts: i64,
pub receipt_ts: i64,
}
#[derive(Debug, Clone, Serialize, Deserialize)]
pub struct OrderBookData {
pub symbol: String,
pub exchange: String,
pub asks: Vec<[f64; 2]>,
pub bids: Vec<[f64; 2]>,
pub exchange_ts: i64,
pub receipt_ts: i64,
pub is_snapshot: bool,
}
#[non_exhaustive]
#[derive(Debug, Clone)]
pub enum DataMessage {
Trade(TradeData),
Ticker(TickerData),
OrderBook(OrderBookData),
OrderUpdate(OrderUpdate),
PositionChange(PositionChange),
BalanceUpdate(BalanceUpdate),
InstrumentEvent(InstrumentEvent),
AdvancedOrderUpdate(AdvancedOrderUpdate),
}
pub trait ExchangeConnector: Send + Sync {
fn exchange_name(&self) -> &str;
fn ws_url(&self) -> &str;
fn build_ws_config(&self, symbol: &str) -> WebSocketConfig;
fn subscription_message(&self, symbol: &str) -> Option<String>;
fn parse_message(&self, raw: &str) -> Result<Vec<DataMessage>>;
}
#[derive(Debug, Clone, Serialize, Deserialize)]
pub struct OrderUpdate {
pub symbol: String,
pub exchange: String,
pub order_id: String,
pub client_oid: Option<String>,
pub side: TradeSide,
pub order_type: String,
pub status: String,
pub price: f64,
pub size: u32,
pub filled_size: u32,
pub remaining_size: u32,
pub fee: f64,
pub exchange_ts: i64,
pub receipt_ts: i64,
}
#[derive(Debug, Clone, Serialize, Deserialize)]
pub struct PositionChange {
pub symbol: String,
pub exchange: String,
pub current_qty: i32,
pub avg_entry_price: f64,
pub unrealised_pnl: f64,
pub realised_pnl: f64,
pub change_reason: String,
pub exchange_ts: i64,
pub receipt_ts: i64,
}
#[derive(Debug, Clone, Serialize, Deserialize)]
pub struct BalanceUpdate {
pub exchange: String,
pub currency: String,
pub available_balance: f64,
pub hold_balance: f64,
pub event: String,
pub exchange_ts: i64,
pub receipt_ts: i64,
}
#[derive(Debug, Clone, Serialize, Deserialize)]
pub struct InstrumentEvent {
pub symbol: String,
pub exchange: String,
pub subject: String,
pub mark_price: Option<f64>,
pub index_price: Option<f64>,
pub funding_rate: Option<f64>,
pub predicted_funding_rate: Option<f64>,
pub premium_index: Option<f64>,
pub exchange_ts: i64,
pub receipt_ts: i64,
}
#[derive(Debug, Clone, Serialize, Deserialize)]
pub struct AdvancedOrderUpdate {
pub symbol: String,
pub exchange: String,
pub order_id: String,
pub client_oid: Option<String>,
pub status: String,
pub side: TradeSide,
pub order_type: String,
pub stop: Option<String>,
pub stop_price: Option<f64>,
pub price: Option<f64>,
pub size: u32,
pub exchange_ts: i64,
pub receipt_ts: i64,
}