Browse Source

keystore: API changes for from_seed/from_bip43_rootseed/bip39_to_seed

- force kwargs
- add type hints
master
SomberNight 2 years ago
parent
commit
8ab3dcce5d
No known key found for this signature in database
GPG Key ID: B33B5F232C6271E9
  1. 2
      electrum/gui/qml/qebip39recovery.py
  2. 2
      electrum/gui/qt/wizard/wallet.py
  3. 42
      electrum/keystore.py
  4. 2
      electrum/scripts/bip39_recovery.py
  5. 4
      electrum/wallet.py
  6. 14
      electrum/wizard.py
  7. 98
      tests/test_wallet_vertical.py

2
electrum/gui/qml/qebip39recovery.py

@ -77,7 +77,7 @@ class QEBip39RecoveryListModel(QAbstractListModel):
assert wallet_type == 'standard' assert wallet_type == 'standard'
self._root_seed = keystore.bip39_to_seed(seed, seed_extra_words) self._root_seed = keystore.bip39_to_seed(seed, passphrase=seed_extra_words)
self.clear() self.clear()

2
electrum/gui/qt/wizard/wallet.py

@ -712,7 +712,7 @@ class WCScriptAndDerivation(WalletWizardComponent, Logger):
passphrase = self.wizard_data['seed_extra_words'] if self.wizard_data['seed_extend'] else '' passphrase = self.wizard_data['seed_extra_words'] if self.wizard_data['seed_extend'] else ''
if self.wizard_data['seed_variant'] == 'bip39': if self.wizard_data['seed_variant'] == 'bip39':
root_seed = bip39_to_seed(self.wizard_data['seed'], passphrase) root_seed = bip39_to_seed(self.wizard_data['seed'], passphrase=passphrase)
elif self.wizard_data['seed_variant'] == 'slip39': elif self.wizard_data['seed_variant'] == 'slip39':
root_seed = self.wizard_data['seed'].decrypt(passphrase) root_seed = self.wizard_data['seed'].decrypt(passphrase)

42
electrum/keystore.py

