use std::fmt::Display;
use alloy_primitives::{Address, I256, U160};
use nautilus_core::UnixNanos;
use crate::{
defi::{
PoolIdentifier, SharedChain, SharedDex, Token,
data::swap_trade_info::{SwapTradeInfo, SwapTradeInfoCalculator},
},
identifiers::InstrumentId,
};
#[derive(Debug, Clone)]
pub struct RawSwapData {
pub amount0: I256,
pub amount1: I256,
pub sqrt_price_x96: U160,
}
impl RawSwapData {
pub fn new(amount0: I256, amount1: I256, sqrt_price_x96: U160) -> Self {
Self {
amount0,
amount1,
sqrt_price_x96,
}
}
}
#[derive(Debug, Clone, PartialEq)]
#[cfg_attr(
feature = "python",
pyo3::pyclass(module = "nautilus_trader.core.nautilus_pyo3.model", from_py_object)
)]
#[cfg_attr(
feature = "python",
pyo3_stub_gen::derive::gen_stub_pyclass(module = "nautilus_trader.model")
)]
pub struct PoolSwap {
pub chain: SharedChain,
pub dex: SharedDex,
pub instrument_id: InstrumentId,
pub pool_identifier: PoolIdentifier,
pub block: u64,
pub transaction_hash: String,
pub transaction_index: u32,
pub log_index: u32,
pub sender: Address,
pub recipient: Address,
pub sqrt_price_x96: U160,
pub amount0: I256,
pub amount1: I256,
pub liquidity: u128,
pub tick: i32,
pub timestamp: Option<UnixNanos>,
pub ts_init: Option<UnixNanos>,
pub trade_info: Option<SwapTradeInfo>,
}
impl PoolSwap {
#[must_use]
#[allow(clippy::too_many_arguments)]
pub fn new(
chain: SharedChain,
dex: SharedDex,
instrument_id: InstrumentId,
pool_identifier: PoolIdentifier,
block: u64,
transaction_hash: String,
transaction_index: u32,
log_index: u32,
timestamp: Option<UnixNanos>,
sender: Address,
recipient: Address,
amount0: I256,
amount1: I256,
sqrt_price_x96: U160,
liquidity: u128,
tick: i32,
) -> Self {
Self {
chain,
dex,
instrument_id,
pool_identifier,
block,
transaction_hash,
transaction_index,
log_index,
timestamp,
sender,
recipient,
amount0,
amount1,
sqrt_price_x96,
liquidity,
tick,
ts_init: timestamp, trade_info: None,
}
}
pub fn calculate_trade_info(
&mut self,
token0: &Token,
token1: &Token,
sqrt_price_x96: Option<U160>,
) -> anyhow::Result<()> {
let trade_info_calculator = SwapTradeInfoCalculator::new(
token0,
token1,
RawSwapData::new(self.amount0, self.amount1, self.sqrt_price_x96),
);
self.trade_info = Some(trade_info_calculator.compute(sqrt_price_x96)?);
Ok(())
}
}
impl Display for PoolSwap {
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
write!(
f,
"{}(instrument_id={})",
stringify!(PoolSwap),
self.instrument_id,
)
}
}