use crate::core::request_trait::HasLock;
use crate::impl_request_has_field;
use crate::impl_request_has_field_passthrough;
use crate::param::{AccountId, Fee, Pnl, PositionEffect, PositionSide, Quantity, Side, Trade};
use crate::pretrade::PreTradeLock;
use super::{
HasAccountId, HasAutoBorrow, HasClosePosition, HasExecutionReportIsFinal,
HasExecutionReportLastTrade, HasExecutionReportPositionEffect, HasExecutionReportPositionSide,
HasFee, HasInstrument, HasLeavesQuantity, HasOrderCollateralAsset, HasOrderLeverage,
HasOrderPositionSide, HasOrderPrice, HasPnl, HasReduceOnly, HasSide, HasTradeAmount,
Instrument,
};
#[derive(Clone, Debug, PartialEq, Eq)]
pub struct ExecutionReportOperation {
pub instrument: Instrument,
pub account_id: AccountId,
pub side: Side,
}
#[derive(Clone, Debug, PartialEq, Eq)]
pub struct WithExecutionReportOperation<T> {
pub inner: T,
pub operation: ExecutionReportOperation,
}
impl_request_has_field!(
ExecutionReportOperation,
WithExecutionReportOperation,
operation,
HasInstrument, instrument, &Instrument, instrument;
);
impl_request_has_field_passthrough!(
WithExecutionReportOperation,
inner,
HasReduceOnly, reduce_only, bool;
HasClosePosition, close_position, bool;
HasAutoBorrow, auto_borrow, bool;
HasPnl, pnl, Pnl;
HasFee, fee, Fee;
HasLeavesQuantity, leaves_quantity, Quantity;
HasLock, lock, PreTradeLock;
HasOrderPrice, price, Option<crate::param::Price>;
HasOrderPositionSide, position_side, Option<PositionSide>;
HasOrderLeverage, leverage, Option<crate::param::Leverage>;
HasOrderCollateralAsset, collateral_asset, Option<&crate::param::Asset>;
HasExecutionReportLastTrade, last_trade, Option<Trade>;
HasExecutionReportIsFinal, is_final, bool;
HasExecutionReportPositionEffect, position_effect, Option<PositionEffect>;
HasExecutionReportPositionSide, position_side, Option<PositionSide>;
);
impl_request_has_field!(
ExecutionReportOperation,
WithExecutionReportOperation,
operation,
HasAccountId, account_id, AccountId, account_id;
HasSide, side, Side, side;
);
impl_request_has_field_passthrough!(
WithFinancialImpact,
inner,
HasInstrument, instrument, &Instrument;
);
impl_request_has_field_passthrough!(
WithFinancialImpact,
inner,
HasAccountId, account_id, AccountId;
HasSide, side, Side;
HasTradeAmount, trade_amount, crate::param::TradeAmount;
HasReduceOnly, reduce_only, bool;
HasClosePosition, close_position, bool;
HasAutoBorrow, auto_borrow, bool;
HasLeavesQuantity, leaves_quantity, Quantity;
HasLock, lock, PreTradeLock;
HasOrderPrice, price, Option<crate::param::Price>;
HasOrderPositionSide, position_side, Option<PositionSide>;
HasOrderLeverage, leverage, Option<crate::param::Leverage>;
HasOrderCollateralAsset, collateral_asset, Option<&crate::param::Asset>;
HasExecutionReportLastTrade, last_trade, Option<Trade>;
HasExecutionReportIsFinal, is_final, bool;
HasExecutionReportPositionEffect, position_effect, Option<PositionEffect>;
HasExecutionReportPositionSide, position_side, Option<PositionSide>;
);
#[derive(Clone, Debug, PartialEq, Eq)]
pub struct FinancialImpact {
pub pnl: Pnl,
pub fee: Fee,
}
#[derive(Clone, Debug, PartialEq, Eq)]
pub struct WithFinancialImpact<T> {
pub inner: T,
pub financial_impact: FinancialImpact,
}
impl_request_has_field!(
FinancialImpact,
WithFinancialImpact,
financial_impact,
HasPnl, pnl, Pnl, pnl;
HasFee, fee, Fee, fee;
);
impl_request_has_field_passthrough!(
WithExecutionReportFillDetails,
inner,
HasInstrument, instrument, &Instrument;
);
impl_request_has_field_passthrough!(
WithExecutionReportFillDetails,
inner,
HasAccountId, account_id, AccountId;
HasSide, side, Side;
HasTradeAmount, trade_amount, crate::param::TradeAmount;
HasReduceOnly, reduce_only, bool;
HasClosePosition, close_position, bool;
HasAutoBorrow, auto_borrow, bool;
HasPnl, pnl, Pnl;
HasFee, fee, Fee;
HasOrderPrice, price, Option<crate::param::Price>;
HasOrderPositionSide, position_side, Option<PositionSide>;
HasOrderLeverage, leverage, Option<crate::param::Leverage>;
HasOrderCollateralAsset, collateral_asset, Option<&crate::param::Asset>;
HasExecutionReportPositionEffect, position_effect, Option<PositionEffect>;
HasExecutionReportPositionSide, position_side, Option<PositionSide>;
);
#[derive(Clone, Debug, PartialEq, Eq)]
pub struct ExecutionReportFillDetails {
pub last_trade: Option<Trade>,
pub leaves_quantity: Quantity,
pub lock: PreTradeLock,
pub is_final: bool,
}
#[derive(Clone, Debug, PartialEq, Eq)]
pub struct WithExecutionReportFillDetails<T> {
pub inner: T,
pub fill: ExecutionReportFillDetails,
}
impl_request_has_field!(
ExecutionReportFillDetails,
WithExecutionReportFillDetails,
fill,
HasExecutionReportLastTrade, last_trade, Option<Trade>, last_trade;
HasLeavesQuantity, leaves_quantity, Quantity, leaves_quantity;
HasLock, lock, PreTradeLock, lock;
HasExecutionReportIsFinal, is_final, bool, is_final;
);
impl_request_has_field_passthrough!(
WithExecutionReportPositionImpact,
inner,
HasInstrument, instrument, &Instrument;
);
impl_request_has_field_passthrough!(
WithExecutionReportPositionImpact,
inner,
HasAccountId, account_id, AccountId;
HasSide, side, Side;
HasTradeAmount, trade_amount, crate::param::TradeAmount;
HasReduceOnly, reduce_only, bool;
HasClosePosition, close_position, bool;
HasAutoBorrow, auto_borrow, bool;
HasPnl, pnl, Pnl;
HasFee, fee, Fee;
HasLeavesQuantity, leaves_quantity, Quantity;
HasLock, lock, PreTradeLock;
HasOrderPrice, price, Option<crate::param::Price>;
HasOrderPositionSide, position_side, Option<PositionSide>;
HasOrderLeverage, leverage, Option<crate::param::Leverage>;
HasOrderCollateralAsset, collateral_asset, Option<&crate::param::Asset>;
HasExecutionReportLastTrade, last_trade, Option<Trade>;
HasExecutionReportIsFinal, is_final, bool;
);
#[derive(Clone, Debug, Default, PartialEq, Eq)]
pub struct ExecutionReportPositionImpact {
pub position_effect: Option<PositionEffect>,
pub position_side: Option<PositionSide>,
}
#[derive(Clone, Debug, PartialEq, Eq)]
pub struct WithExecutionReportPositionImpact<T> {
pub inner: T,
pub position_impact: ExecutionReportPositionImpact,
}
impl_request_has_field!(
ExecutionReportPositionImpact,
WithExecutionReportPositionImpact,
position_impact,
HasExecutionReportPositionEffect, position_effect, Option<PositionEffect>, position_effect;
HasExecutionReportPositionSide, position_side, Option<PositionSide>, position_side;
);
#[cfg(test)]
mod tests {
use crate::param::{AccountId, Quantity};
use crate::pretrade::PreTradeLock;
use super::{
ExecutionReportFillDetails, ExecutionReportOperation, WithExecutionReportOperation,
};
fn fill() -> ExecutionReportFillDetails {
ExecutionReportFillDetails {
last_trade: None,
leaves_quantity: Quantity::from_str("0").expect("must be valid"),
lock: PreTradeLock::default(),
is_final: false,
}
}
#[test]
fn execution_report_operation_account_id_via_has_account_id() {
use crate::param::Asset;
use crate::param::Side;
use crate::{HasAccountId, Instrument};
let id = AccountId::from_u64(99);
let op = ExecutionReportOperation {
instrument: Instrument::new(
Asset::new("SPX").expect("must be valid"),
Asset::new("USD").expect("must be valid"),
),
account_id: id,
side: Side::Sell,
};
assert_eq!(op.account_id(), Ok(id));
let wrapped = WithExecutionReportOperation {
inner: (),
operation: op,
};
assert_eq!(wrapped.account_id(), Ok(id));
}
#[test]
fn fill_defaults_are_stable() {
let f = fill();
assert_eq!(f.last_trade, None);
assert_eq!(
f.leaves_quantity,
Quantity::from_str("0").expect("must be valid")
);
assert_eq!(f.lock, PreTradeLock::default());
assert!(!f.is_final);
}
}