Skip to content

Commit 08a4a0f

Browse files
committed
[tests] add get_multisig function to wallet_importmulti.py
Adds a new get_multisig function which generates a new multisig and returns the public keys, private keys and all script and address types.
1 parent 7c99614 commit 08a4a0f

File tree

1 file changed

+76
-55
lines changed

1 file changed

+76
-55
lines changed

test/functional/wallet_importmulti.py

Lines changed: 76 additions & 55 deletions
Original file line numberDiff line numberDiff line change
@@ -9,18 +9,24 @@
99
key_to_p2pkh,
1010
key_to_p2sh_p2wpkh,
1111
key_to_p2wpkh,
12+
script_to_p2sh,
13+
script_to_p2sh_p2wsh,
14+
script_to_p2wsh,
1215
)
13-
from test_framework.messages import sha256
1416
from test_framework.script import (
1517
CScript,
1618
OP_0,
19+
OP_2,
20+
OP_3,
21+
OP_CHECKMULTISIG,
1722
OP_CHECKSIG,
1823
OP_DUP,
1924
OP_EQUAL,
2025
OP_EQUALVERIFY,
2126
OP_HASH160,
2227
OP_NOP,
2328
hash160,
29+
sha256,
2430
)
2531
from test_framework.test_framework import BitcoinTestFramework
2632
from test_framework.util import (
@@ -41,6 +47,16 @@
4147
'p2sh_p2wpkh_redeem_script',
4248
'p2sh_p2wpkh_addr'])
4349

50+
Multisig = namedtuple('Multisig', ['privkeys',
51+
'pubkeys',
52+
'p2sh_script',
53+
'p2sh_addr',
54+
'redeem_script',
55+
'p2wsh_script',
56+
'p2wsh_addr',
57+
'p2sh_p2wsh_script',
58+
'p2sh_p2wsh_addr'])
59+
4460
class ImportMultiTest(BitcoinTestFramework):
4561
def set_test_params(self):
4662
self.num_nodes = 2
@@ -70,6 +86,28 @@ def get_key(self):
7086
CScript([OP_0, pkh]).hex(), # p2sh-p2wpkh redeem script
7187
key_to_p2sh_p2wpkh(pubkey)) # p2sh-p2wpkh addr
7288

89+
def get_multisig(self):
90+
"""Generate a fresh multisig on node0
91+
92+
Returns a named tuple of privkeys, pubkeys and all address and scripts."""
93+
addrs = []
94+
pubkeys = []
95+
for _ in range(3):
96+
addr = self.nodes[0].getaddressinfo(self.nodes[0].getnewaddress())
97+
addrs.append(addr['address'])
98+
pubkeys.append(addr['pubkey'])
99+
script_code = CScript([OP_2] + [hex_str_to_bytes(pubkey) for pubkey in pubkeys] + [OP_3, OP_CHECKMULTISIG])
100+
witness_script = CScript([OP_0, sha256(script_code)])
101+
return Multisig([self.nodes[0].dumpprivkey(addr) for addr in addrs],
102+
pubkeys,
103+
CScript([OP_HASH160, hash160(script_code), OP_EQUAL]).hex(), # p2sh
104+
script_to_p2sh(script_code), # p2sh addr
105+
script_code.hex(), # redeem script
106+
witness_script.hex(), # p2wsh
107+
script_to_p2wsh(script_code), # p2wsh addr
108+
CScript([OP_HASH160, witness_script, OP_EQUAL]).hex(), # p2sh-p2wsh
109+
script_to_p2sh_p2wsh(script_code)) # p2sh-p2wsh addr
110+
73111
def run_test(self):
74112
self.log.info("Mining blocks...")
75113
self.nodes[0].generate(1)
@@ -302,102 +340,90 @@ def run_test(self):
302340
assert_equal('timestamp' in address_assert, False)
303341