@ -374,7 +374,7 @@ class Deterministic_KeyStore(Software_KeyStore):
def format_seed(self, seed: str) -> str: def format_seed(self, seed: str) -> str:
pass pass
def add_seed(self, seed): def add_seed(self, seed: str) -> None:
if self.seed: if self.seed:
raise Exception("a seed exists") raise Exception("a seed exists")
self.seed = self.format_seed(seed) self.seed = self.format_seed(seed)
@ -577,7 +577,7 @@ class Xpub(MasterPublicKeyMixin):
deriv_path=strpath, deriv_path=strpath,
) )
def add_key_origin_from_root_node(self, *, derivation_prefix: str, root_node: BIP32Node): def add_key_origin_from_root_node(self, *, derivation_prefix: str, root_node: BIP32Node) -> None:
assert self.xpub assert self.xpub
# try to derive ourselves from what we were given # try to derive ourselves from what we were given
child_node1 = root_node.subkey_at_private_derivation(derivation_prefix) child_node1 = root_node.subkey_at_private_derivation(derivation_prefix)
@ -677,18 +677,18 @@ class BIP32_KeyStore(Xpub, Deterministic_KeyStore):
def is_watching_only(self): def is_watching_only(self):
return self.xprv is None return self.xprv is None
def add_xpub(self, xpub): def add_xpub(self, xpub: str) -> None:
assert is_xpub(xpub) assert is_xpub(xpub)
self.xpub = xpub self.xpub = xpub
root_fingerprint, derivation_prefix = bip32.root_fp_and_der_prefix_from_xkey(xpub) root_fingerprint, derivation_prefix = bip32.root_fp_and_der_prefix_from_xkey(xpub)
self.add_key_origin(derivation_prefix=derivation_prefix, root_fingerprint=root_fingerprint) self.add_key_origin(derivation_prefix=derivation_prefix, root_fingerprint=root_fingerprint)
def add_xprv(self, xprv): def add_xprv(self, xprv: str) -> None:
assert is_xprv(xprv) assert is_xprv(xprv)
self.xprv = xprv self.xprv = xprv
self.add_xpub(bip32.xpub_from_xprv(xprv)) self.add_xpub(bip32.xpub_from_xprv(xprv))
def add_xprv_from_seed(self, bip32_seed, xtype, derivation): def add_xprv_from_seed(self, bip32_seed: bytes, *, xtype: str, derivation: str) -> None:
rootnode = BIP32Node.from_rootseed(bip32_seed, xtype=xtype) rootnode = BIP32Node.from_rootseed(bip32_seed, xtype=xtype)
node = rootnode.subkey_at_private_derivation(derivation) node = rootnode.subkey_at_private_derivation(derivation)
self.add_xprv(node.to_xprv()) self.add_xprv(node.to_xprv())
@ -735,12 +735,12 @@ class Old_KeyStore(MasterPublicKeyMixin, Deterministic_KeyStore):
d['mpk'] = self.mpk d['mpk'] = self.mpk
return d return d
def add_seed(self, seedphrase): def add_seed(self, seed):
Deterministic_KeyStore.add_seed(self, seedphrase) Deterministic_KeyStore.add_seed(self, seed)
s = self.get_hex_seed(None) s = self.get_hex_seed(None)
self.mpk = self.mpk_from_seed(s) self.mpk = self.mpk_from_seed(s)
def add_master_public_key(self, mpk): def add_master_public_key(self, mpk) -> None:
self.mpk = mpk self.mpk = mpk
def format_seed(self, seed): def format_seed(self, seed):
@ -978,11 +978,13 @@ KeyStoreWithMPK = Union[KeyStore, MasterPublicKeyMixin] # intersection really..
AddressIndexGeneric = Union[Sequence[int], str] # can be hex pubkey str AddressIndexGeneric = Union[Sequence[int], str] # can be hex pubkey str
def bip39_normalize_passphrase(passphrase): def bip39_normalize_passphrase(passphrase: str):
return normalize('NFKD', passphrase or '') return normalize('NFKD', passphrase or '')
def bip39_to_seed(mnemonic, passphrase):
import hashlib, hmac def bip39_to_seed(mnemonic: str, *, passphrase: Optional[str]) -> bytes:
import hashlib
passphrase = passphrase or ""
PBKDF2_ROUNDS = 2048 PBKDF2_ROUNDS = 2048
mnemonic = normalize('NFKD', ' '.join(mnemonic.split())) mnemonic = normalize('NFKD', ' '.join(mnemonic.split()))
passphrase = bip39_normalize_passphrase(passphrase) passphrase = bip39_normalize_passphrase(passphrase)
@ -1024,11 +1026,16 @@ def bip39_is_checksum_valid(
return checksum == calculated_checksum, True return checksum == calculated_checksum, True
def from_bip43_rootseed(root_seed, derivation, xtype=None): def from_bip43_rootseed(
root_seed: bytes,
*,
derivation: str,
xtype: Optional[str] = None,
):
k = BIP32_KeyStore({}) k = BIP32_KeyStore({})
if xtype is None: if xtype is None:
xtype = xtype_from_derivation(derivation) xtype = xtype_from_derivation(derivation)
k.add_xprv_from_seed(root_seed, xtype, derivation) k.add_xprv_from_seed(root_seed, xtype=xtype, derivation=derivation)
return k return k
@ -1156,7 +1163,8 @@ def purpose48_derivation(account_id: int, xtype: str) -> str:
return normalize_bip32_derivation(der) return normalize_bip32_derivation(der)
def from_seed(seed, passphrase, is_p2sh=False): def from_seed(seed: str, *, passphrase: Optional[str], for_multisig: bool = False):
passphrase = passphrase or ""
t = seed_type(seed) t = seed_type(seed)
if t == 'old': if t == 'old':
if passphrase: if passphrase:
@ -1172,9 +1180,9 @@ def from_seed(seed, passphrase, is_p2sh=False):
der = "m/" der = "m/"
xtype = 'standard' xtype = 'standard'
else: else:
der = "m/1'/" if is_p2sh else "m/0'/" der = "m/1'/" if for_multisig else "m/0'/"
xtype = 'p2wsh' if is_p2sh else 'p2wpkh' xtype = 'p2wsh' if for_multisig else 'p2wpkh'
keystore.add_xprv_from_seed(bip32_seed, xtype, der) keystore.add_xprv_from_seed(bip32_seed, xtype=xtype, derivation=der)
else: else:
raise BitcoinException('Unexpected seed type {}'.format(repr(t))) raise BitcoinException('Unexpected seed type {}'.format(repr(t)))
return keystore return keystore

2
electrum/scripts/bip39_recovery.py

@ -27,7 +27,7 @@ network.start()
async def f(): async def f():
try: try:
def get_account_xpub(account_path): def get_account_xpub(account_path):
root_seed = bip39_to_seed(mnemonic, passphrase) root_seed = bip39_to_seed(mnemonic, passphrase=passphrase)
root_node = BIP32Node.from_rootseed(root_seed, xtype="standard") root_node = BIP32Node.from_rootseed(root_seed, xtype="standard")
account_node = root_node.subkey_at_private_derivation(account_path) account_node = root_node.subkey_at_private_derivation(account_path)
account_xpub = account_node.to_xpub() account_xpub = account_node.to_xpub()

4
electrum/wallet.py

@ -3909,7 +3909,7 @@ def create_new_wallet(*, path, config: SimpleConfig, passphrase=None, password=N
db = WalletDB('', storage=storage, upgrade=True) db = WalletDB('', storage=storage, upgrade=True)
seed = Mnemonic('en').make_seed(seed_type=seed_type) seed = Mnemonic('en').make_seed(seed_type=seed_type)
k = keystore.from_seed(seed, passphrase) k = keystore.from_seed(seed, passphrase=passphrase)
db.put('keystore', k.dump()) db.put('keystore', k.dump())
db.put('wallet_type', 'standard') db.put('wallet_type', 'standard')
if k.can_have_deterministic_lightning_xprv(): if k.can_have_deterministic_lightning_xprv():
@ -3967,7 +3967,7 @@ def restore_wallet_from_text(
if keystore.is_master_key(text): if keystore.is_master_key(text):
k = keystore.from_master_key(text) k = keystore.from_master_key(text)
elif keystore.is_seed(text): elif keystore.is_seed(text):
k = keystore.from_seed(text, passphrase) k = keystore.from_seed(text, passphrase=passphrase)
if k.can_have_deterministic_lightning_xprv(): if k.can_have_deterministic_lightning_xprv():
db.put('lightning_xprv', k.get_lightning_xprv(None)) db.put('lightning_xprv', k.get_lightning_xprv(None))
else: else:

14
electrum/wizard.py

@ -415,15 +415,15 @@ class NewWalletWizard(AbstractWizard):
def keystore_from_data(self, wallet_type: str, data: dict): def keystore_from_data(self, wallet_type: str, data: dict):
if data['keystore_type'] in ['createseed', 'haveseed'] and 'seed' in data: if data['keystore_type'] in ['createseed', 'haveseed'] and 'seed' in data:
if data['seed_variant'] == 'electrum': if data['seed_variant'] == 'electrum':
return keystore.from_seed(data['seed'], data['seed_extra_words'], True) return keystore.from_seed(data['seed'], passphrase=data['seed_extra_words'], for_multisig=True)
elif data['seed_variant'] == 'bip39': elif data['seed_variant'] == 'bip39':
root_seed = keystore.bip39_to_seed(data['seed'], data['seed_extra_words']) root_seed = keystore.bip39_to_seed(data['seed'], passphrase=data['seed_extra_words'])
derivation = normalize_bip32_derivation(data['derivation_path']) derivation = normalize_bip32_derivation(data['derivation_path'])
if wallet_type == 'multisig': if wallet_type == 'multisig':
script = data['script_type'] if data['script_type'] != 'p2sh' else 'standard' script = data['script_type'] if data['script_type'] != 'p2sh' else 'standard'
else: else:
script = data['script_type'] if data['script_type'] != 'p2pkh' else 'standard' script = data['script_type'] if data['script_type'] != 'p2pkh' else 'standard'
return keystore.from_bip43_rootseed(root_seed, derivation, xtype=script) return keystore.from_bip43_rootseed(root_seed, derivation=derivation, xtype=script)
elif data['seed_variant'] == 'slip39': elif data['seed_variant'] == 'slip39':
root_seed = data['seed'].decrypt(data['seed_extra_words']) root_seed = data['seed'].decrypt(data['seed_extra_words'])
derivation = normalize_bip32_derivation(data['derivation_path']) derivation = normalize_bip32_derivation(data['derivation_path'])
@ -431,7 +431,7 @@ class NewWalletWizard(AbstractWizard):
script = data['script_type'] if data['script_type'] != 'p2sh' else 'standard' script = data['script_type'] if data['script_type'] != 'p2sh' else 'standard'
else: else:
script = data['script_type'] if data['script_type'] != 'p2pkh' else 'standard' script = data['script_type'] if data['script_type'] != 'p2pkh' else 'standard'
return keystore.from_bip43_rootseed(root_seed, derivation, xtype=script) return keystore.from_bip43_rootseed(root_seed, derivation=derivation, xtype=script)
else: else:
raise Exception('Unsupported seed variant %s' % data['seed_variant']) raise Exception('Unsupported seed variant %s' % data['seed_variant'])
elif data['keystore_type'] == 'masterkey' and 'master_key' in data: elif data['keystore_type'] == 'masterkey' and 'master_key' in data:
@ -548,11 +548,11 @@ class NewWalletWizard(AbstractWizard):
elif data['keystore_type'] in ['createseed', 'haveseed']: elif data['keystore_type'] in ['createseed', 'haveseed']:
if data['seed_type'] in ['old', 'standard', 'segwit']: if data['seed_type'] in ['old', 'standard', 'segwit']:
self._logger.debug('creating keystore from electrum seed') self._logger.debug('creating keystore from electrum seed')
k = keystore.from_seed(data['seed'], data['seed_extra_words'], data['wallet_type'] == 'multisig') k = keystore.from_seed(data['seed'], passphrase=data['seed_extra_words'], for_multisig=data['wallet_type'] == 'multisig')
elif data['seed_type'] in ['bip39', 'slip39']: elif data['seed_type'] in ['bip39', 'slip39']:
self._logger.debug('creating keystore from %s seed' % data['seed_type']) self._logger.debug('creating keystore from %s seed' % data['seed_type'])
if data['seed_type'] == 'bip39': if data['seed_type'] == 'bip39':
root_seed = keystore.bip39_to_seed(data['seed'], data['seed_extra_words']) root_seed = keystore.bip39_to_seed(data['seed'], passphrase=data['seed_extra_words'])
else: else:
root_seed = data['seed'].decrypt(data['seed_extra_words']) root_seed = data['seed'].decrypt(data['seed_extra_words'])
derivation = normalize_bip32_derivation(data['derivation_path']) derivation = normalize_bip32_derivation(data['derivation_path'])
@ -560,7 +560,7 @@ class NewWalletWizard(AbstractWizard):
script = data['script_type'] if data['script_type'] != 'p2sh' else 'standard' script = data['script_type'] if data['script_type'] != 'p2sh' else 'standard'
else: else:
script = data['script_type'] if data['script_type'] != 'p2pkh' else 'standard' script = data['script_type'] if data['script_type'] != 'p2pkh' else 'standard'
k = keystore.from_bip43_rootseed(root_seed, derivation, xtype=script) k = keystore.from_bip43_rootseed(root_seed, derivation=derivation, xtype=script)
elif is_any_2fa_seed_type(data['seed_type']): elif is_any_2fa_seed_type(data['seed_type']):
self._logger.debug('creating keystore from 2fa seed') self._logger.debug('creating keystore from 2fa seed')
k = keystore.from_xprv(data['x1']['xprv']) k = keystore.from_xprv(data['x1']['xprv'])

98
tests/test_wallet_vertical.py

@ -92,7 +92,7 @@ class TestWalletKeystoreAddressIntegrityForMainnet(ElectrumTestCase):
seed_words = 'cycle rocket west magnet parrot shuffle foot correct salt library feed song' seed_words = 'cycle rocket west magnet parrot shuffle foot correct salt library feed song'
self.assertEqual(seed_type(seed_words), 'standard') self.assertEqual(seed_type(seed_words), 'standard')
ks = keystore.from_seed(seed_words, '', False) ks = keystore.from_seed(seed_words, passphrase='', for_multisig=False)
WalletIntegrityHelper.check_seeded_keystore_sanity(self, ks) WalletIntegrityHelper.check_seeded_keystore_sanity(self, ks)
self.assertTrue(isinstance(ks, keystore.BIP32_KeyStore)) self.assertTrue(isinstance(ks, keystore.BIP32_KeyStore))
@ -111,7 +111,7 @@ class TestWalletKeystoreAddressIntegrityForMainnet(ElectrumTestCase):
seed_words = 'bitter grass shiver impose acquire brush forget axis eager alone wine silver' seed_words = 'bitter grass shiver impose acquire brush forget axis eager alone wine silver'
self.assertEqual(seed_type(seed_words), 'segwit') self.assertEqual(seed_type(seed_words), 'segwit')
ks = keystore.from_seed(seed_words, '', False) ks = keystore.from_seed(seed_words, passphrase='', for_multisig=False)
WalletIntegrityHelper.check_seeded_keystore_sanity(self, ks) WalletIntegrityHelper.check_seeded_keystore_sanity(self, ks)
self.assertTrue(isinstance(ks, keystore.BIP32_KeyStore)) self.assertTrue(isinstance(ks, keystore.BIP32_KeyStore))
@ -133,7 +133,7 @@ class TestWalletKeystoreAddressIntegrityForMainnet(ElectrumTestCase):
seed_words = 'bitter grass shiver impose acquire brush forget axis eager alone wine silver' seed_words = 'bitter grass shiver impose acquire brush forget axis eager alone wine silver'
self.assertEqual(seed_type(seed_words), 'segwit') self.assertEqual(seed_type(seed_words), 'segwit')
ks = keystore.from_seed(seed_words, UNICODE_HORROR, False) ks = keystore.from_seed(seed_words, passphrase=UNICODE_HORROR, for_multisig=False)
WalletIntegrityHelper.check_seeded_keystore_sanity(self, ks) WalletIntegrityHelper.check_seeded_keystore_sanity(self, ks)
self.assertTrue(isinstance(ks, keystore.BIP32_KeyStore)) self.assertTrue(isinstance(ks, keystore.BIP32_KeyStore))
@ -155,7 +155,7 @@ class TestWalletKeystoreAddressIntegrityForMainnet(ElectrumTestCase):
seed_words = 'powerful random nobody notice nothing important anyway look away hidden message over' seed_words = 'powerful random nobody notice nothing important anyway look away hidden message over'
self.assertEqual(seed_type(seed_words), 'old') self.assertEqual(seed_type(seed_words), 'old')
ks = keystore.from_seed(seed_words, '', False) ks = keystore.from_seed(seed_words, passphrase='', for_multisig=False)
WalletIntegrityHelper.check_seeded_keystore_sanity(self, ks) WalletIntegrityHelper.check_seeded_keystore_sanity(self, ks)
self.assertTrue(isinstance(ks, keystore.Old_KeyStore)) self.assertTrue(isinstance(ks, keystore.Old_KeyStore))
@ -277,8 +277,8 @@ class TestWalletKeystoreAddressIntegrityForMainnet(ElectrumTestCase):
seed_words = 'treat dwarf wealth gasp brass outside high rent blood crowd make initial' seed_words = 'treat dwarf wealth gasp brass outside high rent blood crowd make initial'
self.assertEqual(keystore.bip39_is_checksum_valid(seed_words), (True, True)) self.assertEqual(keystore.bip39_is_checksum_valid(seed_words), (True, True))
root_seed = keystore.bip39_to_seed(seed_words, '') root_seed = keystore.bip39_to_seed(seed_words, passphrase='')
ks = keystore.from_bip43_rootseed(root_seed, "m/44'/0'/0'") ks = keystore.from_bip43_rootseed(root_seed, derivation="m/44'/0'/0'")
self.assertTrue(isinstance(ks, keystore.BIP32_KeyStore)) self.assertTrue(isinstance(ks, keystore.BIP32_KeyStore))
@ -296,8 +296,8 @@ class TestWalletKeystoreAddressIntegrityForMainnet(ElectrumTestCase):
seed_words = 'treat dwarf wealth gasp brass outside high rent blood crowd make initial' seed_words = 'treat dwarf wealth gasp brass outside high rent blood crowd make initial'
self.assertEqual(keystore.bip39_is_checksum_valid(seed_words), (True, True)) self.assertEqual(keystore.bip39_is_checksum_valid(seed_words), (True, True))
root_seed = keystore.bip39_to_seed(seed_words, UNICODE_HORROR) root_seed = keystore.bip39_to_seed(seed_words, passphrase=UNICODE_HORROR)
ks = keystore.from_bip43_rootseed(root_seed, "m/44'/0'/0'") ks = keystore.from_bip43_rootseed(root_seed, derivation="m/44'/0'/0'")
self.assertTrue(isinstance(ks, keystore.BIP32_KeyStore)) self.assertTrue(isinstance(ks, keystore.BIP32_KeyStore))
@ -315,8 +315,8 @@ class TestWalletKeystoreAddressIntegrityForMainnet(ElectrumTestCase):
seed_words = 'treat dwarf wealth gasp brass outside high rent blood crowd make initial' seed_words = 'treat dwarf wealth gasp brass outside high rent blood crowd make initial'
self.assertEqual(keystore.bip39_is_checksum_valid(seed_words), (True, True)) self.assertEqual(keystore.bip39_is_checksum_valid(seed_words), (True, True))
root_seed = keystore.bip39_to_seed(seed_words, '') root_seed = keystore.bip39_to_seed(seed_words, passphrase='')
ks = keystore.from_bip43_rootseed(root_seed, "m/49'/0'/0'") ks = keystore.from_bip43_rootseed(root_seed, derivation="m/49'/0'/0'")
self.assertTrue(isinstance(ks, keystore.BIP32_KeyStore)) self.assertTrue(isinstance(ks, keystore.BIP32_KeyStore))
@ -335,8 +335,8 @@ class TestWalletKeystoreAddressIntegrityForMainnet(ElectrumTestCase):
seed_words = 'abandon abandon abandon abandon abandon abandon abandon abandon abandon abandon abandon about' seed_words = 'abandon abandon abandon abandon abandon abandon abandon abandon abandon abandon abandon about'
self.assertEqual(keystore.bip39_is_checksum_valid(seed_words), (True, True)) self.assertEqual(keystore.bip39_is_checksum_valid(seed_words), (True, True))
root_seed = keystore.bip39_to_seed(seed_words, '') root_seed = keystore.bip39_to_seed(seed_words, passphrase='')
ks = keystore.from_bip43_rootseed(root_seed, "m/84'/0'/0'") ks = keystore.from_bip43_rootseed(root_seed, derivation="m/84'/0'/0'")
self.assertTrue(isinstance(ks, keystore.BIP32_KeyStore)) self.assertTrue(isinstance(ks, keystore.BIP32_KeyStore))
@ -354,7 +354,7 @@ class TestWalletKeystoreAddressIntegrityForMainnet(ElectrumTestCase):
seed_words = 'blast uniform dragon fiscal ensure vast young utility dinosaur abandon rookie sure' seed_words = 'blast uniform dragon fiscal ensure vast young utility dinosaur abandon rookie sure'
self.assertEqual(seed_type(seed_words), 'standard') self.assertEqual(seed_type(seed_words), 'standard')
ks1 = keystore.from_seed(seed_words, '', True) ks1 = keystore.from_seed(seed_words, passphrase='', for_multisig=True)
WalletIntegrityHelper.check_seeded_keystore_sanity(self, ks1) WalletIntegrityHelper.check_seeded_keystore_sanity(self, ks1)
self.assertTrue(isinstance(ks1, keystore.BIP32_KeyStore)) self.assertTrue(isinstance(ks1, keystore.BIP32_KeyStore))
self.assertEqual(ks1.xprv, 'xprv9s21ZrQH143K3t9vo23J3hajRbzvkRLJ6Y1zFrUFAfU3t8oooMPfb7f87cn5KntgqZs5nipZkCiBFo5ZtaSD2eDo7j7CMuFV8Zu6GYLTpY6') self.assertEqual(ks1.xprv, 'xprv9s21ZrQH143K3t9vo23J3hajRbzvkRLJ6Y1zFrUFAfU3t8oooMPfb7f87cn5KntgqZs5nipZkCiBFo5ZtaSD2eDo7j7CMuFV8Zu6GYLTpY6')
@ -376,7 +376,7 @@ class TestWalletKeystoreAddressIntegrityForMainnet(ElectrumTestCase):
seed_words = 'snow nest raise royal more walk demise rotate smooth spirit canyon gun' seed_words = 'snow nest raise royal more walk demise rotate smooth spirit canyon gun'
self.assertEqual(seed_type(seed_words), 'segwit') self.assertEqual(seed_type(seed_words), 'segwit')
ks1 = keystore.from_seed(seed_words, '', True) ks1 = keystore.from_seed(seed_words, passphrase='', for_multisig=True)
WalletIntegrityHelper.check_seeded_keystore_sanity(self, ks1) WalletIntegrityHelper.check_seeded_keystore_sanity(self, ks1)
self.assertTrue(isinstance(ks1, keystore.BIP32_KeyStore)) self.assertTrue(isinstance(ks1, keystore.BIP32_KeyStore))
self.assertEqual(ks1.xprv, 'ZprvAjxLRqPiDfPDxXrm8JvcoCGRAW6xUtktucG6AMtdzaEbTEJN8qcECvujfhtDU3jLJ9g3Dr3Gz5m1ypfMs8iSUh62gWyHZ73bYLRWyeHf6y4') self.assertEqual(ks1.xprv, 'ZprvAjxLRqPiDfPDxXrm8JvcoCGRAW6xUtktucG6AMtdzaEbTEJN8qcECvujfhtDU3jLJ9g3Dr3Gz5m1ypfMs8iSUh62gWyHZ73bYLRWyeHf6y4')
@ -398,8 +398,8 @@ class TestWalletKeystoreAddressIntegrityForMainnet(ElectrumTestCase):
seed_words = 'treat dwarf wealth gasp brass outside high rent blood crowd make initial' seed_words = 'treat dwarf wealth gasp brass outside high rent blood crowd make initial'
self.assertEqual(keystore.bip39_is_checksum_valid(seed_words), (True, True)) self.assertEqual(keystore.bip39_is_checksum_valid(seed_words), (True, True))
root_seed = keystore.bip39_to_seed(seed_words, '') root_seed = keystore.bip39_to_seed(seed_words, passphrase='')
ks1 = keystore.from_bip43_rootseed(root_seed, "m/45'/0") ks1 = keystore.from_bip43_rootseed(root_seed, derivation="m/45'/0")
self.assertTrue(isinstance(ks1, keystore.BIP32_KeyStore)) self.assertTrue(isinstance(ks1, keystore.BIP32_KeyStore))
self.assertEqual(ks1.xprv, 'xprv9vyEFyXf7pYVv4eDU3hhuCEAHPHNGuxX73nwtYdpbLcqwJCPwFKknAK8pHWuHHBirCzAPDZ7UJHrYdhLfn1NkGp9rk3rVz2aEqrT93qKRD9') self.assertEqual(ks1.xprv, 'xprv9vyEFyXf7pYVv4eDU3hhuCEAHPHNGuxX73nwtYdpbLcqwJCPwFKknAK8pHWuHHBirCzAPDZ7UJHrYdhLfn1NkGp9rk3rVz2aEqrT93qKRD9')
self.assertEqual(ks1.xpub, 'xpub69xafV4YxC6o8Yiga5EiGLAtqR7rgNgNUGiYgw3S9g9pp6XYUne1KxdcfYtxwmA3eBrzMFuYcNQKfqsXCygCo4GxQFHfywxpUbKNfYvGJka') self.assertEqual(ks1.xpub, 'xpub69xafV4YxC6o8Yiga5EiGLAtqR7rgNgNUGiYgw3S9g9pp6XYUne1KxdcfYtxwmA3eBrzMFuYcNQKfqsXCygCo4GxQFHfywxpUbKNfYvGJka')
@ -441,7 +441,7 @@ class TestWalletKeystoreAddressIntegrityForMainnet(ElectrumTestCase):
async def test_bip32_extended_version_bytes(self, mock_save_db): async def test_bip32_extended_version_bytes(self, mock_save_db):
seed_words = 'crouch dumb relax small truck age shine pink invite spatial object tenant' seed_words = 'crouch dumb relax small truck age shine pink invite spatial object tenant'
self.assertEqual(keystore.bip39_is_checksum_valid(seed_words), (True, True)) self.assertEqual(keystore.bip39_is_checksum_valid(seed_words), (True, True))
bip32_seed = keystore.bip39_to_seed(seed_words, '') bip32_seed = keystore.bip39_to_seed(seed_words, passphrase='')
self.assertEqual('0df68c16e522eea9c1d8e090cfb2139c3b3a2abed78cbcb3e20be2c29185d3b8df4e8ce4e52a1206a688aeb88bfee249585b41a7444673d1f16c0d45755fa8b9', self.assertEqual('0df68c16e522eea9c1d8e090cfb2139c3b3a2abed78cbcb3e20be2c29185d3b8df4e8ce4e52a1206a688aeb88bfee249585b41a7444673d1f16c0d45755fa8b9',
bip32_seed.hex()) bip32_seed.hex())
@ -510,7 +510,7 @@ class TestWalletKeystoreAddressIntegrityForMainnet(ElectrumTestCase):
encrypted_seed = slip39.recover_ems(mnemonics) encrypted_seed = slip39.recover_ems(mnemonics)
root_seed = encrypted_seed.decrypt('TREZOR') root_seed = encrypted_seed.decrypt('TREZOR')
ks = keystore.from_bip43_rootseed(root_seed, "m/44'/0'/0'") ks = keystore.from_bip43_rootseed(root_seed, derivation="m/44'/0'/0'")
self.assertTrue(isinstance(ks, keystore.BIP32_KeyStore)) self.assertTrue(isinstance(ks, keystore.BIP32_KeyStore))
@ -536,7 +536,7 @@ class TestWalletKeystoreAddressIntegrityForMainnet(ElectrumTestCase):
encrypted_seed = slip39.recover_ems(mnemonics) encrypted_seed = slip39.recover_ems(mnemonics)
root_seed = encrypted_seed.decrypt('TREZOR') root_seed = encrypted_seed.decrypt('TREZOR')
ks = keystore.from_bip43_rootseed(root_seed, "m/49'/0'/0'") ks = keystore.from_bip43_rootseed(root_seed, derivation="m/49'/0'/0'")
self.assertTrue(isinstance(ks, keystore.BIP32_KeyStore)) self.assertTrue(isinstance(ks, keystore.BIP32_KeyStore))
@ -566,7 +566,7 @@ class TestWalletKeystoreAddressIntegrityForMainnet(ElectrumTestCase):
encrypted_seed = slip39.recover_ems(mnemonics) encrypted_seed = slip39.recover_ems(mnemonics)
root_seed = encrypted_seed.decrypt('TREZOR') root_seed = encrypted_seed.decrypt('TREZOR')
ks = keystore.from_bip43_rootseed(root_seed, "m/84'/0'/0'") ks = keystore.from_bip43_rootseed(root_seed, derivation="m/84'/0'/0'")
self.assertTrue(isinstance(ks, keystore.BIP32_KeyStore)) self.assertTrue(isinstance(ks, keystore.BIP32_KeyStore))
@ -594,7 +594,7 @@ class TestWalletKeystoreAddressIntegrityForMainnet(ElectrumTestCase):
encrypted_seed = slip39.recover_ems(mnemonics) encrypted_seed = slip39.recover_ems(mnemonics)
root_seed = encrypted_seed.decrypt('TREZOR') root_seed = encrypted_seed.decrypt('TREZOR')
ks = keystore.from_bip43_rootseed(root_seed, "m/49'/0'/0'") ks = keystore.from_bip43_rootseed(root_seed, derivation="m/49'/0'/0'")
self.assertTrue(isinstance(ks, keystore.BIP32_KeyStore)) self.assertTrue(isinstance(ks, keystore.BIP32_KeyStore))
@ -640,7 +640,7 @@ class TestWalletKeystoreAddressIntegrityForTestnet(ElectrumTestCase):
async def test_bip32_extended_version_bytes(self, mock_save_db): async def test_bip32_extended_version_bytes(self, mock_save_db):
seed_words = 'crouch dumb relax small truck age shine pink invite spatial object tenant' seed_words = 'crouch dumb relax small truck age shine pink invite spatial object tenant'
self.assertEqual(keystore.bip39_is_checksum_valid(seed_words), (True, True)) self.assertEqual(keystore.bip39_is_checksum_valid(seed_words), (True, True))
bip32_seed = keystore.bip39_to_seed(seed_words, '') bip32_seed = keystore.bip39_to_seed(seed_words, passphrase='')
self.assertEqual('0df68c16e522eea9c1d8e090cfb2139c3b3a2abed78cbcb3e20be2c29185d3b8df4e8ce4e52a1206a688aeb88bfee249585b41a7444673d1f16c0d45755fa8b9', self.assertEqual('0df68c16e522eea9c1d8e090cfb2139c3b3a2abed78cbcb3e20be2c29185d3b8df4e8ce4e52a1206a688aeb88bfee249585b41a7444673d1f16c0d45755fa8b9',
bip32_seed.hex()) bip32_seed.hex())
@ -706,7 +706,7 @@ class TestWalletSending(ElectrumTestCase):
def create_standard_wallet_from_seed(self, seed_words, *, config=None, gap_limit=2): def create_standard_wallet_from_seed(self, seed_words, *, config=None, gap_limit=2):
if config is None: if config is None:
config = self.config config = self.config
ks = keystore.from_seed(seed_words, '', False) ks = keystore.from_seed(seed_words, passphrase='', for_multisig=False)
return WalletIntegrityHelper.create_standard_wallet(ks, gap_limit=gap_limit, config=config) return WalletIntegrityHelper.create_standard_wallet(ks, gap_limit=gap_limit, config=config)
@mock.patch.object(wallet.Abstract_Wallet, 'save_db') @mock.patch.object(wallet.Abstract_Wallet, 'save_db')
@ -767,7 +767,7 @@ class TestWalletSending(ElectrumTestCase):
async def test_sending_between_p2sh_2of3_and_uncompressed_p2pkh(self, mock_save_db): async def test_sending_between_p2sh_2of3_and_uncompressed_p2pkh(self, mock_save_db):
wallet1a = WalletIntegrityHelper.create_multisig_wallet( wallet1a = WalletIntegrityHelper.create_multisig_wallet(
[ [
keystore.from_seed('blast uniform dragon fiscal ensure vast young utility dinosaur abandon rookie sure', '', True), keystore.from_seed('blast uniform dragon fiscal ensure vast young utility dinosaur abandon rookie sure', passphrase='', for_multisig=True),
keystore.from_xpub('tpubD6NzVbkrYhZ4YTPEgwk4zzr8wyo7pXGmbbVUnfYNtx6SgAMF5q3LN3Kch58P9hxGNsTmP7Dn49nnrmpE6upoRb1Xojg12FGLuLHkVpVtS44'), keystore.from_xpub('tpubD6NzVbkrYhZ4YTPEgwk4zzr8wyo7pXGmbbVUnfYNtx6SgAMF5q3LN3Kch58P9hxGNsTmP7Dn49nnrmpE6upoRb1Xojg12FGLuLHkVpVtS44'),
keystore.from_xpub('tpubD6NzVbkrYhZ4XJzYkhsCbDCcZRmDAKSD7bXi9mdCni7acVt45fxbTVZyU6jRGh29ULKTjoapkfFsSJvQHitcVKbQgzgkkYsAmaovcro7Mhf') keystore.from_xpub('tpubD6NzVbkrYhZ4XJzYkhsCbDCcZRmDAKSD7bXi9mdCni7acVt45fxbTVZyU6jRGh29ULKTjoapkfFsSJvQHitcVKbQgzgkkYsAmaovcro7Mhf')
], ],
@ -776,7 +776,7 @@ class TestWalletSending(ElectrumTestCase):
) )
wallet1b = WalletIntegrityHelper.create_multisig_wallet( wallet1b = WalletIntegrityHelper.create_multisig_wallet(
[ [
keystore.from_seed('cycle rocket west magnet parrot shuffle foot correct salt library feed song', '', True), keystore.from_seed('cycle rocket west magnet parrot shuffle foot correct salt library feed song', passphrase='', for_multisig=True),
keystore.from_xpub('tpubD6NzVbkrYhZ4YTPEgwk4zzr8wyo7pXGmbbVUnfYNtx6SgAMF5q3LN3Kch58P9hxGNsTmP7Dn49nnrmpE6upoRb1Xojg12FGLuLHkVpVtS44'), keystore.from_xpub('tpubD6NzVbkrYhZ4YTPEgwk4zzr8wyo7pXGmbbVUnfYNtx6SgAMF5q3LN3Kch58P9hxGNsTmP7Dn49nnrmpE6upoRb1Xojg12FGLuLHkVpVtS44'),
keystore.from_xpub('tpubD6NzVbkrYhZ4YARFMEZPckrqJkw59GZD1PXtQnw14ukvWDofR7Z1HMeSCxfYEZVvg4VdZ8zGok5VxHwdrLqew5cMdQntWc5mT7mh1CSgrnX') keystore.from_xpub('tpubD6NzVbkrYhZ4YARFMEZPckrqJkw59GZD1PXtQnw14ukvWDofR7Z1HMeSCxfYEZVvg4VdZ8zGok5VxHwdrLqew5cMdQntWc5mT7mh1CSgrnX')
], ],
@ -849,7 +849,7 @@ class TestWalletSending(ElectrumTestCase):
async def test_sending_between_p2wsh_2of3_and_p2wsh_p2sh_2of2(self, mock_save_db): async def test_sending_between_p2wsh_2of3_and_p2wsh_p2sh_2of2(self, mock_save_db):
wallet1a = WalletIntegrityHelper.create_multisig_wallet( wallet1a = WalletIntegrityHelper.create_multisig_wallet(
[ [
keystore.from_seed('bitter grass shiver impose acquire brush forget axis eager alone wine silver', '', True), keystore.from_seed('bitter grass shiver impose acquire brush forget axis eager alone wine silver', passphrase='', for_multisig=True),
keystore.from_xpub('Vpub5fcdcgEwTJmbmqAktuK8Kyq92fMf7sWkcP6oqAii2tG47dNbfkGEGUbfS9NuZaRywLkHE6EmUksrqo32ZL3ouLN1HTar6oRiHpDzKMAF1tf'), keystore.from_xpub('Vpub5fcdcgEwTJmbmqAktuK8Kyq92fMf7sWkcP6oqAii2tG47dNbfkGEGUbfS9NuZaRywLkHE6EmUksrqo32ZL3ouLN1HTar6oRiHpDzKMAF1tf'),
keystore.from_xpub('Vpub5fjkKyYnvSS4wBuakWTkNvZDaBM2vQ1MeXWq368VJHNr2eT8efqhpmZ6UUkb7s2dwCXv2Vuggjdhk4vZVyiAQTwUftvff73XcUGq2NQmWra') keystore.from_xpub('Vpub5fjkKyYnvSS4wBuakWTkNvZDaBM2vQ1MeXWq368VJHNr2eT8efqhpmZ6UUkb7s2dwCXv2Vuggjdhk4vZVyiAQTwUftvff73XcUGq2NQmWra')
], ],
@ -858,7 +858,7 @@ class TestWalletSending(ElectrumTestCase):
) )
wallet1b = WalletIntegrityHelper.create_multisig_wallet( wallet1b = WalletIntegrityHelper.create_multisig_wallet(
[ [
keystore.from_seed('snow nest raise royal more walk demise rotate smooth spirit canyon gun', '', True), keystore.from_seed('snow nest raise royal more walk demise rotate smooth spirit canyon gun', passphrase='', for_multisig=True),
keystore.from_xpub('Vpub5fjkKyYnvSS4wBuakWTkNvZDaBM2vQ1MeXWq368VJHNr2eT8efqhpmZ6UUkb7s2dwCXv2Vuggjdhk4vZVyiAQTwUftvff73XcUGq2NQmWra'), keystore.from_xpub('Vpub5fjkKyYnvSS4wBuakWTkNvZDaBM2vQ1MeXWq368VJHNr2eT8efqhpmZ6UUkb7s2dwCXv2Vuggjdhk4vZVyiAQTwUftvff73XcUGq2NQmWra'),
keystore.from_xpub('Vpub5gSKXzxK7FeKQedu2q1z9oJWxqvX72AArW3HSWpEhc8othDH8xMDu28gr7gf17sp492BuJod8Tn7anjvJrKpETwqnQqX7CS8fcYyUtedEMk') keystore.from_xpub('Vpub5gSKXzxK7FeKQedu2q1z9oJWxqvX72AArW3HSWpEhc8othDH8xMDu28gr7gf17sp492BuJod8Tn7anjvJrKpETwqnQqX7CS8fcYyUtedEMk')
], ],
@ -968,7 +968,7 @@ class TestWalletSending(ElectrumTestCase):
async def test_sending_between_p2sh_1of2_and_p2wpkh_p2sh(self, mock_save_db): async def test_sending_between_p2sh_1of2_and_p2wpkh_p2sh(self, mock_save_db):
wallet1a = WalletIntegrityHelper.create_multisig_wallet( wallet1a = WalletIntegrityHelper.create_multisig_wallet(
[ [
keystore.from_seed('phone guilt ancient scan defy gasp off rotate approve ill word exchange', '', True), keystore.from_seed('phone guilt ancient scan defy gasp off rotate approve ill word exchange', passphrase='', for_multisig=True),
keystore.from_xpub('tpubD6NzVbkrYhZ4YPZ3ntVjqSCxiUUv2jikrUBU73Q3iJ7Y8iR41oYf991L5fanv7ciHjbjokdK2bjYqg1BzEUDxucU9qM5WRdBiY738wmgLP4') keystore.from_xpub('tpubD6NzVbkrYhZ4YPZ3ntVjqSCxiUUv2jikrUBU73Q3iJ7Y8iR41oYf991L5fanv7ciHjbjokdK2bjYqg1BzEUDxucU9qM5WRdBiY738wmgLP4')
], ],
'1of2', gap_limit=2, '1of2', gap_limit=2,
@ -2152,12 +2152,12 @@ class TestWalletSending(ElectrumTestCase):
@mock.patch.object(wallet.Abstract_Wallet, 'save_db') @mock.patch.object(wallet.Abstract_Wallet, 'save_db')
async def test_coinjoin_between_two_p2wpkh_electrum_seeds(self, mock_save_db): async def test_coinjoin_between_two_p2wpkh_electrum_seeds(self, mock_save_db):
wallet1 = WalletIntegrityHelper.create_standard_wallet( wallet1 = WalletIntegrityHelper.create_standard_wallet(
keystore.from_seed('humor argue expand gain goat shiver remove morning security casual leopard degree', ''), keystore.from_seed('humor argue expand gain goat shiver remove morning security casual leopard degree', passphrase=''),
gap_limit=2, gap_limit=2,
config=self.config config=self.config
) )
wallet2 = WalletIntegrityHelper.create_standard_wallet( wallet2 = WalletIntegrityHelper.create_standard_wallet(
keystore.from_seed('couple fade lift useless text thank badge act august roof drastic violin', ''), keystore.from_seed('couple fade lift useless text thank badge act august roof drastic violin', passphrase=''),
gap_limit=2, gap_limit=2,
config=self.config config=self.config
) )
@ -2844,8 +2844,8 @@ class TestWalletSending(ElectrumTestCase):
"""When exporting a PSBT to be signed by a hw device, test that we populate """When exporting a PSBT to be signed by a hw device, test that we populate
the PSBT_GLOBAL_XPUB field with wallet xpubs. the PSBT_GLOBAL_XPUB field with wallet xpubs.
""" """
root_seed = keystore.bip39_to_seed("pulse mixture jazz invite dune enrich minor weapon mosquito flight fly vapor", '') root_seed = keystore.bip39_to_seed("pulse mixture jazz invite dune enrich minor weapon mosquito flight fly vapor", passphrase='')
ks = keystore.from_bip43_rootseed(root_seed, "m/84'/1'/0'") ks = keystore.from_bip43_rootseed(root_seed, derivation="m/84'/1'/0'")
wallet = WalletIntegrityHelper.create_standard_wallet(ks, gap_limit=2, config=self.config) wallet = WalletIntegrityHelper.create_standard_wallet(ks, gap_limit=2, config=self.config)
# bootstrap wallet # bootstrap wallet
@ -2883,7 +2883,9 @@ class TestWalletSending(ElectrumTestCase):
""" """
wallet1a = WalletIntegrityHelper.create_multisig_wallet( wallet1a = WalletIntegrityHelper.create_multisig_wallet(
[ [
keystore.from_bip43_rootseed(keystore.bip39_to_seed("income sample useless art skate lucky fold field bargain course hope chest", ''), "m/45h/0", xtype="standard"), keystore.from_bip43_rootseed(
keystore.bip39_to_seed("income sample useless art skate lucky fold field bargain course hope chest", passphrase=''),
derivation="m/45h/0", xtype="standard"),
keystore.from_xpub('tpubDC1y33c2iTcxCBFva3zxbQxUnbzBT1TPVrwLgwVHtqSnVRx2pbJsrHzNYmXnKEnrNqyKk9BERrpSatqVu4JHV4K4hepFQdqnMojA5NVKxcF'), keystore.from_xpub('tpubDC1y33c2iTcxCBFva3zxbQxUnbzBT1TPVrwLgwVHtqSnVRx2pbJsrHzNYmXnKEnrNqyKk9BERrpSatqVu4JHV4K4hepFQdqnMojA5NVKxcF'),
], ],
'2of2', gap_limit=2, '2of2', gap_limit=2,
@ -2902,7 +2904,9 @@ class TestWalletSending(ElectrumTestCase):
wallet1b.get_keystores()[1].add_key_origin(derivation_prefix="m/45h/0", root_fingerprint="25750cf7") wallet1b.get_keystores()[1].add_key_origin(derivation_prefix="m/45h/0", root_fingerprint="25750cf7")
wallet1b_offline = WalletIntegrityHelper.create_multisig_wallet( wallet1b_offline = WalletIntegrityHelper.create_multisig_wallet(
[ [
keystore.from_bip43_rootseed(keystore.bip39_to_seed("wear wasp subject october amount essay maximum monkey excuse plastic ginger donor", ''), "m/45h/0", xtype="standard"), keystore.from_bip43_rootseed(
keystore.bip39_to_seed("wear wasp subject october amount essay maximum monkey excuse plastic ginger donor", passphrase=''),
derivation="m/45h/0", xtype="standard"),
keystore.from_xpub('tpubDAKtPDG6fezcwhB7rNJ9NVEWwGokNzowW3AaMVYFTS4WKoBTNESS1NpntWYDq2uABVYM1xa5cVmu8LD2xKYipMRVLy1VjBQeVe6pixJeBgr'), keystore.from_xpub('tpubDAKtPDG6fezcwhB7rNJ9NVEWwGokNzowW3AaMVYFTS4WKoBTNESS1NpntWYDq2uABVYM1xa5cVmu8LD2xKYipMRVLy1VjBQeVe6pixJeBgr'),
], ],
'2of2', gap_limit=2, '2of2', gap_limit=2,
@ -3055,7 +3059,7 @@ class TestWalletOfflineSigning(ElectrumTestCase):
@mock.patch.object(wallet.Abstract_Wallet, 'save_db') @mock.patch.object(wallet.Abstract_Wallet, 'save_db')
async def test_sending_offline_old_electrum_seed_online_mpk(self, mock_save_db): async def test_sending_offline_old_electrum_seed_online_mpk(self, mock_save_db):
wallet_offline = WalletIntegrityHelper.create_standard_wallet( wallet_offline = WalletIntegrityHelper.create_standard_wallet(
keystore.from_seed('alone body father children lead goodbye phone twist exist grass kick join', '', False), keystore.from_seed('alone body father children lead goodbye phone twist exist grass kick join', passphrase='', for_multisig=False),
gap_limit=4, gap_limit=4,
config=self.config config=self.config
) )
@ -3568,7 +3572,7 @@ class TestWalletOfflineSigning(ElectrumTestCase):
# 2-of-3 legacy p2sh multisig # 2-of-3 legacy p2sh multisig
wallet_offline1 = WalletIntegrityHelper.create_multisig_wallet( wallet_offline1 = WalletIntegrityHelper.create_multisig_wallet(
[ [
keystore.from_seed('blast uniform dragon fiscal ensure vast young utility dinosaur abandon rookie sure', '', True), keystore.from_seed('blast uniform dragon fiscal ensure vast young utility dinosaur abandon rookie sure', passphrase='', for_multisig=True),
keystore.from_xpub('tpubD6NzVbkrYhZ4YTPEgwk4zzr8wyo7pXGmbbVUnfYNtx6SgAMF5q3LN3Kch58P9hxGNsTmP7Dn49nnrmpE6upoRb1Xojg12FGLuLHkVpVtS44'), keystore.from_xpub('tpubD6NzVbkrYhZ4YTPEgwk4zzr8wyo7pXGmbbVUnfYNtx6SgAMF5q3LN3Kch58P9hxGNsTmP7Dn49nnrmpE6upoRb1Xojg12FGLuLHkVpVtS44'),
keystore.from_xpub('tpubD6NzVbkrYhZ4XJzYkhsCbDCcZRmDAKSD7bXi9mdCni7acVt45fxbTVZyU6jRGh29ULKTjoapkfFsSJvQHitcVKbQgzgkkYsAmaovcro7Mhf') keystore.from_xpub('tpubD6NzVbkrYhZ4XJzYkhsCbDCcZRmDAKSD7bXi9mdCni7acVt45fxbTVZyU6jRGh29ULKTjoapkfFsSJvQHitcVKbQgzgkkYsAmaovcro7Mhf')
], ],
@ -3577,7 +3581,7 @@ class TestWalletOfflineSigning(ElectrumTestCase):
) )
wallet_offline2 = WalletIntegrityHelper.create_multisig_wallet( wallet_offline2 = WalletIntegrityHelper.create_multisig_wallet(
[ [
keystore.from_seed('cycle rocket west magnet parrot shuffle foot correct salt library feed song', '', True), keystore.from_seed('cycle rocket west magnet parrot shuffle foot correct salt library feed song', passphrase='', for_multisig=True),
keystore.from_xpub('tpubD6NzVbkrYhZ4YTPEgwk4zzr8wyo7pXGmbbVUnfYNtx6SgAMF5q3LN3Kch58P9hxGNsTmP7Dn49nnrmpE6upoRb1Xojg12FGLuLHkVpVtS44'), keystore.from_xpub('tpubD6NzVbkrYhZ4YTPEgwk4zzr8wyo7pXGmbbVUnfYNtx6SgAMF5q3LN3Kch58P9hxGNsTmP7Dn49nnrmpE6upoRb1Xojg12FGLuLHkVpVtS44'),
keystore.from_xpub('tpubD6NzVbkrYhZ4YARFMEZPckrqJkw59GZD1PXtQnw14ukvWDofR7Z1HMeSCxfYEZVvg4VdZ8zGok5VxHwdrLqew5cMdQntWc5mT7mh1CSgrnX') keystore.from_xpub('tpubD6NzVbkrYhZ4YARFMEZPckrqJkw59GZD1PXtQnw14ukvWDofR7Z1HMeSCxfYEZVvg4VdZ8zGok5VxHwdrLqew5cMdQntWc5mT7mh1CSgrnX')
], ],
@ -3704,7 +3708,7 @@ class TestWalletOfflineSigning(ElectrumTestCase):
# 2-of-3 p2wsh multisig # 2-of-3 p2wsh multisig
wallet_offline1 = WalletIntegrityHelper.create_multisig_wallet( wallet_offline1 = WalletIntegrityHelper.create_multisig_wallet(
[ [
keystore.from_seed('bitter grass shiver impose acquire brush forget axis eager alone wine silver', '', True), keystore.from_seed('bitter grass shiver impose acquire brush forget axis eager alone wine silver', passphrase='', for_multisig=True),
keystore.from_xpub('Vpub5fcdcgEwTJmbmqAktuK8Kyq92fMf7sWkcP6oqAii2tG47dNbfkGEGUbfS9NuZaRywLkHE6EmUksrqo32ZL3ouLN1HTar6oRiHpDzKMAF1tf'), keystore.from_xpub('Vpub5fcdcgEwTJmbmqAktuK8Kyq92fMf7sWkcP6oqAii2tG47dNbfkGEGUbfS9NuZaRywLkHE6EmUksrqo32ZL3ouLN1HTar6oRiHpDzKMAF1tf'),
keystore.from_xpub('Vpub5fjkKyYnvSS4wBuakWTkNvZDaBM2vQ1MeXWq368VJHNr2eT8efqhpmZ6UUkb7s2dwCXv2Vuggjdhk4vZVyiAQTwUftvff73XcUGq2NQmWra') keystore.from_xpub('Vpub5fjkKyYnvSS4wBuakWTkNvZDaBM2vQ1MeXWq368VJHNr2eT8efqhpmZ6UUkb7s2dwCXv2Vuggjdhk4vZVyiAQTwUftvff73XcUGq2NQmWra')
], ],
@ -3713,7 +3717,7 @@ class TestWalletOfflineSigning(ElectrumTestCase):
) )
wallet_offline2 = WalletIntegrityHelper.create_multisig_wallet( wallet_offline2 = WalletIntegrityHelper.create_multisig_wallet(
[ [
keystore.from_seed('snow nest raise royal more walk demise rotate smooth spirit canyon gun', '', True), keystore.from_seed('snow nest raise royal more walk demise rotate smooth spirit canyon gun', passphrase='', for_multisig=True),
keystore.from_xpub('Vpub5fjkKyYnvSS4wBuakWTkNvZDaBM2vQ1MeXWq368VJHNr2eT8efqhpmZ6UUkb7s2dwCXv2Vuggjdhk4vZVyiAQTwUftvff73XcUGq2NQmWra'), keystore.from_xpub('Vpub5fjkKyYnvSS4wBuakWTkNvZDaBM2vQ1MeXWq368VJHNr2eT8efqhpmZ6UUkb7s2dwCXv2Vuggjdhk4vZVyiAQTwUftvff73XcUGq2NQmWra'),
keystore.from_xpub('Vpub5gSKXzxK7FeKQedu2q1z9oJWxqvX72AArW3HSWpEhc8othDH8xMDu28gr7gf17sp492BuJod8Tn7anjvJrKpETwqnQqX7CS8fcYyUtedEMk') keystore.from_xpub('Vpub5gSKXzxK7FeKQedu2q1z9oJWxqvX72AArW3HSWpEhc8othDH8xMDu28gr7gf17sp492BuJod8Tn7anjvJrKpETwqnQqX7CS8fcYyUtedEMk')
], ],
@ -3780,7 +3784,7 @@ class TestWalletCreationChecks(ElectrumTestCase):
with self.assertRaises(Exception) as ctx1: with self.assertRaises(Exception) as ctx1:
w1 = WalletIntegrityHelper.create_multisig_wallet( w1 = WalletIntegrityHelper.create_multisig_wallet(
[ [
keystore.from_seed('bitter grass shiver impose acquire brush forget axis eager alone wine silver', '', True), keystore.from_seed('bitter grass shiver impose acquire brush forget axis eager alone wine silver', passphrase='', for_multisig=True),
keystore.from_xpub('Vpub5gSKXzxK7FeKQedu2q1z9oJWxqvX72AArW3HSWpEhc8othDH8xMDu28gr7gf17sp492BuJod8Tn7anjvJrKpETwqnQqX7CS8fcYyUtedEMk'), # collides with seed keystore.from_xpub('Vpub5gSKXzxK7FeKQedu2q1z9oJWxqvX72AArW3HSWpEhc8othDH8xMDu28gr7gf17sp492BuJod8Tn7anjvJrKpETwqnQqX7CS8fcYyUtedEMk'), # collides with seed
keystore.from_xpub('Vpub5fjkKyYnvSS4wBuakWTkNvZDaBM2vQ1MeXWq368VJHNr2eT8efqhpmZ6UUkb7s2dwCXv2Vuggjdhk4vZVyiAQTwUftvff73XcUGq2NQmWra'), keystore.from_xpub('Vpub5fjkKyYnvSS4wBuakWTkNvZDaBM2vQ1MeXWq368VJHNr2eT8efqhpmZ6UUkb7s2dwCXv2Vuggjdhk4vZVyiAQTwUftvff73XcUGq2NQmWra'),
], ],
@ -3792,7 +3796,7 @@ class TestWalletCreationChecks(ElectrumTestCase):
with self.assertRaises(Exception) as ctx2: with self.assertRaises(Exception) as ctx2:
w2 = WalletIntegrityHelper.create_multisig_wallet( w2 = WalletIntegrityHelper.create_multisig_wallet(
[ [
keystore.from_seed('bitter grass shiver impose acquire brush forget axis eager alone wine silver', '', True), keystore.from_seed('bitter grass shiver impose acquire brush forget axis eager alone wine silver', passphrase='', for_multisig=True),
keystore.from_xpub('Vpub5fcdcgEwTJmbmqAktuK8Kyq92fMf7sWkcP6oqAii2tG47dNbfkGEGUbfS9NuZaRywLkHE6EmUksrqo32ZL3ouLN1HTar6oRiHpDzKMAF1tf'), keystore.from_xpub('Vpub5fcdcgEwTJmbmqAktuK8Kyq92fMf7sWkcP6oqAii2tG47dNbfkGEGUbfS9NuZaRywLkHE6EmUksrqo32ZL3ouLN1HTar6oRiHpDzKMAF1tf'),
keystore.from_xpub('Vpub5fcdcgEwTJmbmqAktuK8Kyq92fMf7sWkcP6oqAii2tG47dNbfkGEGUbfS9NuZaRywLkHE6EmUksrqo32ZL3ouLN1HTar6oRiHpDzKMAF1tf'), keystore.from_xpub('Vpub5fcdcgEwTJmbmqAktuK8Kyq92fMf7sWkcP6oqAii2tG47dNbfkGEGUbfS9NuZaRywLkHE6EmUksrqo32ZL3ouLN1HTar6oRiHpDzKMAF1tf'),
], ],
@ -3803,7 +3807,7 @@ class TestWalletCreationChecks(ElectrumTestCase):
# all xpubs different. should not raise. # all xpubs different. should not raise.
w3 = WalletIntegrityHelper.create_multisig_wallet( w3 = WalletIntegrityHelper.create_multisig_wallet(
[ [
keystore.from_seed('bitter grass shiver impose acquire brush forget axis eager alone wine silver', '', True), keystore.from_seed('bitter grass shiver impose acquire brush forget axis eager alone wine silver', passphrase='', for_multisig=True),
keystore.from_xpub('Vpub5fcdcgEwTJmbmqAktuK8Kyq92fMf7sWkcP6oqAii2tG47dNbfkGEGUbfS9NuZaRywLkHE6EmUksrqo32ZL3ouLN1HTar6oRiHpDzKMAF1tf'), keystore.from_xpub('Vpub5fcdcgEwTJmbmqAktuK8Kyq92fMf7sWkcP6oqAii2tG47dNbfkGEGUbfS9NuZaRywLkHE6EmUksrqo32ZL3ouLN1HTar6oRiHpDzKMAF1tf'),
keystore.from_xpub('Vpub5fjkKyYnvSS4wBuakWTkNvZDaBM2vQ1MeXWq368VJHNr2eT8efqhpmZ6UUkb7s2dwCXv2Vuggjdhk4vZVyiAQTwUftvff73XcUGq2NQmWra'), keystore.from_xpub('Vpub5fjkKyYnvSS4wBuakWTkNvZDaBM2vQ1MeXWq368VJHNr2eT8efqhpmZ6UUkb7s2dwCXv2Vuggjdhk4vZVyiAQTwUftvff73XcUGq2NQmWra'),
], ],
@ -3829,7 +3833,7 @@ class TestWalletCreationChecks(ElectrumTestCase):
w1 = WalletIntegrityHelper.create_multisig_wallet( w1 = WalletIntegrityHelper.create_multisig_wallet(
[ [
keystore.from_xpub('tpubD6NzVbkrYhZ4XYdbWCGSusTDQRAX4UnuqcikJAkqMYxBkvnGfUBvXBE84eyQS6e4To3Pz1xwLrEuxGgQayn4dqVXwNM7dWh4U4DgHai2scz'), keystore.from_xpub('tpubD6NzVbkrYhZ4XYdbWCGSusTDQRAX4UnuqcikJAkqMYxBkvnGfUBvXBE84eyQS6e4To3Pz1xwLrEuxGgQayn4dqVXwNM7dWh4U4DgHai2scz'),
keystore.from_seed('bitter grass shiver impose acquire brush forget axis eager alone wine silver', '', True), keystore.from_seed('bitter grass shiver impose acquire brush forget axis eager alone wine silver', passphrase='', for_multisig=True),
], ],
'2of2', gap_limit=2, '2of2', gap_limit=2,
config=self.config config=self.config
@ -3839,8 +3843,8 @@ class TestWalletCreationChecks(ElectrumTestCase):
with self.assertRaises(Exception) as ctx3: with self.assertRaises(Exception) as ctx3:
w1 = WalletIntegrityHelper.create_multisig_wallet( w1 = WalletIntegrityHelper.create_multisig_wallet(
[ [
keystore.from_seed('cycle rocket west magnet parrot shuffle foot correct salt library feed song', '', True), keystore.from_seed('cycle rocket west magnet parrot shuffle foot correct salt library feed song', passphrase='', for_multisig=True),
keystore.from_seed('bitter grass shiver impose acquire brush forget axis eager alone wine silver', '', True), keystore.from_seed('bitter grass shiver impose acquire brush forget axis eager alone wine silver', passphrase='', for_multisig=True),
], ],
'2of2', gap_limit=2, '2of2', gap_limit=2,
config=self.config config=self.config
@ -3850,8 +3854,8 @@ class TestWalletCreationChecks(ElectrumTestCase):
with self.assertRaises(Exception) as ctx4: with self.assertRaises(Exception) as ctx4:
w1 = WalletIntegrityHelper.create_multisig_wallet( w1 = WalletIntegrityHelper.create_multisig_wallet(
[ [
keystore.from_seed('cycle rocket west magnet parrot shuffle foot correct salt library feed song', '', True), keystore.from_seed('cycle rocket west magnet parrot shuffle foot correct salt library feed song', passphrase='', for_multisig=True),
keystore.from_seed('powerful random nobody notice nothing important anyway look away hidden message over', '', True), keystore.from_seed('powerful random nobody notice nothing important anyway look away hidden message over', passphrase='', for_multisig=True),
], ],
'2of2', gap_limit=2, '2of2', gap_limit=2,
config=self.config config=self.config

Loading…
Cancel
Save