1
+ use bdk_chain:: BlockId ;
2
+ use bdk_chain:: ConfirmationBlockTime ;
1
3
use bdk_wallet:: bitcoin:: hashes:: Hash ;
2
4
use bdk_wallet:: bitcoin:: secp256k1;
3
5
use bdk_wallet:: bitcoin:: { Amount , FeeRate , Network , Psbt , TxIn } ;
@@ -17,8 +19,6 @@ fn test_create_psbt() {
17
19
. unwrap ( ) ;
18
20
19
21
// Receive coins
20
- use bdk_chain:: BlockId ;
21
- use bdk_chain:: ConfirmationBlockTime ;
22
22
let anchor = ConfirmationBlockTime {
23
23
block_id : BlockId {
24
24
height : 100 ,
@@ -67,6 +67,76 @@ fn test_create_psbt() {
67
67
. any( |( _, ( fp, _) ) | fp. to_string( ) == "f6a5cb8b" ) ) ) ;
68
68
}
69
69
70
+ #[ test]
71
+ fn test_create_psbt_cltv ( ) {
72
+ use bdk_wallet:: CreatePsbtError ;
73
+ use bitcoin:: absolute:: LockTime ;
74
+ use miniscript:: plan:: Assets ;
75
+
76
+ let desc = get_test_single_sig_cltv ( ) ;
77
+ let mut wallet = Wallet :: create_single ( desc)
78
+ . network ( Network :: Regtest )
79
+ . create_wallet_no_persist ( )
80
+ . unwrap ( ) ;
81
+
82
+ // Receive coins
83
+ let anchor = ConfirmationBlockTime {
84
+ block_id : BlockId {
85
+ height : 99_999 ,
86
+ hash : Hash :: hash ( b"abc" ) ,
87
+ } ,
88
+ confirmation_time : 1234567000 ,
89
+ } ;
90
+ insert_checkpoint ( & mut wallet, anchor. block_id ) ;
91
+ let op = receive_output ( & mut wallet, Amount :: ONE_BTC , ReceiveTo :: Block ( anchor) ) ;
92
+
93
+ let mut rng = rand:: thread_rng ( ) ;
94
+
95
+ let addr = wallet. reveal_next_address ( KeychainKind :: External ) ;
96
+
97
+ // No assets fail
98
+ {
99
+ let mut params = psbt:: PsbtParams :: default ( ) ;
100
+ params
101
+ . add_utxos ( & [ op] )
102
+ . add_recipients ( [ ( addr. script_pubkey ( ) , Amount :: from_btc ( 0.42 ) . unwrap ( ) ) ] ) ;
103
+ let res = wallet. create_psbt ( params, & mut rng) ;
104
+ assert ! (
105
+ matches!( res, Err ( CreatePsbtError :: Plan ( err) ) if err == op) ,
106
+ "UTXO requires CLTV but the assets are insufficient" ,
107
+ ) ;
108
+ }
109
+
110
+ // Add assets ok
111
+ {
112
+ let mut params = psbt:: PsbtParams :: default ( ) ;
113
+ params
114
+ . add_utxos ( & [ op] )
115
+ . add_assets ( Assets :: new ( ) . after ( LockTime :: from_consensus ( 100_000 ) ) )
116
+ . add_recipients ( [ ( addr. script_pubkey ( ) , Amount :: from_btc ( 0.42 ) . unwrap ( ) ) ] ) ;
117
+ let _ = wallet
118
+ . create_psbt ( params, & mut rng)
119
+ . expect ( "Create psbt should succeed" ) ;
120
+ }
121
+
122
+ // New chain tip (no assets) ok
123
+ {
124
+ let block_id = BlockId {
125
+ height : 100_000 ,
126
+ hash : Hash :: hash ( b"123" ) ,
127
+ } ;
128
+ insert_checkpoint ( & mut wallet, block_id) ;
129
+
130
+ let mut params = psbt:: PsbtParams :: default ( ) ;
131
+ params
132
+ . add_utxos ( & [ op] )
133
+ . add_recipients ( [ ( addr. script_pubkey ( ) , Amount :: from_btc ( 0.42 ) . unwrap ( ) ) ] ) ;
134
+ let _ = wallet
135
+ . create_psbt ( params, & mut rng)
136
+ . expect ( "Create psbt should succeed" ) ;
137
+ }
138
+ }
139
+
70
140
#[ test]
71
141
#[ should_panic( expected = "InputIndexOutOfRange" ) ]
72
142
fn test_psbt_malformed_psbt_input_legacy ( ) {
0 commit comments