304342
# P2SH address
305-
sig_address_1 = self.nodes[0].getaddressinfo(self.nodes[0].getnewaddress())
306-
sig_address_2 = self.nodes[0].getaddressinfo(self.nodes[0].getnewaddress())
307-
sig_address_3 = self.nodes[0].getaddressinfo(self.nodes[0].getnewaddress())
308-
multi_sig_script = self.nodes[0].createmultisig(2, [sig_address_1['pubkey'], sig_address_2['pubkey'], sig_address_3['pubkey']])
343+
multisig = self.get_multisig()
309344
self.nodes[1].generate(100)
310-
self.nodes[1].sendtoaddress(multi_sig_script['address'], 10.00)
345+
self.nodes[1].sendtoaddress(multisig.p2sh_addr, 10.00)
311346
self.nodes[1].generate(1)
312347
timestamp = self.nodes[1].getblock(self.nodes[1].getbestblockhash())['mediantime']
313348

314349
self.log.info("Should import a p2sh")
315350
result = self.nodes[1].importmulti([{
316351
"scriptPubKey": {
317-
"address": multi_sig_script['address']
352+
"address": multisig.p2sh_addr
318353
},
319354
"timestamp": "now",
320355
}])
321356
assert_equal(result[0]['success'], True)
322-
address_assert = self.nodes[1].getaddressinfo(multi_sig_script['address'])
357+
address_assert = self.nodes[1].getaddressinfo(multisig.p2sh_addr)
323358
assert_equal(address_assert['isscript'], True)
324359
assert_equal(address_assert['iswatchonly'], True)
325360
assert_equal(address_assert['timestamp'], timestamp)
326-
p2shunspent = self.nodes[1].listunspent(0, 999999, [multi_sig_script['address']])[0]
361+
p2shunspent = self.nodes[1].listunspent(0, 999999, [multisig.p2sh_addr])[0]
327362
assert_equal(p2shunspent['spendable'], False)
328363
assert_equal(p2shunspent['solvable'], False)
329364

330365
# P2SH + Redeem script
331-
sig_address_1 = self.nodes[0].getaddressinfo(self.nodes[0].getnewaddress())
332-
sig_address_2 = self.nodes[0].getaddressinfo(self.nodes[0].getnewaddress())
333-
sig_address_3 = self.nodes[0].getaddressinfo(self.nodes[0].getnewaddress())
334-
multi_sig_script = self.nodes[0].createmultisig(2, [sig_address_1['pubkey'], sig_address_2['pubkey'], sig_address_3['pubkey']])
366+
multisig = self.get_multisig()
335367
self.nodes[1].generate(100)
336-
self.nodes[1].sendtoaddress(multi_sig_script['address'], 10.00)
368+
self.nodes[1].sendtoaddress(multisig.p2sh_addr, 10.00)
337369
self.nodes[1].generate(1)
338370
timestamp = self.nodes[1].getblock(self.nodes[1].getbestblockhash())['mediantime']
339371

340372
self.log.info("Should import a p2sh with respective redeem script")
341373
result = self.nodes[1].importmulti([{
342374
"scriptPubKey": {
343-
"address": multi_sig_script['address']
375+
"address": multisig.p2sh_addr
344376
},
345377
"timestamp": "now",
346-
"redeemscript": multi_sig_script['redeemScript']
378+
"redeemscript": multisig.redeem_script
347379
}])
348380
assert_equal(result[0]['success'], True)
349-
address_assert = self.nodes[1].getaddressinfo(multi_sig_script['address'])
381+
address_assert = self.nodes[1].getaddressinfo(multisig.p2sh_addr)
350382
assert_equal(address_assert['timestamp'], timestamp)
351383

352-
p2shunspent = self.nodes[1].listunspent(0, 999999, [multi_sig_script['address']])[0]
384+
p2shunspent = self.nodes[1].listunspent(0, 999999, [multisig.p2sh_addr])[0]
353385
assert_equal(p2shunspent['spendable'], False)
354386
assert_equal(p2shunspent['solvable'], True)
355387

