@@ -17,7 +17,7 @@ use bdk_chain::miniscript::{
17
17
descriptor:: { DescriptorSecretKey , SinglePubKey } ,
18
18
plan:: { Assets , Plan } ,
19
19
psbt:: PsbtExt ,
20
- Descriptor , DescriptorPublicKey ,
20
+ Descriptor , DescriptorPublicKey , ForEachKey ,
21
21
} ;
22
22
use bdk_chain:: ConfirmationBlockTime ;
23
23
use bdk_chain:: {
@@ -147,9 +147,14 @@ pub enum PsbtCmd<S: clap::Args> {
147
147
/// Create a new PSBT.
148
148
New {
149
149
/// Amount to send in satoshis
150
+ #[ clap( required = true ) ]
150
151
value : u64 ,
151
152
/// Recipient address
153
+ #[ clap( required = true ) ]
152
154
address : Address < NetworkUnchecked > ,
155
+ /// Set the feerate of the tx (sat/vbyte)
156
+ #[ clap( long, short, default_value = "1.0" ) ]
157
+ feerate : Option < f32 > ,
153
158
/// Set max absolute timelock (from consensus value)
154
159
#[ clap( long, short) ]
155
160
after : Option < u32 > ,
@@ -165,20 +170,21 @@ pub enum PsbtCmd<S: clap::Args> {
165
170
} ,
166
171
/// Sign with a hot signer
167
172
Sign {
168
- /// PSBT
169
- #[ clap( long) ]
170
- psbt : Option < String > ,
171
- /// Private descriptor
172
- #[ clap( long, short = 'd' ) ]
173
+ /// Private descriptor [env: DESCRIPTOR=]
174
+ #[ clap( long, short) ]
173
175
descriptor : Option < String > ,
176
+ /// PSBT
177
+ #[ clap( long, short, required = true ) ]
178
+ psbt : String ,
174
179
} ,
175
180
/// Extract transaction
176
181
Extract {
177
182
/// PSBT
183
+ #[ clap( long, short, required = true ) ]
178
184
psbt : String ,
179
185
/// Whether to try broadcasting the tx
180
- #[ clap( long, short = 'b' ) ]
181
- try_broadcast : bool ,
186
+ #[ clap( long, short) ]
187
+ broadcast : bool ,
182
188
#[ clap( flatten) ]
183
189
chain_specific : S ,
184
190
} ,
@@ -260,6 +266,7 @@ pub fn create_tx<O: ChainOracle>(
260
266
cs_algorithm : CoinSelectionAlgo ,
261
267
address : Address ,
262
268
value : u64 ,
269
+ feerate : f32 ,
263
270
) -> anyhow:: Result < ( Psbt , Option < ChangeInfo > ) >
264
271
where
265
272
O :: Error : std:: error:: Error + Send + Sync + ' static ,
@@ -288,7 +295,7 @@ where
288
295
. map ( |( plan, utxo) | {
289
296
Candidate :: new (
290
297
utxo. txout . value . to_sat ( ) ,
291
- plan. satisfaction_weight ( ) as u32 ,
298
+ plan. satisfaction_weight ( ) as u64 ,
292
299
plan. witness_version ( ) . is_some ( ) ,
293
300
)
294
301
} )
@@ -330,9 +337,12 @@ where
330
337
outputs : TargetOutputs :: fund_outputs (
331
338
outputs
332
339
. iter ( )
333
- . map ( |output| ( output. weight ( ) . to_wu ( ) as u32 , output. value . to_sat ( ) ) ) ,
340
+ . map ( |output| ( output. weight ( ) . to_wu ( ) , output. value . to_sat ( ) ) ) ,
334
341
) ,
335
- fee : TargetFee :: default ( ) ,
342
+ fee : TargetFee {
343
+ rate : FeeRate :: from_sat_per_vb ( feerate) ,
344
+ ..Default :: default ( )
345
+ } ,
336
346
} ;
337
347
338
348
let change_policy = ChangePolicy {
@@ -444,7 +454,7 @@ pub fn handle_commands<CS: clap::Subcommand, S: clap::Args>(
444
454
chain : & Mutex < LocalChain > ,
445
455
db : & Mutex < Store < ChangeSet > > ,
446
456
network : Network ,
447
- broadcast : impl FnOnce ( S , & Transaction ) -> anyhow:: Result < ( ) > ,
457
+ broadcast_fn : impl FnOnce ( S , & Transaction ) -> anyhow:: Result < ( ) > ,
448
458
cmd : Commands < CS , S > ,
449
459
) -> anyhow:: Result < ( ) > {
450
460
match cmd {
@@ -584,6 +594,7 @@ pub fn handle_commands<CS: clap::Subcommand, S: clap::Args>(
584
594
PsbtCmd :: New {
585
595
value,
586
596
address,
597
+ feerate,
587
598
after,
588
599
older,
589
600
coin_select,
@@ -596,26 +607,30 @@ pub fn handle_commands<CS: clap::Subcommand, S: clap::Args>(
596
607
let chain = chain. lock ( ) . unwrap ( ) ;
597
608
598
609
// collect assets we can sign for
599
- let mut assets = Assets :: new ( ) ;
610
+ let mut pks = vec ! [ ] ;
611
+ for ( _, desc) in graph. index . keychains ( ) {
612
+ desc. for_each_key ( |k| {
613
+ pks. push ( k. clone ( ) ) ;
614
+ true
615
+ } ) ;
616
+ }
617
+ let mut assets = Assets :: new ( ) . add ( pks) ;
600
618
if let Some ( n) = after {
601
619
assets = assets. after ( absolute:: LockTime :: from_consensus ( n) ) ;
602
620
}
603
621
if let Some ( n) = older {
604
622
assets = assets. older ( relative:: LockTime :: from_consensus ( n) ?) ;
605
623
}
606
- for ( _, desc) in graph. index . keychains ( ) {
607
- match desc {
608
- Descriptor :: Wpkh ( wpkh) => {
609
- assets = assets. add ( wpkh. clone ( ) . into_inner ( ) ) ;
610
- }
611
- Descriptor :: Tr ( tr) => {
612
- assets = assets. add ( tr. internal_key ( ) . clone ( ) ) ;
613
- }
614
- _ => bail ! ( "unsupported descriptor type" ) ,
615
- }
616
- }
617
624
618
- create_tx ( & mut graph, & * chain, & assets, coin_select, address, value) ?
625
+ create_tx (
626
+ & mut graph,
627
+ & * chain,
628
+ & assets,
629
+ coin_select,
630
+ address,
631
+ value,
632
+ feerate. expect ( "must have feerate" ) ,
633
+ ) ?
619
634
} ;
620
635
621
636
if let Some ( ChangeInfo {
@@ -659,7 +674,7 @@ pub fn handle_commands<CS: clap::Subcommand, S: clap::Args>(
659
674
Ok ( ( ) )
660
675
}
661
676
PsbtCmd :: Sign { psbt, descriptor } => {
662
- let mut psbt = Psbt :: from_str ( psbt. unwrap_or_default ( ) . as_str ( ) ) ?;
677
+ let mut psbt = Psbt :: from_str ( & psbt) ?;
663
678
664
679
let desc_str = match descriptor {
665
680
Some ( s) => s,
@@ -697,20 +712,20 @@ pub fn handle_commands<CS: clap::Subcommand, S: clap::Args>(
697
712
Ok ( ( ) )
698
713
}
699
714
PsbtCmd :: Extract {
700
- try_broadcast ,
715
+ broadcast ,
701
716
chain_specific,
702
717
psbt,
703
718
} => {
704
- let mut psbt = Psbt :: from_str ( psbt. as_str ( ) ) ?;
719
+ let mut psbt = Psbt :: from_str ( & psbt) ?;
705
720
psbt. finalize_mut ( & Secp256k1 :: new ( ) )
706
721
. map_err ( |errors| anyhow:: anyhow!( "failed to finalize PSBT {errors:?}" ) ) ?;
707
722
708
723
let tx = psbt. extract_tx ( ) ?;
709
724
710
- if try_broadcast {
725
+ if broadcast {
711
726
let mut graph = graph. lock ( ) . unwrap ( ) ;
712
727
713
- match broadcast ( chain_specific, & tx) {
728
+ match broadcast_fn ( chain_specific, & tx) {
714
729
Ok ( _) => {
715
730
println ! ( "Broadcasted Tx: {}" , tx. compute_txid( ) ) ;
716
731
0 commit comments