]> Untitled Git - bdk/commitdiff
tx_builder: Support setting explicit nSequence for foreign inputs
authorSteven Roose <steven@stevenroose.org>
Fri, 2 Feb 2024 01:24:39 +0000 (01:24 +0000)
committerSteven Roose <steven@stevenroose.org>
Fri, 2 Feb 2024 02:03:53 +0000 (02:03 +0000)
crates/bdk/src/types.rs
crates/bdk/src/wallet/mod.rs
crates/bdk/src/wallet/tx_builder.rs

index b52635e5502e1697d95a7d3985dfd7292531534d..5f2173596ebba59f77ead95167b912ba19e1dffd 100644 (file)
@@ -14,7 +14,7 @@ use core::convert::AsRef;
 use core::ops::Sub;
 
 use bdk_chain::ConfirmationTime;
-use bitcoin::blockdata::transaction::{OutPoint, TxOut};
+use bitcoin::blockdata::transaction::{OutPoint, Sequence, TxOut};
 use bitcoin::{psbt, Weight};
 
 use serde::{Deserialize, Serialize};
@@ -197,6 +197,8 @@ pub enum Utxo {
     Foreign {
         /// The location of the output.
         outpoint: OutPoint,
+        /// The nSequence value to set for this input.
+        sequence: Option<Sequence>,
         /// The information about the input we require to add it to a PSBT.
         // Box it to stop the type being too big.
         psbt_input: Box<psbt::Input>,
@@ -219,6 +221,7 @@ impl Utxo {
             Utxo::Foreign {
                 outpoint,
                 psbt_input,
+                ..
             } => {
                 if let Some(prev_tx) = &psbt_input.non_witness_utxo {
                     return &prev_tx.output[outpoint.vout as usize];
@@ -232,6 +235,14 @@ impl Utxo {
             }
         }
     }
+
+    /// Get the sequence number if an explicit sequence number has to be set for this input.
+    pub fn sequence(&self) -> Option<Sequence> {
+        match self {
+            Utxo::Local(_) => None,
+            Utxo::Foreign { sequence, .. } => *sequence,
+        }
+    }
 }
 
 #[cfg(test)]
index c6c922d5570448e34f034e9c6f4a3a370388a69d..a6b4f9874ad3df0b1a1445ad05d9eee3c07ca43b 100644 (file)
@@ -1400,6 +1400,7 @@ impl<D> Wallet<D> {
             }
         };
 
+        // The nSequence to be by default for inputs unless an explicit sequence is specified.
         let n_sequence = match (params.rbf, requirements.csv) {
             // No RBF or CSV but there's an nLockTime, so the nSequence cannot be final
             (None, None) if lock_time != absolute::LockTime::ZERO => {
@@ -1558,7 +1559,7 @@ impl<D> Wallet<D> {
             .map(|u| bitcoin::TxIn {
                 previous_output: u.outpoint(),
                 script_sig: ScriptBuf::default(),
-                sequence: n_sequence,
+                sequence: u.sequence().unwrap_or(n_sequence),
                 witness: Witness::new(),
             })
             .collect();
@@ -1738,6 +1739,7 @@ impl<D> Wallet<D> {
                             satisfaction_weight,
                             utxo: Utxo::Foreign {
                                 outpoint: txin.previous_output,
+                                sequence: Some(txin.sequence),
                                 psbt_input: Box::new(psbt::Input {
                                     witness_utxo: Some(txout.clone()),
                                     non_witness_utxo: Some(prev_tx.clone()),
@@ -2218,8 +2220,9 @@ impl<D> Wallet<D> {
                         }
                 }
                 Utxo::Foreign {
-                    psbt_input: foreign_psbt_input,
                     outpoint,
+                    psbt_input: foreign_psbt_input,
+                    ..
                 } => {
                     let is_taproot = foreign_psbt_input
                         .witness_utxo
index f914aaefa7959dc2aaba84ff7f956562dd8db8c3..4af7b3bf44ca4a76cae76eebe8f11e63a0690359 100644 (file)
@@ -389,6 +389,22 @@ impl<'a, D, Cs: CoinSelectionAlgorithm, Ctx: TxBuilderContext> TxBuilder<'a, D,
         outpoint: OutPoint,
         psbt_input: psbt::Input,
         satisfaction_weight: usize,
+    ) -> Result<&mut Self, AddForeignUtxoError> {
+        self.add_foreign_utxo_with_sequence(
+            outpoint,
+            psbt_input,
+            satisfaction_weight,
+            Sequence::MAX,
+        )
+    }
+
+    /// Same as [add_foreign_utxo](TxBuilder::add_foreign_utxo) but allows to set the nSequence value.
+    pub fn add_foreign_utxo_with_sequence(
+        &mut self,
+        outpoint: OutPoint,
+        psbt_input: psbt::Input,
+        satisfaction_weight: usize,
+        sequence: Sequence,
     ) -> Result<&mut Self, AddForeignUtxoError> {
         if psbt_input.witness_utxo.is_none() {
             match psbt_input.non_witness_utxo.as_ref() {
@@ -413,6 +429,7 @@ impl<'a, D, Cs: CoinSelectionAlgorithm, Ctx: TxBuilderContext> TxBuilder<'a, D,
             satisfaction_weight,
             utxo: Utxo::Foreign {
                 outpoint,
+                sequence: Some(sequence),
                 psbt_input: Box::new(psbt_input),
             },
         });