356388
# P2SH + Redeem script + Private Keys + !Watchonly
357-
sig_address_1 = self.nodes[0].getaddressinfo(self.nodes[0].getnewaddress())
358-
sig_address_2 = self.nodes[0].getaddressinfo(self.nodes[0].getnewaddress())
359-
sig_address_3 = self.nodes[0].getaddressinfo(self.nodes[0].getnewaddress())
360-
multi_sig_script = self.nodes[0].createmultisig(2, [sig_address_1['pubkey'], sig_address_2['pubkey'], sig_address_3['pubkey']])
389+
multisig = self.get_multisig()
361390
self.nodes[1].generate(100)
362-
self.nodes[1].sendtoaddress(multi_sig_script['address'], 10.00)
391+
self.nodes[1].sendtoaddress(multisig.p2sh_addr, 10.00)
363392
self.nodes[1].generate(1)
364393
timestamp = self.nodes[1].getblock(self.nodes[1].getbestblockhash())['mediantime']
365394

366395
self.log.info("Should import a p2sh with respective redeem script and private keys")
367396
result = self.nodes[1].importmulti([{
368397
"scriptPubKey": {
369-
"address": multi_sig_script['address']
398+
"address": multisig.p2sh_addr
370399
},
371400
"timestamp": "now",
372-
"redeemscript": multi_sig_script['redeemScript'],
373-
"keys": [self.nodes[0].dumpprivkey(sig_address_1['address']), self.nodes[0].dumpprivkey(sig_address_2['address'])]
401+
"redeemscript": multisig.redeem_script,
402+
"keys": multisig.privkeys[0:2]
374403
}])
375404
assert_equal(result[0]['success'], True)
376-
address_assert = self.nodes[1].getaddressinfo(multi_sig_script['address'])
405+
address_assert = self.nodes[1].getaddressinfo(multisig.p2sh_addr)
377406
assert_equal(address_assert['timestamp'], timestamp)
378407

379-
p2shunspent = self.nodes[1].listunspent(0, 999999, [multi_sig_script['address']])[0]
408+
p2shunspent = self.nodes[1].listunspent(0, 999999, [multisig.p2sh_addr])[0]
380409
assert_equal(p2shunspent['spendable'], False)
381410
assert_equal(p2shunspent['solvable'], True)
382411

383412
# P2SH + Redeem script + Private Keys + Watchonly
384-
sig_address_1 = self.nodes[0].getaddressinfo(self.nodes[0].getnewaddress())
385-
sig_address_2 = self.nodes[0].getaddressinfo(self.nodes[0].getnewaddress())
386-
sig_address_3 = self.nodes[0].getaddressinfo(self.nodes[0].getnewaddress())
387-
multi_sig_script = self.nodes[0].createmultisig(2, [sig_address_1['pubkey'], sig_address_2['pubkey'], sig_address_3['pubkey']])
413+
multisig = self.get_multisig()
388414
self.nodes[1].generate(100)
389-
self.nodes[1].sendtoaddress(multi_sig_script['address'], 10.00)
415+
self.nodes[1].sendtoaddress(multisig.p2sh_addr, 10.00)
390416
self.nodes[1].generate(1)
391417
timestamp = self.nodes[1].getblock(self.nodes[1].getbestblockhash())['mediantime']
392418

393419
self.log.info("Should import a p2sh with respective redeem script and private keys")
394420
result = self.nodes[1].importmulti([{
395421
"scriptPubKey": {
396-
"address": multi_sig_script['address']
422+
"address": multisig.p2sh_addr
397423
},
398424
"timestamp": "now",
399-
"redeemscript": multi_sig_script['redeemScript'],
400-
"keys": [self.nodes[0].dumpprivkey(sig_address_1['address']), self.nodes[0].dumpprivkey(sig_address_2['address'])],
425+
"redeemscript": multisig.redeem_script,
426+
"keys": multisig.privkeys[0:2],
401427
"watchonly": True
402428
}])
403429
assert_equal(result[0]['success'], False)
@@ -565,32 +591,30 @@ def run_test(self):
565591
assert_equal(address_assert['ismine'], True)
566592

