extract out ChainService

This commit is contained in:
Roei Erez
2024-06-09 13:36:44 +03:00
parent 7276346a5f
commit 55fe7c71b0
4 changed files with 42 additions and 45 deletions

View File

@@ -1,12 +1,11 @@
use anyhow::{anyhow, Result};
use boltz_client::network::electrum::ElectrumConfig;
use boltz_client::network::Chain;
use boltz_client::swaps::boltzv2::{
CreateReverseResponse, CreateSubmarineResponse, Leaf, SwapTree, BOLTZ_MAINNET_URL_V2,
BOLTZ_TESTNET_URL_V2,
};
use boltz_client::{Keypair, LBtcSwapScriptV2, ToHex};
use lwk_wollet::{ElectrumClient, ElectrumUrl, ElementsNetwork};
use lwk_wollet::ElementsNetwork;
use rusqlite::types::{FromSql, FromSqlError, FromSqlResult, ToSqlOutput, ValueRef};
use rusqlite::ToSql;
use serde::{Deserialize, Serialize};
@@ -28,14 +27,6 @@ pub struct Config {
pub payment_timeout_sec: u64,
}
impl Config {
pub(crate) fn get_electrum_client(&self) -> Result<ElectrumClient, lwk_wollet::Error> {
ElectrumClient::new(&ElectrumUrl::new(&self.electrum_url, true, true))
}
pub(crate) fn get_electrum_config(&self) -> ElectrumConfig {
ElectrumConfig::new(self.network.into(), &self.electrum_url, true, true, 100)
}
pub fn mainnet() -> Self {
Config {
boltz_url: BOLTZ_MAINNET_URL_V2.to_owned(),

View File

@@ -20,6 +20,7 @@ use log::{debug, error, info, warn};
use lwk_wollet::bitcoin::hex::DisplayHex;
use lwk_wollet::hashes::{sha256, Hash};
use lwk_wollet::{elements::LockTime, ElementsNetwork};
use lwk_wollet::{BlockchainBackend, ElectrumClient, ElectrumUrl};
use tokio::sync::{watch, RwLock};
use tokio::time::MissedTickBehavior;
use tokio_stream::wrappers::BroadcastStream;
@@ -46,6 +47,9 @@ pub const LIQUID_CLAIM_TX_FEERATE_MSAT: f32 = 100.0;
pub const DEFAULT_DATA_DIR: &str = ".data";
pub(crate) trait ChainService: Send + Sync + BlockchainBackend {}
impl ChainService for ElectrumClient {}
pub struct LiquidSdk {
config: Config,
onchain_wallet: Arc<dyn OnchainWallet>,
@@ -81,13 +85,22 @@ impl LiquidSdk {
let swapper = Arc::new(BoltzSwapper::new(config.clone()));
let status_stream = Arc::<dyn SwapperStatusStream>::from(swapper.create_status_stream());
let chain_service = Arc::new(ElectrumClient::new(&ElectrumUrl::new(
&config.electrum_url,
true,
true,
))?);
let onchain_wallet = Arc::new(LiquidOnchainWallet::new(mnemonic, config.clone())?);
let send_swap_state_handler = SendSwapStateHandler::new(
config.clone(),
onchain_wallet.clone(),
persister.clone(),
swapper.clone(),
chain_service.clone(),
);
let receive_swap_state_handler = ReceiveSwapStateHandler::new(
onchain_wallet.clone(),
persister.clone(),
@@ -286,13 +299,7 @@ impl LiquidSdk {
let id = &send_swap.id;
let refund_tx_id = self.try_refund(send_swap).await?;
info!("Broadcast refund tx for Send Swap {id}. Tx id: {refund_tx_id}");
let send_swap_state_handler = SendSwapStateHandler::new(
self.config.clone(),
self.onchain_wallet.clone(),
self.persister.clone(),
self.swapper.clone(),
);
send_swap_state_handler
self.send_swap_state_handler
.update_swap_info(id, Pending, None, None, Some(&refund_tx_id))
.await?;
}
@@ -765,12 +772,7 @@ impl LiquidSdk {
let mut events_stream = self.event_manager.subscribe();
let mut maybe_payment: Option<Payment> = None;
let send_swap_state_handler = SendSwapStateHandler::new(
self.config.clone(),
self.onchain_wallet.clone(),
self.persister.clone(),
self.swapper.clone(),
);
let send_swap_state_handler = self.send_swap_state_handler.clone();
loop {
tokio::select! {
@@ -970,12 +972,6 @@ impl LiquidSdk {
let pending_send_swaps_by_refund_tx_id =
self.persister.list_pending_send_swaps_by_refund_tx_id()?;
let send_swap_state_handler = SendSwapStateHandler::new(
self.config.clone(),
self.onchain_wallet.clone(),
self.persister.clone(),
self.swapper.clone(),
);
for tx in self.onchain_wallet.transactions().await? {
let tx_id = tx.txid.to_string();
let is_tx_confirmed = tx.height.is_some();
@@ -1001,7 +997,7 @@ impl LiquidSdk {
}
} else if let Some(swap) = pending_send_swaps_by_refund_tx_id.get(&tx_id) {
if is_tx_confirmed {
send_swap_state_handler
self.send_swap_state_handler
.update_swap_info(&swap.id, Failed, None, None, None)
.await?;
}

View File

@@ -8,11 +8,11 @@ use log::{debug, error, info, warn};
use lwk_wollet::bitcoin::Witness;
use lwk_wollet::elements::Transaction;
use lwk_wollet::hashes::{sha256, Hash};
use lwk_wollet::BlockchainBackend;
use tokio::sync::broadcast;
use crate::model::PaymentState::{Complete, Created, Failed, Pending, TimedOut};
use crate::model::{Config, SendSwap};
use crate::sdk::ChainService;
use crate::swapper::Swapper;
use crate::wallet::OnchainWallet;
use crate::{ensure_sdk, get_invoice_amount};
@@ -21,12 +21,13 @@ use crate::{
model::{PaymentState, PaymentTxData, PaymentType},
persist::Persister,
};
#[derive(Clone)]
pub(crate) struct SendSwapStateHandler {
config: Config,
onchain_wallet: Arc<dyn OnchainWallet>,
persister: Arc<Persister>,
swapper: Arc<dyn Swapper>,
chain_service: Arc<dyn ChainService>,
subscription_notifier: broadcast::Sender<String>,
}
@@ -36,6 +37,7 @@ impl SendSwapStateHandler {
onchain_wallet: Arc<dyn OnchainWallet>,
persister: Arc<Persister>,
swapper: Arc<dyn Swapper>,
chain_service: Arc<dyn ChainService>,
) -> Self {
let (subscription_notifier, _) = broadcast::channel::<String>(30);
Self {
@@ -43,6 +45,7 @@ impl SendSwapStateHandler {
onchain_wallet,
persister,
swapper,
chain_service,
subscription_notifier,
}
}
@@ -194,8 +197,7 @@ impl SendSwapStateHandler {
)
.await?;
let electrum_client = self.config.get_electrum_client()?;
let lockup_tx_id = electrum_client.broadcast(&lockup_tx)?.to_string();
let lockup_tx_id = self.chain_service.broadcast(&lockup_tx)?.to_string();
debug!("Successfully broadcast lockup tx for Send Swap {swap_id}. Lockup tx id: {lockup_tx_id}");
Ok(lockup_tx)
@@ -262,7 +264,6 @@ impl SendSwapStateHandler {
info!("Retrieving preimage from non-cooperative claim tx");
let id = &swap.id;
let electrum_client = self.config.get_electrum_client()?;
let swap_script = swap.get_swap_script()?;
let swap_script_pk = swap_script
.to_address(self.config.network.into())?
@@ -270,7 +271,8 @@ impl SendSwapStateHandler {
debug!("Found Send Swap swap_script_pk: {swap_script_pk:?}");
// Get tx history of the swap script (lockup address)
let history: Vec<_> = electrum_client
let history: Vec<_> = self
.chain_service
.get_scripts_history(&[&swap_script_pk])?
.into_iter()
.flatten()
@@ -292,7 +294,8 @@ impl SendSwapStateHandler {
let claim_tx_id = claim_tx_entry.txid;
debug!("Send Swap {id} has claim tx {claim_tx_id}");
let claim_tx = electrum_client
let claim_tx = self
.chain_service
.get_transactions(&[claim_tx_id])
.map_err(|e| anyhow!("Failed to fetch claim tx {claim_tx_id}: {e}"))?
.first()

View File

@@ -6,6 +6,7 @@ use std::sync::Arc;
use anyhow::Result;
use async_trait::async_trait;
use boltz_client::error::Error;
use boltz_client::network::electrum::ElectrumConfig;
use boltz_client::network::Chain;
use boltz_client::swaps::boltzv2::{
self, BoltzApiClientV2, ClaimTxResponse, CreateReverseRequest, CreateReverseResponse,
@@ -108,13 +109,21 @@ pub trait Swapper: Send + Sync {
pub struct BoltzSwapper {
client: BoltzApiClientV2,
config: Config,
electrum_config: ElectrumConfig,
}
impl BoltzSwapper {
pub fn new(config: Config) -> BoltzSwapper {
BoltzSwapper {
client: BoltzApiClientV2::new(&config.boltz_url),
config,
config: config.clone(),
electrum_config: ElectrumConfig::new(
config.network.into(),
&config.electrum_url,
true,
true,
100,
),
}
}
@@ -128,7 +137,7 @@ impl BoltzSwapper {
Ok(LBtcSwapTxV2::new_refund(
swap_script.clone(),
output_address,
&self.config.get_electrum_config(),
&self.electrum_config,
self.config.boltz_url.clone(),
swap.id.to_string(),
)?)
@@ -194,8 +203,7 @@ impl Swapper for BoltzSwapper {
Network::Mainnet => None,
Network::Testnet => Some((&self.client, boltz_client::network::Chain::LiquidTestnet)),
};
let refund_tx_id =
refund_tx.broadcast(&tx, &self.config.get_electrum_config(), is_lowball)?;
let refund_tx_id = refund_tx.broadcast(&tx, &self.electrum_config, is_lowball)?;
info!(
"Successfully broadcast cooperative refund for Send Swap {}",
&swap.id
@@ -239,8 +247,7 @@ impl Swapper for BoltzSwapper {
Network::Mainnet => None,
Network::Testnet => Some((&self.client, boltz_client::network::Chain::LiquidTestnet)),
};
let refund_tx_id =
refund_tx.broadcast(&tx, &self.config.get_electrum_config(), is_lowball)?;
let refund_tx_id = refund_tx.broadcast(&tx, &self.electrum_config, is_lowball)?;
info!(
"Successfully broadcast non-cooperative refund for swap-in {}",
swap.id
@@ -305,7 +312,7 @@ impl Swapper for BoltzSwapper {
let claim_tx_wrapper = LBtcSwapTxV2::new_claim(
swap_script,
claim_address,
&self.config.get_electrum_config(),
&self.electrum_config,
self.config.boltz_url.clone(),
swap.id.clone(),
)?;
@@ -322,7 +329,7 @@ impl Swapper for BoltzSwapper {
let claim_tx_id = claim_tx_wrapper.broadcast(
&claim_tx,
&self.config.get_electrum_config(),
&self.electrum_config,
Some((&self.client, self.config.network.into())),
)?;
info!("Successfully broadcast claim tx {claim_tx_id} for Receive Swap {swap_id}");