Browse Source

Optimise data structure used for settlement proposals

New HashMap can store both incoming and outgoing settlement proposals at the
same time and resulted in some code simplification, as there are less types
needed to convey the intention.

Provide a type alias for convenience (this also ensures that both binaries store
settlement proposals in the same way)
upload-correct-windows-binary
Mariusz Klochowicz 3 years ago
parent
commit
36c04140f6
No known key found for this signature in database GPG Key ID: 470C865699C8D4D
  1. 2
      daemon/src/maker.rs
  2. 10
      daemon/src/maker_cfd.rs
  3. 10
      daemon/src/model/cfd.rs
  4. 2
      daemon/src/taker.rs
  5. 14
      daemon/src/taker_cfd.rs
  6. 48
      daemon/src/to_sse_event.rs

2
daemon/src/maker.rs

@ -114,7 +114,7 @@ async fn main() -> Result<()> {
let (order_feed_sender, order_feed_receiver) = watch::channel::<Option<Order>>(None); let (order_feed_sender, order_feed_receiver) = watch::channel::<Option<Order>>(None);
let (wallet_feed_sender, wallet_feed_receiver) = watch::channel::<WalletInfo>(wallet_info); let (wallet_feed_sender, wallet_feed_receiver) = watch::channel::<WalletInfo>(wallet_info);
let (settlement_feed_sender, settlement_feed_receiver) = let (settlement_feed_sender, settlement_feed_receiver) =
watch::channel::<SettlementProposals>(SettlementProposals::Incoming(HashMap::new())); watch::channel::<SettlementProposals>(HashMap::new());
let figment = rocket::Config::figment() let figment = rocket::Config::figment()
.merge(("databases.maker.url", data_dir.join("maker.sqlite"))) .merge(("databases.maker.url", data_dir.join("maker.sqlite")))

10
daemon/src/maker_cfd.rs

@ -6,7 +6,7 @@ use crate::db::{
use crate::maker_inc_connections::TakerCommand; use crate::maker_inc_connections::TakerCommand;
use crate::model::cfd::{ use crate::model::cfd::{
Cfd, CfdState, CfdStateChangeEvent, CfdStateCommon, Dlc, Order, OrderId, Origin, Role, Cfd, CfdState, CfdStateChangeEvent, CfdStateCommon, Dlc, Order, OrderId, Origin, Role,
SettlementProposal, SettlementProposals, SettlementKind, SettlementProposal, SettlementProposals,
}; };
use crate::model::{OracleEventId, TakerId, Usd}; use crate::model::{OracleEventId, TakerId, Usd};
use crate::monitor::MonitorParams; use crate::monitor::MonitorParams;
@ -76,7 +76,7 @@ pub struct Actor {
setup_state: SetupState, setup_state: SetupState,
latest_announcements: Option<BTreeMap<OracleEventId, oracle::Announcement>>, latest_announcements: Option<BTreeMap<OracleEventId, oracle::Announcement>>,
oracle_actor: Address<oracle::Actor<Actor, monitor::Actor<Actor>>>, oracle_actor: Address<oracle::Actor<Actor, monitor::Actor<Actor>>>,
current_settlement_proposals: HashMap<OrderId, SettlementProposal>, current_settlement_proposals: SettlementProposals,
} }
enum SetupState { enum SetupState {
@ -120,9 +120,7 @@ impl Actor {
fn send_current_settlement_proposals(&self) -> Result<()> { fn send_current_settlement_proposals(&self) -> Result<()> {
Ok(self Ok(self
.settlements_feed_sender .settlements_feed_sender
.send(SettlementProposals::Incoming( .send(self.current_settlement_proposals.clone())?)
self.current_settlement_proposals.clone(),
))?)
} }
async fn handle_new_order( async fn handle_new_order(
@ -192,7 +190,7 @@ impl Actor {
proposal proposal
); );
self.current_settlement_proposals self.current_settlement_proposals
.insert(proposal.order_id, proposal); .insert(proposal.order_id, (proposal, SettlementKind::Incoming));
self.send_current_settlement_proposals()?; self.send_current_settlement_proposals()?;
Ok(()) Ok(())

10
daemon/src/model/cfd.rs

@ -355,12 +355,14 @@ pub struct SettlementProposal {
} }
#[derive(Debug, Clone)] #[derive(Debug, Clone)]
#[allow(dead_code)] // Variants used by different binaries #[allow(dead_code)] // Variants (for now) used by different binaries.
pub enum SettlementProposals { pub enum SettlementKind {
Incoming(HashMap<OrderId, SettlementProposal>), Incoming,
Outgoing(HashMap<OrderId, SettlementProposal>), Outgoing,
} }
pub type SettlementProposals = HashMap<OrderId, (SettlementProposal, SettlementKind)>;
/// Represents a cfd (including state) /// Represents a cfd (including state)
#[derive(Debug, Clone, Serialize, Deserialize, PartialEq)] #[derive(Debug, Clone, Serialize, Deserialize, PartialEq)]
pub struct Cfd { pub struct Cfd {

2
daemon/src/taker.rs

@ -109,7 +109,7 @@ async fn main() -> Result<()> {
let (order_feed_sender, order_feed_receiver) = watch::channel::<Option<Order>>(None); let (order_feed_sender, order_feed_receiver) = watch::channel::<Option<Order>>(None);
let (wallet_feed_sender, wallet_feed_receiver) = watch::channel::<WalletInfo>(wallet_info); let (wallet_feed_sender, wallet_feed_receiver) = watch::channel::<WalletInfo>(wallet_info);
let (settlement_feed_sender, settlement_feed_receiver) = let (settlement_feed_sender, settlement_feed_receiver) =
watch::channel::<SettlementProposals>(SettlementProposals::Outgoing(HashMap::new())); watch::channel::<SettlementProposals>(HashMap::new());
let (read, write) = loop { let (read, write) = loop {
let socket = tokio::net::TcpSocket::new_v4()?; let socket = tokio::net::TcpSocket::new_v4()?;

14
daemon/src/taker_cfd.rs

@ -5,7 +5,7 @@ use crate::db::{
}; };
use crate::model::cfd::{ use crate::model::cfd::{
Cfd, CfdState, CfdStateChangeEvent, CfdStateCommon, Dlc, Order, OrderId, Origin, Role, Cfd, CfdState, CfdStateChangeEvent, CfdStateCommon, Dlc, Order, OrderId, Origin, Role,
SettlementProposal, SettlementProposals, SettlementKind, SettlementProposals,
}; };
use crate::model::{OracleEventId, Usd}; use crate::model::{OracleEventId, Usd};
use crate::monitor::{self, MonitorParams}; use crate::monitor::{self, MonitorParams};
@ -65,7 +65,7 @@ pub struct Actor {
setup_state: SetupState, setup_state: SetupState,
latest_announcements: Option<BTreeMap<OracleEventId, oracle::Announcement>>, latest_announcements: Option<BTreeMap<OracleEventId, oracle::Announcement>>,
oracle_actor: Address<oracle::Actor<Actor, monitor::Actor<Actor>>>, oracle_actor: Address<oracle::Actor<Actor, monitor::Actor<Actor>>>,
current_settlement_proposals: HashMap<OrderId, SettlementProposal>, current_settlement_proposals: SettlementProposals,
} }
impl Actor { impl Actor {
@ -100,9 +100,7 @@ impl Actor {
fn send_current_settlement_proposals(&self) -> Result<()> { fn send_current_settlement_proposals(&self) -> Result<()> {
Ok(self Ok(self
.settlements_feed_sender .settlements_feed_sender
.send(SettlementProposals::Outgoing( .send(self.current_settlement_proposals.clone())?)
self.current_settlement_proposals.clone(),
))?)
} }
async fn handle_take_offer(&mut self, order_id: OrderId, quantity: Usd) -> Result<()> { async fn handle_take_offer(&mut self, order_id: OrderId, quantity: Usd) -> Result<()> {
@ -153,8 +151,10 @@ impl Actor {
) )
} }
self.current_settlement_proposals self.current_settlement_proposals.insert(
.insert(proposal.order_id, proposal.clone()); proposal.order_id,
(proposal.clone(), SettlementKind::Outgoing),
);
self.send_current_settlement_proposals()?; self.send_current_settlement_proposals()?;
self.send_to_maker self.send_to_maker

48
daemon/src/to_sse_event.rs

@ -1,4 +1,4 @@
use crate::model::cfd::{OrderId, Role, SettlementProposals}; use crate::model::cfd::{OrderId, Role, SettlementKind, SettlementProposals};
use crate::model::{Leverage, Position, TradingPair, Usd}; use crate::model::{Leverage, Position, TradingPair, Usd};
use crate::{bitmex_price_feed, model}; use crate::{bitmex_price_feed, model};
use bdk::bitcoin::{Amount, SignedAmount}; use bdk::bitcoin::{Amount, SignedAmount};
@ -103,12 +103,6 @@ pub struct CfdsWithAuxData {
pub settlement_proposals: SettlementProposals, pub settlement_proposals: SettlementProposals,
} }
enum SettlementProposalStatus {
Incoming,
Outgoing,
None,
}
impl CfdsWithAuxData { impl CfdsWithAuxData {
pub fn new( pub fn new(
rx_cfds: &watch::Receiver<Vec<model::cfd::Cfd>>, rx_cfds: &watch::Receiver<Vec<model::cfd::Cfd>>,
@ -124,20 +118,6 @@ impl CfdsWithAuxData {
let settlement_proposals = rx_settlement.borrow().clone(); let settlement_proposals = rx_settlement.borrow().clone();
// Test whether the correct settlement proposals were sent
match settlement_proposals {
SettlementProposals::Incoming(_) => {
if role == Role::Taker {
panic!("Taker should never receive incoming settlement proposals");
}
}
SettlementProposals::Outgoing(_) => {
if role == Role::Maker {
panic!("Maker should never receive outgoing settlement proposals");
}
}
}
CfdsWithAuxData { CfdsWithAuxData {
cfds: rx_cfds.borrow().clone(), cfds: rx_cfds.borrow().clone(),
current_price, current_price,
@ -146,20 +126,10 @@ impl CfdsWithAuxData {
} }
/// Check whether given CFD has any active settlement proposals /// Check whether given CFD has any active settlement proposals
fn settlement_proposal_status(&self, cfd: &model::cfd::Cfd) -> SettlementProposalStatus { fn settlement_proposal_status(&self, cfd: &model::cfd::Cfd) -> Option<SettlementKind> {
match &self.settlement_proposals { self.settlement_proposals
SettlementProposals::Incoming(proposals) => { .get(&cfd.order.id)
if proposals.contains_key(&cfd.order.id) { .map(|(_, kind)| kind.clone())
return SettlementProposalStatus::Incoming;
}
}
SettlementProposals::Outgoing(proposals) => {
if proposals.contains_key(&cfd.order.id) {
return SettlementProposalStatus::Outgoing;
}
}
}
SettlementProposalStatus::None
} }
} }
@ -258,12 +228,12 @@ impl ToSseEvent for model::WalletInfo {
fn to_cfd_state( fn to_cfd_state(
cfd_state: &model::cfd::CfdState, cfd_state: &model::cfd::CfdState,
proposal_status: SettlementProposalStatus, proposal_status: Option<SettlementKind>,
) -> CfdState { ) -> CfdState {
match proposal_status { match proposal_status {
SettlementProposalStatus::Incoming => CfdState::IncomingSettlementProposal, Some(SettlementKind::Incoming) => CfdState::IncomingSettlementProposal,
SettlementProposalStatus::Outgoing => CfdState::OutgoingSettlementProposal, Some(SettlementKind::Outgoing) => CfdState::OutgoingSettlementProposal,
SettlementProposalStatus::None => match cfd_state { None => match cfd_state {
model::cfd::CfdState::OutgoingOrderRequest { .. } => CfdState::OutgoingOrderRequest, model::cfd::CfdState::OutgoingOrderRequest { .. } => CfdState::OutgoingOrderRequest,
model::cfd::CfdState::IncomingOrderRequest { .. } => CfdState::IncomingOrderRequest, model::cfd::CfdState::IncomingOrderRequest { .. } => CfdState::IncomingOrderRequest,
model::cfd::CfdState::Accepted { .. } => CfdState::Accepted, model::cfd::CfdState::Accepted { .. } => CfdState::Accepted,

Loading…
Cancel
Save