567593
# P2WSH multisig address without scripts or keys
568-
sig_address_1 = self.nodes[0].getaddressinfo(self.nodes[0].getnewaddress())
569-
sig_address_2 = self.nodes[0].getaddressinfo(self.nodes[0].getnewaddress())
570-
multi_sig_script = self.nodes[0].addmultisigaddress(2, [sig_address_1['pubkey'], sig_address_2['pubkey']], "", "bech32")
594+
multisig = self.get_multisig()
571595
self.log.info("Should import a p2wsh multisig as watch only without respective redeem script and private keys")
572596
result = self.nodes[1].importmulti([{
573597
"scriptPubKey": {
574-
"address": multi_sig_script['address']
598+
"address": multisig.p2wsh_addr
575599
},
576600
"timestamp": "now"
577601
}])
578602
assert_equal(result[0]['success'], True)
579-
address_assert = self.nodes[1].getaddressinfo(multi_sig_script['address'])
603+
address_assert = self.nodes[1].getaddressinfo(multisig.p2sh_addr)
580604
assert_equal(address_assert['solvable'], False)
581605

582606
# Same P2WSH multisig address as above, but now with witnessscript + private keys
583-
self.log.info("Should import a p2wsh with respective redeem script and private keys")
607+
self.log.info("Should import a p2wsh with respective witness script and private keys")
584608
result = self.nodes[1].importmulti([{
585609
"scriptPubKey": {
586-
"address": multi_sig_script['address']
610+
"address": multisig.p2wsh_addr
587611
},
588612
"timestamp": "now",
589-
"witnessscript": multi_sig_script['redeemScript'],
590-
"keys": [self.nodes[0].dumpprivkey(sig_address_1['address']), self.nodes[0].dumpprivkey(sig_address_2['address'])]
613+
"witnessscript": multisig.redeem_script,
614+
"keys": multisig.privkeys
591615
}])
592616
assert_equal(result[0]['success'], True)
593-
address_assert = self.nodes[1].getaddressinfo(multi_sig_script['address'])
617+
address_assert = self.nodes[1].getaddressinfo(multisig.p2sh_addr)
594618
assert_equal(address_assert['solvable'], True)
595619
assert_equal(address_assert['ismine'], True)
596620
assert_equal(address_assert['sigsrequired'], 2)
@@ -642,22 +666,19 @@ def run_test(self):
642666
assert_equal(address_assert['solvable'], True)
643667
assert_equal(address_assert['ismine'], True)
644668

645-
# P2SH-P2WSH 1-of-1 multisig + redeemscript with no private key
646-
sig_address_1 = self.nodes[0].getaddressinfo(self.nodes[0].getnewaddress())
647-
multi_sig_script = self.nodes[0].addmultisigaddress(1, [sig_address_1['pubkey']], "", "p2sh-segwit")
648-
scripthash = sha256(hex_str_to_bytes(multi_sig_script['redeemScript']))
649-
redeem_script = CScript([OP_0, scripthash])
669+
# P2SH-P2WSH multisig + redeemscript with no private key
670+
multisig = self.get_multisig()
650671
self.log.info("Should import a p2sh-p2wsh with respective redeem script but no private key")
651672
result = self.nodes[1].importmulti([{
652673
"scriptPubKey": {
653-
"address": multi_sig_script['address']
674+
"address": multisig.p2sh_p2wsh_addr
654675
},
655676
"timestamp": "now",
656-
"redeemscript": bytes_to_hex_str(redeem_script),
657-
"witnessscript": multi_sig_script['redeemScript']
677+
"redeemscript": multisig.p2wsh_script,
678+
"witnessscript": multisig.redeem_script,
658679
}])
659680
assert_equal(result[0]['success'], True)
660-
address_assert = self.nodes[1].getaddressinfo(multi_sig_script['address'])
681+
address_assert = self.nodes[1].getaddressinfo(multisig.p2sh_addr)
661682
assert_equal(address_assert['solvable'], True)
662683

663684
if __name__ == '__main__':

0 commit comments

Comments
 (0)