@@ -2,18 +2,15 @@ extern crate core;
2
2
3
3
use std:: { fs, path:: PathBuf , str:: FromStr } ;
4
4
5
- use base64:: { prelude:: BASE64_STANDARD , Engine } ;
6
5
use clap:: { Parser , Subcommand } ;
7
6
use jsonrpsee:: {
8
7
core:: { client:: Error , ClientError } ,
9
8
http_client:: { HttpClient , HttpClientBuilder } ,
10
9
} ;
11
10
use protocol:: {
12
11
bitcoin:: { Amount , FeeRate , OutPoint , Txid } ,
13
- hasher:: { KeyHasher , SpaceKey } ,
14
- opcodes:: OP_SETALL ,
15
- sname:: { NameLike , SName } ,
16
- Covenant , FullSpaceOut ,
12
+ hasher:: KeyHasher ,
13
+ slabel:: SLabel ,
17
14
} ;
18
15
use serde:: { Deserialize , Serialize } ;
19
16
use spaced:: {
@@ -32,14 +29,14 @@ use wallet::export::WalletExport;
32
29
pub struct Args {
33
30
/// Bitcoin network to use
34
31
#[ arg( long, env = "SPACED_CHAIN" ) ]
35
- chain : spaced :: config :: ExtendedNetwork ,
32
+ chain : ExtendedNetwork ,
36
33
/// Spaced RPC URL [default: based on specified chain]
37
34
#[ arg( long) ]
38
35
spaced_rpc_url : Option < String > ,
39
36
/// Specify wallet to use
40
37
#[ arg( long, short, global = true , default_value = "default" ) ]
41
38
wallet : String ,
42
- /// Custom dust amount in sat for auction outputs
39
+ /// Custom dust amount in sat for bid outputs
43
40
#[ arg( long, short, global = true ) ]
44
41
dust : Option < u64 > ,
45
42
/// Force invalid transaction (for testing only)
@@ -53,21 +50,15 @@ pub struct Args {
53
50
enum Commands {
54
51
/// Generate a new wallet
55
52
#[ command( name = "createwallet" ) ]
56
- CreateWallet {
57
- #[ arg( default_value = "default" ) ]
58
- name : String ,
59
- } ,
53
+ CreateWallet ,
60
54
/// Load a wallet
61
55
#[ command( name = "loadwallet" ) ]
62
- LoadWallet {
63
- #[ arg( default_value = "default" ) ]
64
- name : String ,
65
- } ,
56
+ LoadWallet ,
66
57
/// Export a wallet
67
58
#[ command( name = "exportwallet" ) ]
68
59
ExportWallet {
69
- # [ arg ( default_value = "default" ) ]
70
- name : String ,
60
+ // Destination path to export json file
61
+ path : PathBuf ,
71
62
} ,
72
63
/// Import a wallet
73
64
#[ command( name = "importwallet" ) ]
@@ -77,10 +68,7 @@ enum Commands {
77
68
} ,
78
69
/// Export a wallet
79
70
#[ command( name = "getwalletinfo" ) ]
80
- GetWalletInfo {
81
- #[ arg( default_value = "default" ) ]
82
- name : String ,
83
- } ,
71
+ GetWalletInfo ,
84
72
/// Export a wallet
85
73
#[ command( name = "getserverinfo" ) ]
86
74
GetServerInfo ,
@@ -164,8 +152,8 @@ enum Commands {
164
152
#[ command( name = "balance" ) ]
165
153
Balance ,
166
154
/// Pre-create outputs that can be auctioned off during the bidding process
167
- #[ command( name = "createauctionoutputs " ) ]
168
- CreateAuctionOutputs {
155
+ #[ command( name = "createbidouts " ) ]
156
+ CreateBidOuts {
169
157
/// Number of output pairs to create
170
158
/// Each pair can be used to make a bid
171
159
pairs : u8 ,
@@ -188,20 +176,21 @@ enum Commands {
188
176
outpoint : OutPoint ,
189
177
} ,
190
178
/// Get the estimated rollout batch for the specified interval
191
- #[ command( name = "getrolloutestimate " ) ]
192
- GetRolloutEstimate {
179
+ #[ command( name = "getrollout " ) ]
180
+ GetRollout {
193
181
// Get the estimated rollout for the target interval. Every ~144 blocks (a rollout interval),
194
182
// 10 spaces are released for auction. Specify 0 [default] for the coming interval, 1
195
183
// for the interval after and so on.
196
184
#[ arg( default_value = "0" ) ]
197
185
target_interval : usize ,
198
186
} ,
199
- /// Associate the specified data with a given space (experimental may be removed)
200
- #[ command( name = "setdata" ) ]
201
- SetData {
187
+ /// Associate the specified data with a given space (not recommended use Fabric instead)
188
+ /// If for whatever reason it's not possible to use other protocols, then you may use this.
189
+ #[ command( name = "setrawfallback" ) ]
190
+ SetRawFallback {
202
191
/// Space name
203
192
space : String ,
204
- /// Base64 encoded data
193
+ /// Hex encoded data
205
194
data : String ,
206
195
/// Fee rate to use in sat/vB
207
196
#[ arg( long, short) ]
@@ -221,8 +210,8 @@ enum Commands {
221
210
ListSpaces ,
222
211
/// List unspent auction outputs i.e. outputs that can be
223
212
/// auctioned off in the bidding process
224
- #[ command( name = "listauctionoutputs " ) ]
225
- ListAuctionOutputs ,
213
+ #[ command( name = "listbidouts " ) ]
214
+ ListBidOuts ,
226
215
/// List unspent coins owned by wallet
227
216
#[ command( name = "listunspent" ) ]
228
217
ListUnspent ,
@@ -234,12 +223,16 @@ enum Commands {
234
223
/// compatible with most bitcoin wallets
235
224
#[ command( name = "getnewaddress" ) ]
236
225
GetCoinAddress ,
237
- /// Calculate a spacehash from the specified space name
238
- #[ command( name = "spacehash" ) ]
239
- SpaceHash {
240
- /// The space name
241
- space : String ,
226
+ /// Force spend an output owned by wallet (for testing only)
227
+ #[ command( name = "forcespend" ) ]
228
+ ForceSpend {
229
+ outpoint : OutPoint ,
230
+ #[ arg( long, short) ]
231
+ fee_rate : u64 ,
242
232
} ,
233
+ /// DNS encodes the space and calculates the SHA-256 hash
234
+ #[ command( name = "hashspace" ) ]
235
+ HashSpace { space : String } ,
243
236
}
244
237
245
238
struct SpaceCli {
@@ -275,7 +268,7 @@ impl SpaceCli {
275
268
async fn send_request (
276
269
& self ,
277
270
req : Option < RpcWalletRequest > ,
278
- auction_outputs : Option < u8 > ,
271
+ bidouts : Option < u8 > ,
279
272
fee_rate : Option < u64 > ,
280
273
) -> Result < ( ) , ClientError > {
281
274
let fee_rate = fee_rate. map ( |fee| FeeRate :: from_sat_per_vb ( fee) . unwrap ( ) ) ;
@@ -284,7 +277,7 @@ impl SpaceCli {
284
277
. wallet_send_request (
285
278
& self . wallet ,
286
279
RpcWalletTxBuilder {
287
- auction_outputs ,
280
+ bidouts ,
288
281
requests : match req {
289
282
None => vec ! [ ] ,
290
283
Some ( req) => vec ! [ req] ,
@@ -378,89 +371,57 @@ async fn main() -> anyhow::Result<()> {
378
371
Ok ( ( ) )
379
372
}
380
373
381
- fn space_hash ( spaceish : & str ) -> anyhow:: Result < String > {
374
+ fn hash_space ( spaceish : & str ) -> anyhow:: Result < String > {
382
375
let space = normalize_space ( & spaceish) ;
383
- let sname = SName :: from_str ( & space) ?;
384
- let spacehash = SpaceKey :: from ( Sha256 :: hash ( sname. to_bytes ( ) ) ) ;
385
- Ok ( hex:: encode ( spacehash. as_slice ( ) ) )
376
+ let sname = SLabel :: from_str ( & space) ?;
377
+ Ok ( hex:: encode ( Sha256 :: hash ( sname. as_ref ( ) ) ) )
386
378
}
387
379
388
380
async fn handle_commands (
389
381
cli : & SpaceCli ,
390
382
command : Commands ,
391
383
) -> std:: result:: Result < ( ) , ClientError > {
392
384
match command {
393
- Commands :: GetRolloutEstimate {
385
+ Commands :: GetRollout {
394
386
target_interval : target,
395
387
} => {
396
- let hashes = cli. client . get_rollout ( target) . await ?;
397
- let mut spaceouts = Vec :: with_capacity ( hashes. len ( ) ) ;
398
- for ( priority, spacehash) in hashes {
399
- let outpoint = cli
400
- . client
401
- . get_space_owner ( & hex:: encode ( spacehash. as_slice ( ) ) )
402
- . await ?;
403
-
404
- if let Some ( outpoint) = outpoint {
405
- if let Some ( spaceout) = cli. client . get_spaceout ( outpoint) . await ? {
406
- spaceouts. push ( (
407
- priority,
408
- FullSpaceOut {
409
- txid : outpoint. txid ,
410
- spaceout,
411
- } ,
412
- ) ) ;
413
- }
414
- }
415
- }
416
-
417
- let data: Vec < _ > = spaceouts
418
- . into_iter ( )
419
- . map ( |( priority, spaceout) | {
420
- let space = spaceout. spaceout . space . unwrap ( ) ;
421
- (
422
- space. name . to_string ( ) ,
423
- match space. covenant {
424
- Covenant :: Bid { .. } => priority,
425
- _ => 0 ,
426
- } ,
427
- )
428
- } )
429
- . collect ( ) ;
430
-
388
+ let data = cli. client . get_rollout ( target) . await ?;
431
389
println ! ( "{}" , serde_json:: to_string_pretty( & data) ?) ;
432
390
}
433
391
Commands :: EstimateBid { target } => {
434
392
let response = cli. client . estimate_bid ( target) . await ?;
435
393
println ! ( "{} sat" , Amount :: from_sat( response) . to_string( ) ) ;
436
394
}
437
395
Commands :: GetSpace { space } => {
438
- let space_hash = space_hash ( & space) . map_err ( |e| ClientError :: Custom ( e. to_string ( ) ) ) ?;
396
+ let space_hash = hash_space ( & space) . map_err ( |e| ClientError :: Custom ( e. to_string ( ) ) ) ?;
439
397
let response = cli. client . get_space ( & space_hash) . await ?;
440
398
println ! ( "{}" , serde_json:: to_string_pretty( & response) ?) ;
441
399
}
442
400
Commands :: GetSpaceOut { outpoint } => {
443
401
let response = cli. client . get_spaceout ( outpoint) . await ?;
444
402
println ! ( "{}" , serde_json:: to_string_pretty( & response) ?) ;
445
403
}
446
- Commands :: CreateWallet { name } => {
447
- cli. client . wallet_create ( & name ) . await ?;
404
+ Commands :: CreateWallet => {
405
+ cli. client . wallet_create ( & cli . wallet ) . await ?;
448
406
}
449
- Commands :: LoadWallet { name } => {
450
- cli. client . wallet_load ( & name ) . await ?;
407
+ Commands :: LoadWallet => {
408
+ cli. client . wallet_load ( & cli . wallet ) . await ?;
451
409
}
452
410
Commands :: ImportWallet { path } => {
453
411
let content =
454
412
fs:: read_to_string ( path) . map_err ( |e| ClientError :: Custom ( e. to_string ( ) ) ) ?;
455
413
let wallet: WalletExport = serde_json:: from_str ( & content) ?;
456
414
cli. client . wallet_import ( wallet) . await ?;
457
415
}
458
- Commands :: ExportWallet { name } => {
459
- let result = cli. client . wallet_export ( & name) . await ?;
460
- println ! ( "{}" , serde_json:: to_string_pretty( & result) . expect( "result" ) ) ;
416
+ Commands :: ExportWallet { path } => {
417
+ let result = cli. client . wallet_export ( & cli. wallet ) . await ?;
418
+ let content = serde_json:: to_string_pretty ( & result) . expect ( "result" ) ;
419
+ fs:: write ( path, content) . map_err ( |e| {
420
+ ClientError :: Custom ( format ! ( "Could not save to path: {}" , e. to_string( ) ) )
421
+ } ) ?;
461
422
}
462
- Commands :: GetWalletInfo { name } => {
463
- let result = cli. client . wallet_get_info ( & name ) . await ?;
423
+ Commands :: GetWalletInfo => {
424
+ let result = cli. client . wallet_get_info ( & cli . wallet ) . await ?;
464
425
println ! ( "{}" , serde_json:: to_string_pretty( & result) . expect( "result" ) ) ;
465
426
}
466
427
Commands :: GetServerInfo => {
@@ -497,7 +458,7 @@ async fn handle_commands(
497
458
)
498
459
. await ?
499
460
}
500
- Commands :: CreateAuctionOutputs { pairs, fee_rate } => {
461
+ Commands :: CreateBidOuts { pairs, fee_rate } => {
501
462
cli. send_request ( None , Some ( pairs) , fee_rate) . await ?
502
463
}
503
464
Commands :: Register {
@@ -546,28 +507,28 @@ async fn handle_commands(
546
507
)
547
508
. await ?
548
509
}
549
- Commands :: SetData {
510
+ Commands :: SetRawFallback {
550
511
mut space,
551
512
data,
552
513
fee_rate,
553
514
} => {
554
515
space = normalize_space ( & space) ;
555
- let data = match BASE64_STANDARD . decode ( data) {
516
+ let data = match hex :: decode ( data) {
556
517
Ok ( data) => data,
557
518
Err ( e) => {
558
519
return Err ( ClientError :: Custom ( format ! (
559
- "Could not base64 decode data: {}" ,
520
+ "Could not hex decode data: {}" ,
560
521
e
561
522
) ) )
562
523
}
563
524
} ;
564
- let builder = protocol :: script :: ScriptBuilder :: new ( )
565
- . push_slice ( data. as_slice ( ) )
566
- . push_opcode ( OP_SETALL . into ( ) ) ;
525
+
526
+ let space_script = protocol :: script :: SpaceScript :: create_set_fallback ( data. as_slice ( ) ) ;
527
+
567
528
cli. send_request (
568
529
Some ( RpcWalletRequest :: Execute ( ExecuteParams {
569
530
context : vec ! [ space] ,
570
- space_script : builder ,
531
+ space_script,
571
532
} ) ) ,
572
533
None ,
573
534
fee_rate,
@@ -578,8 +539,8 @@ async fn handle_commands(
578
539
let spaces = cli. client . wallet_list_unspent ( & cli. wallet ) . await ?;
579
540
println ! ( "{}" , serde_json:: to_string_pretty( & spaces) ?) ;
580
541
}
581
- Commands :: ListAuctionOutputs => {
582
- let spaces = cli. client . wallet_list_auction_outputs ( & cli. wallet ) . await ?;
542
+ Commands :: ListBidOuts => {
543
+ let spaces = cli. client . wallet_list_bidouts ( & cli. wallet ) . await ?;
583
544
println ! ( "{}" , serde_json:: to_string_pretty( & spaces) ?) ;
584
545
}
585
546
Commands :: ListTransactions { count, skip } => {
@@ -619,10 +580,21 @@ async fn handle_commands(
619
580
. await ?;
620
581
println ! ( "{}" , serde_json:: to_string_pretty( & response) ?) ;
621
582
}
622
- Commands :: SpaceHash { space } => {
583
+ Commands :: ForceSpend { outpoint, fee_rate } => {
584
+ let result = cli
585
+ . client
586
+ . wallet_force_spend (
587
+ & cli. wallet ,
588
+ outpoint,
589
+ FeeRate :: from_sat_per_vb ( fee_rate) . unwrap ( ) ,
590
+ )
591
+ . await ?;
592
+ println ! ( "{}" , serde_json:: to_string_pretty( & result) . expect( "result" ) ) ;
593
+ }
594
+ Commands :: HashSpace { space } => {
623
595
println ! (
624
596
"{}" ,
625
- space_hash ( & space) . map_err( |e| ClientError :: Custom ( e. to_string( ) ) ) ?
597
+ hash_space ( & space) . map_err( |e| ClientError :: Custom ( e. to_string( ) ) ) ?
626
598
) ;
627
599
}
628
600
}
0 commit comments