feat: add MVP transaction builder type
This commit is contained in:
parent
372f79a10f
commit
1521811e9b
@ -1,7 +1,7 @@
|
|||||||
namespace bdk {};
|
namespace bdk {};
|
||||||
|
|
||||||
// ------------------------------------------------------------------------
|
// ------------------------------------------------------------------------
|
||||||
// bdk crate
|
// bdk crate - root module
|
||||||
// ------------------------------------------------------------------------
|
// ------------------------------------------------------------------------
|
||||||
|
|
||||||
enum KeychainKind {
|
enum KeychainKind {
|
||||||
@ -86,6 +86,17 @@ interface Wallet {
|
|||||||
|
|
||||||
interface Update {};
|
interface Update {};
|
||||||
|
|
||||||
|
interface TxBuilder {
|
||||||
|
constructor();
|
||||||
|
|
||||||
|
TxBuilder add_recipient(Script script, u64 amount);
|
||||||
|
|
||||||
|
TxBuilder fee_rate(float sat_per_vbyte);
|
||||||
|
|
||||||
|
[Throws=BdkError]
|
||||||
|
string finish([ByRef] Wallet wallet);
|
||||||
|
};
|
||||||
|
|
||||||
// ------------------------------------------------------------------------
|
// ------------------------------------------------------------------------
|
||||||
// bdk crate - descriptor module
|
// bdk crate - descriptor module
|
||||||
// ------------------------------------------------------------------------
|
// ------------------------------------------------------------------------
|
||||||
|
|||||||
@ -6,6 +6,7 @@ mod psbt;
|
|||||||
mod wallet;
|
mod wallet;
|
||||||
|
|
||||||
use bdk::bitcoin::address::{NetworkChecked, NetworkUnchecked};
|
use bdk::bitcoin::address::{NetworkChecked, NetworkUnchecked};
|
||||||
|
use bdk::bitcoin::blockdata::script::ScriptBuf as BdkScriptBuf;
|
||||||
use bdk::bitcoin::Address as BdkAddress;
|
use bdk::bitcoin::Address as BdkAddress;
|
||||||
use bdk::bitcoin::Network as BdkNetwork;
|
use bdk::bitcoin::Network as BdkNetwork;
|
||||||
use bdk::wallet::AddressIndex as BdkAddressIndex;
|
use bdk::wallet::AddressIndex as BdkAddressIndex;
|
||||||
@ -23,6 +24,7 @@ use crate::keys::DerivationPath;
|
|||||||
use crate::keys::DescriptorPublicKey;
|
use crate::keys::DescriptorPublicKey;
|
||||||
use crate::keys::DescriptorSecretKey;
|
use crate::keys::DescriptorSecretKey;
|
||||||
use crate::keys::Mnemonic;
|
use crate::keys::Mnemonic;
|
||||||
|
use crate::wallet::TxBuilder;
|
||||||
use crate::wallet::Update;
|
use crate::wallet::Update;
|
||||||
use crate::wallet::Wallet;
|
use crate::wallet::Wallet;
|
||||||
use bdk::keys::bip39::WordCount;
|
use bdk::keys::bip39::WordCount;
|
||||||
@ -453,11 +455,11 @@ impl Address {
|
|||||||
self.inner.network.into()
|
self.inner.network.into()
|
||||||
}
|
}
|
||||||
|
|
||||||
// fn script_pubkey(&self) -> Arc<Script> {
|
fn script_pubkey(&self) -> Arc<Script> {
|
||||||
// Arc::new(Script {
|
Arc::new(Script {
|
||||||
// inner: self.inner.script_pubkey(),
|
inner: self.inner.script_pubkey(),
|
||||||
// })
|
})
|
||||||
// }
|
}
|
||||||
|
|
||||||
fn to_qr_uri(&self) -> String {
|
fn to_qr_uri(&self) -> String {
|
||||||
self.inner.to_qr_uri()
|
self.inner.to_qr_uri()
|
||||||
@ -495,24 +497,24 @@ impl From<Address> for BdkAddress {
|
|||||||
// program: Vec<u8>,
|
// program: Vec<u8>,
|
||||||
// },
|
// },
|
||||||
// }
|
// }
|
||||||
//
|
|
||||||
// /// A Bitcoin script.
|
/// A Bitcoin script.
|
||||||
// #[derive(Clone, Debug, PartialEq, Eq)]
|
#[derive(Clone, Debug, PartialEq, Eq)]
|
||||||
// pub struct Script {
|
pub struct Script {
|
||||||
// inner: BdkScript,
|
inner: BdkScriptBuf,
|
||||||
// }
|
}
|
||||||
//
|
|
||||||
// impl Script {
|
impl Script {
|
||||||
// fn new(raw_output_script: Vec<u8>) -> Self {
|
fn new(raw_output_script: Vec<u8>) -> Self {
|
||||||
// let script: BdkScript = BdkScript::from(raw_output_script);
|
let script: BdkScriptBuf = BdkScriptBuf::from(raw_output_script);
|
||||||
// Script { inner: script }
|
Script { inner: script }
|
||||||
// }
|
}
|
||||||
//
|
|
||||||
// fn to_bytes(&self) -> Vec<u8> {
|
fn to_bytes(&self) -> Vec<u8> {
|
||||||
// self.inner.to_bytes()
|
self.inner.to_bytes()
|
||||||
// }
|
}
|
||||||
// }
|
}
|
||||||
//
|
|
||||||
// impl From<BdkScript> for Script {
|
// impl From<BdkScript> for Script {
|
||||||
// fn from(bdk_script: BdkScript) -> Self {
|
// fn from(bdk_script: BdkScript) -> Self {
|
||||||
// Script { inner: bdk_script }
|
// Script { inner: bdk_script }
|
||||||
|
|||||||
@ -1,10 +1,11 @@
|
|||||||
use crate::descriptor::Descriptor;
|
use crate::descriptor::Descriptor;
|
||||||
use crate::Balance;
|
|
||||||
use crate::{AddressIndex, AddressInfo, Network};
|
use crate::{AddressIndex, AddressInfo, Network};
|
||||||
|
use crate::{Balance, Script};
|
||||||
use bdk::wallet::Update as BdkUpdate;
|
use bdk::wallet::Update as BdkUpdate;
|
||||||
use bdk::Error as BdkError;
|
|
||||||
use bdk::Wallet as BdkWallet;
|
use bdk::Wallet as BdkWallet;
|
||||||
|
use bdk::{Error as BdkError, FeeRate};
|
||||||
use std::sync::{Arc, Mutex, MutexGuard};
|
use std::sync::{Arc, Mutex, MutexGuard};
|
||||||
|
use bdk::bitcoin::blockdata::script::ScriptBuf as BdkScriptBuf;
|
||||||
|
|
||||||
#[derive(Debug)]
|
#[derive(Debug)]
|
||||||
pub struct Wallet {
|
pub struct Wallet {
|
||||||
@ -314,51 +315,52 @@ pub struct Update(pub(crate) BdkUpdate);
|
|||||||
// }
|
// }
|
||||||
// }
|
// }
|
||||||
//
|
//
|
||||||
// /// A transaction builder.
|
/// A transaction builder.
|
||||||
// /// After creating the TxBuilder, you set options on it until finally calling finish to consume the builder and generate the transaction.
|
/// After creating the TxBuilder, you set options on it until finally calling finish to consume the builder and generate the transaction.
|
||||||
// /// Each method on the TxBuilder returns an instance of a new TxBuilder with the option set/added.
|
/// Each method on the TxBuilder returns an instance of a new TxBuilder with the option set/added.
|
||||||
// #[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
// pub(crate) struct TxBuilder {
|
pub(crate) struct TxBuilder {
|
||||||
// pub(crate) recipients: Vec<(BdkScript, u64)>,
|
pub(crate) recipients: Vec<(BdkScriptBuf, u64)>,
|
||||||
// pub(crate) utxos: Vec<OutPoint>,
|
// pub(crate) utxos: Vec<OutPoint>,
|
||||||
// pub(crate) unspendable: HashSet<OutPoint>,
|
// pub(crate) unspendable: HashSet<OutPoint>,
|
||||||
// pub(crate) change_policy: ChangeSpendPolicy,
|
// pub(crate) change_policy: ChangeSpendPolicy,
|
||||||
// pub(crate) manually_selected_only: bool,
|
// pub(crate) manually_selected_only: bool,
|
||||||
// pub(crate) fee_rate: Option<f32>,
|
pub(crate) fee_rate: Option<f32>,
|
||||||
// pub(crate) fee_absolute: Option<u64>,
|
// pub(crate) fee_absolute: Option<u64>,
|
||||||
// pub(crate) drain_wallet: bool,
|
// pub(crate) drain_wallet: bool,
|
||||||
// pub(crate) drain_to: Option<BdkScript>,
|
// pub(crate) drain_to: Option<BdkScript>,
|
||||||
// pub(crate) rbf: Option<RbfValue>,
|
// pub(crate) rbf: Option<RbfValue>,
|
||||||
// pub(crate) data: Vec<u8>,
|
// pub(crate) data: Vec<u8>,
|
||||||
// }
|
}
|
||||||
//
|
|
||||||
// impl TxBuilder {
|
impl TxBuilder {
|
||||||
// pub(crate) fn new() -> Self {
|
pub(crate) fn new() -> Self {
|
||||||
// TxBuilder {
|
TxBuilder {
|
||||||
// recipients: Vec::new(),
|
recipients: Vec::new(),
|
||||||
// utxos: Vec::new(),
|
// utxos: Vec::new(),
|
||||||
// unspendable: HashSet::new(),
|
// unspendable: HashSet::new(),
|
||||||
// change_policy: ChangeSpendPolicy::ChangeAllowed,
|
// change_policy: ChangeSpendPolicy::ChangeAllowed,
|
||||||
// manually_selected_only: false,
|
// manually_selected_only: false,
|
||||||
// fee_rate: None,
|
fee_rate: None,
|
||||||
// fee_absolute: None,
|
// fee_absolute: None,
|
||||||
// drain_wallet: false,
|
// drain_wallet: false,
|
||||||
// drain_to: None,
|
// drain_to: None,
|
||||||
// rbf: None,
|
// rbf: None,
|
||||||
// data: Vec::new(),
|
// data: Vec::new(),
|
||||||
// }
|
}
|
||||||
// }
|
}
|
||||||
//
|
|
||||||
// /// Add a recipient to the internal list.
|
/// Add a recipient to the internal list.
|
||||||
// pub(crate) fn add_recipient(&self, script: Arc<Script>, amount: u64) -> Arc<Self> {
|
pub(crate) fn add_recipient(&self, script: Arc<Script>, amount: u64) -> Arc<Self> {
|
||||||
// let mut recipients: Vec<(BdkScript, u64)> = self.recipients.clone();
|
let mut recipients: Vec<(BdkScriptBuf, u64)> = self.recipients.clone();
|
||||||
// recipients.append(&mut vec![(script.inner.clone(), amount)]);
|
recipients.append(&mut vec![(script.inner.clone(), amount)]);
|
||||||
// Arc::new(TxBuilder {
|
|
||||||
// recipients,
|
Arc::new(TxBuilder {
|
||||||
// ..self.clone()
|
recipients,
|
||||||
// })
|
..self.clone()
|
||||||
// }
|
})
|
||||||
//
|
}
|
||||||
|
|
||||||
// pub(crate) fn set_recipients(&self, recipients: Vec<ScriptAmount>) -> Arc<Self> {
|
// pub(crate) fn set_recipients(&self, recipients: Vec<ScriptAmount>) -> Arc<Self> {
|
||||||
// let recipients = recipients
|
// let recipients = recipients
|
||||||
// .iter()
|
// .iter()
|
||||||
@ -369,7 +371,7 @@ pub struct Update(pub(crate) BdkUpdate);
|
|||||||
// ..self.clone()
|
// ..self.clone()
|
||||||
// })
|
// })
|
||||||
// }
|
// }
|
||||||
//
|
|
||||||
// /// Add a utxo to the internal list of unspendable utxos. It’s important to note that the "must-be-spent"
|
// /// Add a utxo to the internal list of unspendable utxos. It’s important to note that the "must-be-spent"
|
||||||
// /// utxos added with [TxBuilder.addUtxo] have priority over this. See the Rust docs of the two linked methods for more details.
|
// /// utxos added with [TxBuilder.addUtxo] have priority over this. See the Rust docs of the two linked methods for more details.
|
||||||
// pub(crate) fn add_unspendable(&self, unspendable: OutPoint) -> Arc<Self> {
|
// pub(crate) fn add_unspendable(&self, unspendable: OutPoint) -> Arc<Self> {
|
||||||
@ -433,13 +435,13 @@ pub struct Update(pub(crate) BdkUpdate);
|
|||||||
// })
|
// })
|
||||||
// }
|
// }
|
||||||
//
|
//
|
||||||
// /// Set a custom fee rate.
|
/// Set a custom fee rate.
|
||||||
// pub(crate) fn fee_rate(&self, sat_per_vb: f32) -> Arc<Self> {
|
pub(crate) fn fee_rate(&self, sat_per_vb: f32) -> Arc<Self> {
|
||||||
// Arc::new(TxBuilder {
|
Arc::new(TxBuilder {
|
||||||
// fee_rate: Some(sat_per_vb),
|
fee_rate: Some(sat_per_vb),
|
||||||
// ..self.clone()
|
..self.clone()
|
||||||
// })
|
})
|
||||||
// }
|
}
|
||||||
//
|
//
|
||||||
// /// Set an absolute fee.
|
// /// Set an absolute fee.
|
||||||
// pub(crate) fn fee_absolute(&self, fee_amount: u64) -> Arc<Self> {
|
// pub(crate) fn fee_absolute(&self, fee_amount: u64) -> Arc<Self> {
|
||||||
@ -498,13 +500,17 @@ pub struct Update(pub(crate) BdkUpdate);
|
|||||||
// })
|
// })
|
||||||
// }
|
// }
|
||||||
//
|
//
|
||||||
// /// Finish building the transaction. Returns the BIP174 PSBT.
|
/// Finish building the transaction. Returns the BIP174 PSBT.
|
||||||
// pub(crate) fn finish(&self, wallet: &Wallet) -> Result<TxBuilderResult, BdkError> {
|
/// TODO: The TxBuilder in bdk returns a Psbt type
|
||||||
// let wallet = wallet.get_wallet();
|
pub(crate) fn finish(&self, wallet: &Wallet) -> Result<String, BdkError> {
|
||||||
// let mut tx_builder = wallet.build_tx();
|
// TODO: I had to change the wallet here to be mutable. Why is that now required with the 1.0 API?
|
||||||
// for (script, amount) in &self.recipients {
|
let mut wallet = wallet.get_wallet();
|
||||||
// tx_builder.add_recipient(script.clone(), *amount);
|
let mut tx_builder = wallet.build_tx();
|
||||||
// }
|
// TODO: I'm not yet clear on the Script/ScriptBuf differences and whether this is the best
|
||||||
|
// way to do this.
|
||||||
|
for (script, amount) in &self.recipients {
|
||||||
|
tx_builder.add_recipient(script.clone(), *amount);
|
||||||
|
}
|
||||||
// tx_builder.change_policy(self.change_policy);
|
// tx_builder.change_policy(self.change_policy);
|
||||||
// if !self.utxos.is_empty() {
|
// if !self.utxos.is_empty() {
|
||||||
// let bdk_utxos: Vec<BdkOutPoint> = self.utxos.iter().map(BdkOutPoint::from).collect();
|
// let bdk_utxos: Vec<BdkOutPoint> = self.utxos.iter().map(BdkOutPoint::from).collect();
|
||||||
@ -519,9 +525,9 @@ pub struct Update(pub(crate) BdkUpdate);
|
|||||||
// if self.manually_selected_only {
|
// if self.manually_selected_only {
|
||||||
// tx_builder.manually_selected_only();
|
// tx_builder.manually_selected_only();
|
||||||
// }
|
// }
|
||||||
// if let Some(sat_per_vb) = self.fee_rate {
|
if let Some(sat_per_vb) = self.fee_rate {
|
||||||
// tx_builder.fee_rate(FeeRate::from_sat_per_vb(sat_per_vb));
|
tx_builder.fee_rate(FeeRate::from_sat_per_vb(sat_per_vb));
|
||||||
// }
|
}
|
||||||
// if let Some(fee_amount) = self.fee_absolute {
|
// if let Some(fee_amount) = self.fee_absolute {
|
||||||
// tx_builder.fee_absolute(fee_amount);
|
// tx_builder.fee_absolute(fee_amount);
|
||||||
// }
|
// }
|
||||||
@ -544,17 +550,10 @@ pub struct Update(pub(crate) BdkUpdate);
|
|||||||
// if !&self.data.is_empty() {
|
// if !&self.data.is_empty() {
|
||||||
// tx_builder.add_data(self.data.as_slice());
|
// tx_builder.add_data(self.data.as_slice());
|
||||||
// }
|
// }
|
||||||
//
|
|
||||||
// tx_builder
|
tx_builder.finish().map(|psbt| psbt.serialize_hex())
|
||||||
// .finish()
|
}
|
||||||
// .map(|(psbt, tx_details)| TxBuilderResult {
|
}
|
||||||
// psbt: Arc::new(PartiallySignedTransaction {
|
|
||||||
// inner: Mutex::new(psbt),
|
|
||||||
// }),
|
|
||||||
// transaction_details: TransactionDetails::from(tx_details),
|
|
||||||
// })
|
|
||||||
// }
|
|
||||||
// }
|
|
||||||
//
|
//
|
||||||
// /// The BumpFeeTxBuilder is used to bump the fee on a transaction that has been broadcast and has its RBF flag set to true.
|
// /// The BumpFeeTxBuilder is used to bump the fee on a transaction that has been broadcast and has its RBF flag set to true.
|
||||||
// #[derive(Clone)]
|
// #[derive(Clone)]
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user