|
|
@ -5,7 +5,7 @@ import tempfile |
|
|
|
from typing import Sequence |
|
|
|
import asyncio |
|
|
|
|
|
|
|
from electrum import storage, bitcoin, keystore, bip32 |
|
|
|
from electrum import storage, bitcoin, keystore, bip32, wallet |
|
|
|
from electrum import Transaction |
|
|
|
from electrum import SimpleConfig |
|
|
|
from electrum.address_synchronizer import TX_HEIGHT_UNCONFIRMED, TX_HEIGHT_UNCONF_PARENT |
|
|
@ -46,33 +46,33 @@ class WalletIntegrityHelper: |
|
|
|
|
|
|
|
@classmethod |
|
|
|
def create_standard_wallet(cls, ks, *, config: SimpleConfig, gap_limit=None): |
|
|
|
store = storage.WalletStorage('if_this_exists_mocking_failed_648151893') |
|
|
|
store.put('keystore', ks.dump()) |
|
|
|
store.put('gap_limit', gap_limit or cls.gap_limit) |
|
|
|
w = Standard_Wallet(store, config=config) |
|
|
|
db = storage.WalletDB('', manual_upgrades=False) |
|
|
|
db.put('keystore', ks.dump()) |
|
|
|
db.put('gap_limit', gap_limit or cls.gap_limit) |
|
|
|
w = Standard_Wallet(db, None, config=config) |
|
|
|
w.synchronize() |
|
|
|
return w |
|
|
|
|
|
|
|
@classmethod |
|
|
|
def create_imported_wallet(cls, *, config: SimpleConfig, privkeys: bool): |
|
|
|
store = storage.WalletStorage('if_this_exists_mocking_failed_648151893') |
|
|
|
db = storage.WalletDB('', manual_upgrades=False) |
|
|
|
if privkeys: |
|
|
|
k = keystore.Imported_KeyStore({}) |
|
|
|
store.put('keystore', k.dump()) |
|
|
|
w = Imported_Wallet(store, config=config) |
|
|
|
db.put('keystore', k.dump()) |
|
|
|
w = Imported_Wallet(db, None, config=config) |
|
|
|
return w |
|
|
|
|
|
|
|
@classmethod |
|
|
|
def create_multisig_wallet(cls, keystores: Sequence, multisig_type: str, *, |
|
|
|
config: SimpleConfig, gap_limit=None): |
|
|
|
"""Creates a multisig wallet.""" |
|
|
|
store = storage.WalletStorage('if_this_exists_mocking_failed_648151893') |
|
|
|
db = storage.WalletDB('', manual_upgrades=True) |
|
|
|
for i, ks in enumerate(keystores): |
|
|
|
cosigner_index = i + 1 |
|
|
|
store.put('x%d/' % cosigner_index, ks.dump()) |
|
|
|
store.put('wallet_type', multisig_type) |
|
|
|
store.put('gap_limit', gap_limit or cls.gap_limit) |
|
|
|
w = Multisig_Wallet(store, config=config) |
|
|
|
db.put('x%d/' % cosigner_index, ks.dump()) |
|
|
|
db.put('wallet_type', multisig_type) |
|
|
|
db.put('gap_limit', gap_limit or cls.gap_limit) |
|
|
|
w = Multisig_Wallet(db, None, config=config) |
|
|
|
w.synchronize() |
|
|
|
return w |
|
|
|
|
|
|
@ -84,8 +84,8 @@ class TestWalletKeystoreAddressIntegrityForMainnet(ElectrumTestCase): |
|
|
|
self.config = SimpleConfig({'electrum_path': self.electrum_path}) |
|
|
|
|
|
|
|
@needs_test_with_all_ecc_implementations |
|
|
|
@mock.patch.object(storage.WalletStorage, '_write') |
|
|
|
def test_electrum_seed_standard(self, mock_write): |
|
|
|
@mock.patch.object(wallet.Abstract_Wallet, 'save_db') |
|
|
|
def test_electrum_seed_standard(self, mock_save_db): |
|
|
|
seed_words = 'cycle rocket west magnet parrot shuffle foot correct salt library feed song' |
|
|
|
self.assertEqual(seed_type(seed_words), 'standard') |
|
|
|
|
|
|
@ -104,8 +104,8 @@ class TestWalletKeystoreAddressIntegrityForMainnet(ElectrumTestCase): |
|
|
|
self.assertEqual(w.get_change_addresses()[0], '1KSezYMhAJMWqFbVFB2JshYg69UpmEXR4D') |
|
|
|
|
|
|
|
@needs_test_with_all_ecc_implementations |
|
|
|
@mock.patch.object(storage.WalletStorage, '_write') |
|
|
|
def test_electrum_seed_segwit(self, mock_write): |
|
|
|
@mock.patch.object(wallet.Abstract_Wallet, 'save_db') |
|
|
|
def test_electrum_seed_segwit(self, mock_save_db): |
|
|
|
seed_words = 'bitter grass shiver impose acquire brush forget axis eager alone wine silver' |
|
|
|
self.assertEqual(seed_type(seed_words), 'segwit') |
|
|
|
|
|
|
@ -124,8 +124,8 @@ class TestWalletKeystoreAddressIntegrityForMainnet(ElectrumTestCase): |
|
|
|
self.assertEqual(w.get_change_addresses()[0], 'bc1qdy94n2q5qcp0kg7v9yzwe6wvfkhnvyzje7nx2p') |
|
|
|
|
|
|
|
@needs_test_with_all_ecc_implementations |
|
|
|
@mock.patch.object(storage.WalletStorage, '_write') |
|
|
|
def test_electrum_seed_segwit_passphrase(self, mock_write): |
|
|
|
@mock.patch.object(wallet.Abstract_Wallet, 'save_db') |
|
|
|
def test_electrum_seed_segwit_passphrase(self, mock_save_db): |
|
|
|
seed_words = 'bitter grass shiver impose acquire brush forget axis eager alone wine silver' |
|
|
|
self.assertEqual(seed_type(seed_words), 'segwit') |
|
|
|
|
|
|
@ -144,8 +144,8 @@ class TestWalletKeystoreAddressIntegrityForMainnet(ElectrumTestCase): |
|
|
|
self.assertEqual(w.get_change_addresses()[0], 'bc1qcywwsy87sdp8vz5rfjh3sxdv6rt95kujdqq38g') |
|
|
|
|
|
|
|
@needs_test_with_all_ecc_implementations |
|
|
|
@mock.patch.object(storage.WalletStorage, '_write') |
|
|
|
def test_electrum_seed_old(self, mock_write): |
|
|
|
@mock.patch.object(wallet.Abstract_Wallet, 'save_db') |
|
|
|
def test_electrum_seed_old(self, mock_save_db): |
|
|
|
seed_words = 'powerful random nobody notice nothing important anyway look away hidden message over' |
|
|
|
self.assertEqual(seed_type(seed_words), 'old') |
|
|
|
|
|
|
@ -163,8 +163,8 @@ class TestWalletKeystoreAddressIntegrityForMainnet(ElectrumTestCase): |
|
|
|
self.assertEqual(w.get_change_addresses()[0], '1KRW8pH6HFHZh889VDq6fEKvmrsmApwNfe') |
|
|
|
|
|
|
|
@needs_test_with_all_ecc_implementations |
|
|
|
@mock.patch.object(storage.WalletStorage, '_write') |
|
|
|
def test_electrum_seed_2fa_legacy(self, mock_write): |
|
|
|
@mock.patch.object(wallet.Abstract_Wallet, 'save_db') |
|
|
|
def test_electrum_seed_2fa_legacy(self, mock_save_db): |
|
|
|
seed_words = 'kiss live scene rude gate step hip quarter bunker oxygen motor glove' |
|
|
|
self.assertEqual(seed_type(seed_words), '2fa') |
|
|
|
|
|
|
@ -198,8 +198,8 @@ class TestWalletKeystoreAddressIntegrityForMainnet(ElectrumTestCase): |
|
|
|
self.assertEqual(w.get_change_addresses()[0], '3PeZEcumRqHSPNN43hd4yskGEBdzXgY8Cy') |
|
|
|
|
|
|
|
@needs_test_with_all_ecc_implementations |
|
|
|
@mock.patch.object(storage.WalletStorage, '_write') |
|
|
|
def test_electrum_seed_2fa_segwit(self, mock_write): |
|
|
|
@mock.patch.object(wallet.Abstract_Wallet, 'save_db') |
|
|
|
def test_electrum_seed_2fa_segwit(self, mock_save_db): |
|
|
|
seed_words = 'universe topic remind silver february ranch shine worth innocent cattle enhance wise' |
|
|
|
self.assertEqual(seed_type(seed_words), '2fa_segwit') |
|
|
|
|
|
|
@ -233,8 +233,8 @@ class TestWalletKeystoreAddressIntegrityForMainnet(ElectrumTestCase): |
|
|
|
self.assertEqual(w.get_change_addresses()[0], 'bc1qd4q50nft7kxm9yglfnpup9ed2ukj3tkxp793y0zya8dc9m39jcwq308dxz') |
|
|
|
|
|
|
|
@needs_test_with_all_ecc_implementations |
|
|
|
@mock.patch.object(storage.WalletStorage, '_write') |
|
|
|
def test_bip39_seed_bip44_standard(self, mock_write): |
|
|
|
@mock.patch.object(wallet.Abstract_Wallet, 'save_db') |
|
|
|
def test_bip39_seed_bip44_standard(self, mock_save_db): |
|
|
|
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)) |
|
|
|
|
|
|
@ -252,8 +252,8 @@ class TestWalletKeystoreAddressIntegrityForMainnet(ElectrumTestCase): |
|
|
|
self.assertEqual(w.get_change_addresses()[0], '1GG5bVeWgAp5XW7JLCphse14QaC4qiHyWn') |
|
|
|
|
|
|
|
@needs_test_with_all_ecc_implementations |
|
|
|
@mock.patch.object(storage.WalletStorage, '_write') |
|
|
|
def test_bip39_seed_bip44_standard_passphrase(self, mock_write): |
|
|
|
@mock.patch.object(wallet.Abstract_Wallet, 'save_db') |
|
|
|
def test_bip39_seed_bip44_standard_passphrase(self, mock_save_db): |
|
|
|
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)) |
|
|
|
|
|
|
@ -271,8 +271,8 @@ class TestWalletKeystoreAddressIntegrityForMainnet(ElectrumTestCase): |
|
|
|
self.assertEqual(w.get_change_addresses()[0], '1H4QD1rg2zQJ4UjuAVJr5eW1fEM8WMqyxh') |
|
|
|
|
|
|
|
@needs_test_with_all_ecc_implementations |
|
|
|
@mock.patch.object(storage.WalletStorage, '_write') |
|
|
|
def test_bip39_seed_bip49_p2sh_segwit(self, mock_write): |
|
|
|
@mock.patch.object(wallet.Abstract_Wallet, 'save_db') |
|
|
|
def test_bip39_seed_bip49_p2sh_segwit(self, mock_save_db): |
|
|
|
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)) |
|
|
|
|
|
|
@ -290,8 +290,8 @@ class TestWalletKeystoreAddressIntegrityForMainnet(ElectrumTestCase): |
|
|
|
self.assertEqual(w.get_change_addresses()[0], '3KaBTcviBLEJajTEMstsA2GWjYoPzPK7Y7') |
|
|
|
|
|
|
|
@needs_test_with_all_ecc_implementations |
|
|
|
@mock.patch.object(storage.WalletStorage, '_write') |
|
|
|
def test_bip39_seed_bip84_native_segwit(self, mock_write): |
|
|
|
@mock.patch.object(wallet.Abstract_Wallet, 'save_db') |
|
|
|
def test_bip39_seed_bip84_native_segwit(self, mock_save_db): |
|
|
|
# test case from bip84 |
|
|
|
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)) |
|
|
@ -310,8 +310,8 @@ class TestWalletKeystoreAddressIntegrityForMainnet(ElectrumTestCase): |
|
|
|
self.assertEqual(w.get_change_addresses()[0], 'bc1q8c6fshw2dlwun7ekn9qwf37cu2rn755upcp6el') |
|
|
|
|
|
|
|
@needs_test_with_all_ecc_implementations |
|
|
|
@mock.patch.object(storage.WalletStorage, '_write') |
|
|
|
def test_electrum_multisig_seed_standard(self, mock_write): |
|
|
|
@mock.patch.object(wallet.Abstract_Wallet, 'save_db') |
|
|
|
def test_electrum_multisig_seed_standard(self, mock_save_db): |
|
|
|
seed_words = 'blast uniform dragon fiscal ensure vast young utility dinosaur abandon rookie sure' |
|
|
|
self.assertEqual(seed_type(seed_words), 'standard') |
|
|
|
|
|
|
@ -333,8 +333,8 @@ class TestWalletKeystoreAddressIntegrityForMainnet(ElectrumTestCase): |
|
|
|
self.assertEqual(w.get_change_addresses()[0], '36XWwEHrrVCLnhjK5MrVVGmUHghr9oWTN1') |
|
|
|
|
|
|
|
@needs_test_with_all_ecc_implementations |
|
|
|
@mock.patch.object(storage.WalletStorage, '_write') |
|
|
|
def test_electrum_multisig_seed_segwit(self, mock_write): |
|
|
|
@mock.patch.object(wallet.Abstract_Wallet, 'save_db') |
|
|
|
def test_electrum_multisig_seed_segwit(self, mock_save_db): |
|
|
|
seed_words = 'snow nest raise royal more walk demise rotate smooth spirit canyon gun' |
|
|
|
self.assertEqual(seed_type(seed_words), 'segwit') |
|
|
|
|
|
|
@ -356,8 +356,8 @@ class TestWalletKeystoreAddressIntegrityForMainnet(ElectrumTestCase): |
|
|
|
self.assertEqual(w.get_change_addresses()[0], 'bc1qxqf840dqswcmu7a8v82fj6ej0msx08flvuy6kngr7axstjcaq6us9hrehd') |
|
|
|
|
|
|
|
@needs_test_with_all_ecc_implementations |
|
|
|
@mock.patch.object(storage.WalletStorage, '_write') |
|
|
|
def test_bip39_multisig_seed_bip45_standard(self, mock_write): |
|
|
|
@mock.patch.object(wallet.Abstract_Wallet, 'save_db') |
|
|
|
def test_bip39_multisig_seed_bip45_standard(self, mock_save_db): |
|
|
|
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)) |
|
|
|
|
|
|
@ -379,8 +379,8 @@ class TestWalletKeystoreAddressIntegrityForMainnet(ElectrumTestCase): |
|
|
|
self.assertEqual(w.get_change_addresses()[0], '3FGyDuxgUDn2pSZe5xAJH1yUwSdhzDMyEE') |
|
|
|
|
|
|
|
@needs_test_with_all_ecc_implementations |
|
|
|
@mock.patch.object(storage.WalletStorage, '_write') |
|
|
|
def test_bip39_multisig_seed_p2sh_segwit(self, mock_write): |
|
|
|
@mock.patch.object(wallet.Abstract_Wallet, 'save_db') |
|
|
|
def test_bip39_multisig_seed_p2sh_segwit(self, mock_save_db): |
|
|
|
# bip39 seed: pulse mixture jazz invite dune enrich minor weapon mosquito flight fly vapor |
|
|
|
# der: m/49'/0'/0' |
|
|
|
# NOTE: there is currently no bip43 standard derivation path for p2wsh-p2sh |
|
|
@ -401,8 +401,8 @@ class TestWalletKeystoreAddressIntegrityForMainnet(ElectrumTestCase): |
|
|
|
self.assertEqual(w.get_change_addresses()[0], '39RhtDchc6igmx5tyoimhojFL1ZbQBrXa6') |
|
|
|
|
|
|
|
@needs_test_with_all_ecc_implementations |
|
|
|
@mock.patch.object(storage.WalletStorage, '_write') |
|
|
|
def test_bip32_extended_version_bytes(self, mock_write): |
|
|
|
@mock.patch.object(wallet.Abstract_Wallet, 'save_db') |
|
|
|
def test_bip32_extended_version_bytes(self, mock_save_db): |
|
|
|
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)) |
|
|
|
bip32_seed = keystore.bip39_to_seed(seed_words, '') |
|
|
@ -467,8 +467,8 @@ class TestWalletKeystoreAddressIntegrityForTestnet(TestCaseForTestnet): |
|
|
|
super().setUp() |
|
|
|
self.config = SimpleConfig({'electrum_path': self.electrum_path}) |
|
|
|
|
|
|
|
@mock.patch.object(storage.WalletStorage, '_write') |
|
|
|
def test_bip39_multisig_seed_p2sh_segwit_testnet(self, mock_write): |
|
|
|
@mock.patch.object(wallet.Abstract_Wallet, 'save_db') |
|
|
|
def test_bip39_multisig_seed_p2sh_segwit_testnet(self, mock_save_db): |
|
|
|
# bip39 seed: finish seminar arrange erosion sunny coil insane together pretty lunch lunch rose |
|
|
|
# der: m/49'/1'/0' |
|
|
|
# NOTE: there is currently no bip43 standard derivation path for p2wsh-p2sh |
|
|
@ -489,8 +489,8 @@ class TestWalletKeystoreAddressIntegrityForTestnet(TestCaseForTestnet): |
|
|
|
self.assertEqual(w.get_change_addresses()[0], '2NFp9w8tbYYP9Ze2xQpeYBJQjx3gbXymHX7') |
|
|
|
|
|
|
|
@needs_test_with_all_ecc_implementations |
|
|
|
@mock.patch.object(storage.WalletStorage, '_write') |
|
|
|
def test_bip32_extended_version_bytes(self, mock_write): |
|
|
|
@mock.patch.object(wallet.Abstract_Wallet, 'save_db') |
|
|
|
def test_bip32_extended_version_bytes(self, mock_save_db): |
|
|
|
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)) |
|
|
|
bip32_seed = keystore.bip39_to_seed(seed_words, '') |
|
|
@ -560,8 +560,8 @@ class TestWalletSending(TestCaseForTestnet): |
|
|
|
return WalletIntegrityHelper.create_standard_wallet(ks, gap_limit=2, config=self.config) |
|
|
|
|
|
|
|
@needs_test_with_all_ecc_implementations |
|
|
|
@mock.patch.object(storage.WalletStorage, '_write') |
|
|
|
def test_sending_between_p2wpkh_and_compressed_p2pkh(self, mock_write): |
|
|
|
@mock.patch.object(wallet.Abstract_Wallet, 'save_db') |
|
|
|
def test_sending_between_p2wpkh_and_compressed_p2pkh(self, mock_save_db): |
|
|
|
wallet1 = self.create_standard_wallet_from_seed('bitter grass shiver impose acquire brush forget axis eager alone wine silver') |
|
|
|
wallet2 = self.create_standard_wallet_from_seed('cycle rocket west magnet parrot shuffle foot correct salt library feed song') |
|
|
|
|
|
|
@ -617,8 +617,8 @@ class TestWalletSending(TestCaseForTestnet): |
|
|
|
self.assertEqual((0, 250000 - 5000 - 100000, 0), wallet2.get_balance()) |
|
|
|
|
|
|
|
@needs_test_with_all_ecc_implementations |
|
|
|
@mock.patch.object(storage.WalletStorage, '_write') |
|
|
|
def test_sending_between_p2sh_2of3_and_uncompressed_p2pkh(self, mock_write): |
|
|
|
@mock.patch.object(wallet.Abstract_Wallet, 'save_db') |
|
|
|
def test_sending_between_p2sh_2of3_and_uncompressed_p2pkh(self, mock_save_db): |
|
|
|
wallet1a = WalletIntegrityHelper.create_multisig_wallet( |
|
|
|
[ |
|
|
|
keystore.from_seed('blast uniform dragon fiscal ensure vast young utility dinosaur abandon rookie sure', '', True), |
|
|
@ -698,8 +698,8 @@ class TestWalletSending(TestCaseForTestnet): |
|
|
|
self.assertEqual((0, 370000 - 5000 - 100000, 0), wallet2.get_balance()) |
|
|
|
|
|
|
|
@needs_test_with_all_ecc_implementations |
|
|
|
@mock.patch.object(storage.WalletStorage, '_write') |
|
|
|
def test_sending_between_p2wsh_2of3_and_p2wsh_p2sh_2of2(self, mock_write): |
|
|
|
@mock.patch.object(wallet.Abstract_Wallet, 'save_db') |
|
|
|
def test_sending_between_p2wsh_2of3_and_p2wsh_p2sh_2of2(self, mock_save_db): |
|
|
|
wallet1a = WalletIntegrityHelper.create_multisig_wallet( |
|
|
|
[ |
|
|
|
keystore.from_seed('bitter grass shiver impose acquire brush forget axis eager alone wine silver', '', True), |
|
|
@ -808,8 +808,8 @@ class TestWalletSending(TestCaseForTestnet): |
|
|
|
self.assertEqual((0, 165000 - 5000 - 100000, 0), wallet2a.get_balance()) |
|
|
|
|
|
|
|
@needs_test_with_all_ecc_implementations |
|
|
|
@mock.patch.object(storage.WalletStorage, '_write') |
|
|
|
def test_sending_between_p2sh_1of2_and_p2wpkh_p2sh(self, mock_write): |
|
|
|
@mock.patch.object(wallet.Abstract_Wallet, 'save_db') |
|
|
|
def test_sending_between_p2sh_1of2_and_p2wpkh_p2sh(self, mock_save_db): |
|
|
|
wallet1a = WalletIntegrityHelper.create_multisig_wallet( |
|
|
|
[ |
|
|
|
keystore.from_seed('phone guilt ancient scan defy gasp off rotate approve ill word exchange', '', True), |
|
|
@ -878,8 +878,8 @@ class TestWalletSending(TestCaseForTestnet): |
|
|
|
self.assertEqual((0, 1000000 - 5000 - 300000, 0), wallet2.get_balance()) |
|
|
|
|
|
|
|
@needs_test_with_all_ecc_implementations |
|
|
|
@mock.patch.object(storage.WalletStorage, '_write') |
|
|
|
def test_rbf(self, mock_write): |
|
|
|
@mock.patch.object(wallet.Abstract_Wallet, 'save_db') |
|
|
|
def test_rbf(self, mock_save_db): |
|
|
|
self.maxDiff = None |
|
|
|
for simulate_moving_txs in (False, True): |
|
|
|
with self.subTest(msg="_bump_fee_p2pkh_when_there_is_a_change_address", simulate_moving_txs=simulate_moving_txs): |
|
|
@ -959,8 +959,8 @@ class TestWalletSending(TestCaseForTestnet): |
|
|
|
self.assertEqual((0, 7484320, 0), wallet.get_balance()) |
|
|
|
|
|
|
|
@needs_test_with_all_ecc_implementations |
|
|
|
@mock.patch.object(storage.WalletStorage, '_write') |
|
|
|
def test_cpfp_p2pkh(self, mock_write): |
|
|
|
@mock.patch.object(wallet.Abstract_Wallet, 'save_db') |
|
|
|
def test_cpfp_p2pkh(self, mock_save_db): |
|
|
|
wallet = self.create_standard_wallet_from_seed('fold object utility erase deputy output stadium feed stereo usage modify bean') |
|
|
|
|
|
|
|
# bootstrap wallet |
|
|
@ -1361,8 +1361,8 @@ class TestWalletSending(TestCaseForTestnet): |
|
|
|
self.assertEqual((0, 3_900_000, 0), wallet.get_balance()) |
|
|
|
|
|
|
|
@needs_test_with_all_ecc_implementations |
|
|
|
@mock.patch.object(storage.WalletStorage, '_write') |
|
|
|
def test_cpfp_p2wpkh(self, mock_write): |
|
|
|
@mock.patch.object(wallet.Abstract_Wallet, 'save_db') |
|
|
|
def test_cpfp_p2wpkh(self, mock_save_db): |
|
|
|
wallet = self.create_standard_wallet_from_seed('frost repair depend effort salon ring foam oak cancel receive save usage') |
|
|
|
|
|
|
|
# bootstrap wallet |
|
|
@ -1420,8 +1420,8 @@ class TestWalletSending(TestCaseForTestnet): |
|
|
|
self.assertEqual('7f827fc5256c274fd1094eb7e020c8ded0baf820356f61aa4f14a9093b0ea0ee', tx_copy.wtxid()) |
|
|
|
|
|
|
|
@needs_test_with_all_ecc_implementations |
|
|
|
@mock.patch.object(storage.WalletStorage, '_write') |
|
|
|
def test_coinjoin_between_two_p2wpkh_electrum_seeds(self, mock_write): |
|
|
|
@mock.patch.object(wallet.Abstract_Wallet, 'save_db') |
|
|
|
def test_coinjoin_between_two_p2wpkh_electrum_seeds(self, mock_save_db): |
|
|
|
wallet1 = WalletIntegrityHelper.create_standard_wallet( |
|
|
|
keystore.from_seed('humor argue expand gain goat shiver remove morning security casual leopard degree', ''), |
|
|
|
gap_limit=2, |
|
|
@ -1512,8 +1512,8 @@ class TestWalletOfflineSigning(TestCaseForTestnet): |
|
|
|
self.config = SimpleConfig({'electrum_path': self.electrum_path}) |
|
|
|
|
|
|
|
@needs_test_with_all_ecc_implementations |
|
|
|
@mock.patch.object(storage.WalletStorage, '_write') |
|
|
|
def test_sending_offline_old_electrum_seed_online_mpk(self, mock_write): |
|
|
|
@mock.patch.object(wallet.Abstract_Wallet, 'save_db') |
|
|
|
def test_sending_offline_old_electrum_seed_online_mpk(self, mock_save_db): |
|
|
|
wallet_offline = WalletIntegrityHelper.create_standard_wallet( |
|
|
|
keystore.from_seed('alone body father children lead goodbye phone twist exist grass kick join', '', False), |
|
|
|
gap_limit=4, |
|
|
@ -1559,8 +1559,8 @@ class TestWalletOfflineSigning(TestCaseForTestnet): |
|
|
|
self.assertEqual('06032230d0bf6a277bc4f8c39e3311a712e0e614626d0dea7cc9f592abfae5d8', tx.wtxid()) |
|
|
|
|
|
|
|
@needs_test_with_all_ecc_implementations |
|
|
|
@mock.patch.object(storage.WalletStorage, '_write') |
|
|
|
def test_sending_offline_xprv_online_xpub_p2pkh(self, mock_write): |
|
|
|
@mock.patch.object(wallet.Abstract_Wallet, 'save_db') |
|
|
|
def test_sending_offline_xprv_online_xpub_p2pkh(self, mock_save_db): |
|
|
|
wallet_offline = WalletIntegrityHelper.create_standard_wallet( |
|
|
|
# bip39: "qwe", der: m/44'/1'/0' |
|
|
|
keystore.from_xprv('tprv8gfKwjuAaqtHgqxMh1tosAQ28XvBMkcY5NeFRA3pZMpz6MR4H4YZ3MJM4fvNPnRKeXR1Td2vQGgjorNXfo94WvT5CYDsPAqjHxSn436G1Eu'), |
|
|
@ -1605,8 +1605,8 @@ class TestWalletOfflineSigning(TestCaseForTestnet): |
|
|
|
self.assertEqual('d9c21696eca80321933e7444ca928aaf25eeda81aaa2f4e5c085d4d0a9cf7aa7', tx.wtxid()) |
|
|
|
|
|
|
|
@needs_test_with_all_ecc_implementations |
|
|
|
@mock.patch.object(storage.WalletStorage, '_write') |
|
|
|
def test_sending_offline_xprv_online_xpub_p2wpkh_p2sh(self, mock_write): |
|
|
|
@mock.patch.object(wallet.Abstract_Wallet, 'save_db') |
|
|
|
def test_sending_offline_xprv_online_xpub_p2wpkh_p2sh(self, mock_save_db): |
|
|
|
wallet_offline = WalletIntegrityHelper.create_standard_wallet( |
|
|
|
# bip39: "qwe", der: m/49'/1'/0' |
|
|
|
keystore.from_xprv('uprv8zHHrMQMQ26utWwNJ5MK2SXpB9hbmy7pbPaneii69xT8cZTyFpxQFxkknGWKP8dxBTZhzy7yP6cCnLrRCQjzJDk3G61SjZpxhFQuB2NR8a5'), |
|
|
@ -1652,8 +1652,8 @@ class TestWalletOfflineSigning(TestCaseForTestnet): |
|
|
|
self.assertEqual('27b78ec072a403b0545258e7a1a8d494e4b6fd48bf77f4251a12160c92207cbc', tx.wtxid()) |
|
|
|
|
|
|
|
@needs_test_with_all_ecc_implementations |
|
|
|
@mock.patch.object(storage.WalletStorage, '_write') |
|
|
|
def test_sending_offline_xprv_online_xpub_p2wpkh(self, mock_write): |
|
|
|
@mock.patch.object(wallet.Abstract_Wallet, 'save_db') |
|
|
|
def test_sending_offline_xprv_online_xpub_p2wpkh(self, mock_save_db): |
|
|
|
wallet_offline = WalletIntegrityHelper.create_standard_wallet( |
|
|
|
# bip39: "qwe", der: m/84'/1'/0' |
|
|
|
keystore.from_xprv('vprv9K9hbuA23Bidgj1KRSHUZMa59jJLeZBpXPVn4RP7sBLArNhZxJjw4AX7aQmVTErDt4YFC11ptMLjbwxgrsH8GLQ1cx77KggWeVPeDBjr9xM'), |
|
|
@ -1699,8 +1699,8 @@ class TestWalletOfflineSigning(TestCaseForTestnet): |
|
|
|
self.assertEqual('484e350beaa722a744bb3e2aa38de005baa8526d86536d6143e5814355acf775', tx.wtxid()) |
|
|
|
|
|
|
|
@needs_test_with_all_ecc_implementations |
|
|
|
@mock.patch.object(storage.WalletStorage, '_write') |
|
|
|
def test_offline_signing_beyond_gap_limit(self, mock_write): |
|
|
|
@mock.patch.object(wallet.Abstract_Wallet, 'save_db') |
|
|
|
def test_offline_signing_beyond_gap_limit(self, mock_save_db): |
|
|
|
wallet_offline = WalletIntegrityHelper.create_standard_wallet( |
|
|
|
# bip39: "qwe", der: m/84'/1'/0' |
|
|
|
keystore.from_xprv('vprv9K9hbuA23Bidgj1KRSHUZMa59jJLeZBpXPVn4RP7sBLArNhZxJjw4AX7aQmVTErDt4YFC11ptMLjbwxgrsH8GLQ1cx77KggWeVPeDBjr9xM'), |
|
|
@ -1746,8 +1746,8 @@ class TestWalletOfflineSigning(TestCaseForTestnet): |
|
|
|
self.assertEqual('484e350beaa722a744bb3e2aa38de005baa8526d86536d6143e5814355acf775', tx.wtxid()) |
|
|
|
|
|
|
|
@needs_test_with_all_ecc_implementations |
|
|
|
@mock.patch.object(storage.WalletStorage, '_write') |
|
|
|
def test_sending_offline_wif_online_addr_p2pkh(self, mock_write): # compressed pubkey |
|
|
|
@mock.patch.object(wallet.Abstract_Wallet, 'save_db') |
|
|
|
def test_sending_offline_wif_online_addr_p2pkh(self, mock_save_db): # compressed pubkey |
|
|
|
wallet_offline = WalletIntegrityHelper.create_imported_wallet(privkeys=True, config=self.config) |
|
|
|
wallet_offline.import_private_key('p2pkh:cQDxbmQfwRV3vP1mdnVHq37nJekHLsuD3wdSQseBRA2ct4MFk5Pq', password=None) |
|
|
|
wallet_online = WalletIntegrityHelper.create_imported_wallet(privkeys=False, config=self.config) |
|
|
@ -1785,8 +1785,8 @@ class TestWalletOfflineSigning(TestCaseForTestnet): |
|
|
|
self.assertEqual('e56da664631b8c666c6df38ec80c954c4ac3c4f56f040faf0070e4681e937fc4', tx.wtxid()) |
|
|
|
|
|
|
|
@needs_test_with_all_ecc_implementations |
|
|
|
@mock.patch.object(storage.WalletStorage, '_write') |
|
|
|
def test_sending_offline_wif_online_addr_p2wpkh_p2sh(self, mock_write): |
|
|
|
@mock.patch.object(wallet.Abstract_Wallet, 'save_db') |
|
|
|
def test_sending_offline_wif_online_addr_p2wpkh_p2sh(self, mock_save_db): |
|
|
|
wallet_offline = WalletIntegrityHelper.create_imported_wallet(privkeys=True, config=self.config) |
|
|
|
wallet_offline.import_private_key('p2wpkh-p2sh:cU9hVzhpvfn91u2zTVn8uqF2ymS7ucYH8V5TmsTDmuyMHgRk9WsJ', password=None) |
|
|
|
wallet_online = WalletIntegrityHelper.create_imported_wallet(privkeys=False, config=self.config) |
|
|
@ -1824,8 +1824,8 @@ class TestWalletOfflineSigning(TestCaseForTestnet): |
|
|
|
self.assertEqual('9bb9949974954613945756c48ca5525cd5cba1b667ccb10c7a53e1ed076a1117', tx.wtxid()) |
|
|
|
|
|
|
|
@needs_test_with_all_ecc_implementations |
|
|
|
@mock.patch.object(storage.WalletStorage, '_write') |
|
|
|
def test_sending_offline_wif_online_addr_p2wpkh(self, mock_write): |
|
|
|
@mock.patch.object(wallet.Abstract_Wallet, 'save_db') |
|
|
|
def test_sending_offline_wif_online_addr_p2wpkh(self, mock_save_db): |
|
|
|
wallet_offline = WalletIntegrityHelper.create_imported_wallet(privkeys=True, config=self.config) |
|
|
|
wallet_offline.import_private_key('p2wpkh:cPuQzcNEgbeYZ5at9VdGkCwkPA9r34gvEVJjuoz384rTfYpahfe7', password=None) |
|
|
|
wallet_online = WalletIntegrityHelper.create_imported_wallet(privkeys=False, config=self.config) |
|
|
@ -1863,8 +1863,8 @@ class TestWalletOfflineSigning(TestCaseForTestnet): |
|
|
|
self.assertEqual('3b7cc3c3352bbb43ddc086487ac696e09f2863c3d9e8636721851b8008a83ffa', tx.wtxid()) |
|
|
|
|
|
|
|
@needs_test_with_all_ecc_implementations |
|
|
|
@mock.patch.object(storage.WalletStorage, '_write') |
|
|
|
def test_sending_offline_xprv_online_addr_p2pkh(self, mock_write): # compressed pubkey |
|
|
|
@mock.patch.object(wallet.Abstract_Wallet, 'save_db') |
|
|
|
def test_sending_offline_xprv_online_addr_p2pkh(self, mock_save_db): # compressed pubkey |
|
|
|
wallet_offline = WalletIntegrityHelper.create_standard_wallet( |
|
|
|
# bip39: "qwe", der: m/44'/1'/0' |
|
|
|
keystore.from_xprv('tprv8gfKwjuAaqtHgqxMh1tosAQ28XvBMkcY5NeFRA3pZMpz6MR4H4YZ3MJM4fvNPnRKeXR1Td2vQGgjorNXfo94WvT5CYDsPAqjHxSn436G1Eu'), |
|
|
@ -1906,8 +1906,8 @@ class TestWalletOfflineSigning(TestCaseForTestnet): |
|
|
|
self.assertEqual('e56da664631b8c666c6df38ec80c954c4ac3c4f56f040faf0070e4681e937fc4', tx.wtxid()) |
|
|
|
|
|
|
|
@needs_test_with_all_ecc_implementations |
|
|
|
@mock.patch.object(storage.WalletStorage, '_write') |
|
|
|
def test_sending_offline_xprv_online_addr_p2wpkh_p2sh(self, mock_write): |
|
|
|
@mock.patch.object(wallet.Abstract_Wallet, 'save_db') |
|
|
|
def test_sending_offline_xprv_online_addr_p2wpkh_p2sh(self, mock_save_db): |
|
|
|
wallet_offline = WalletIntegrityHelper.create_standard_wallet( |
|
|
|
# bip39: "qwe", der: m/49'/1'/0' |
|
|
|
keystore.from_xprv('uprv8zHHrMQMQ26utWwNJ5MK2SXpB9hbmy7pbPaneii69xT8cZTyFpxQFxkknGWKP8dxBTZhzy7yP6cCnLrRCQjzJDk3G61SjZpxhFQuB2NR8a5'), |
|
|
@ -1949,8 +1949,8 @@ class TestWalletOfflineSigning(TestCaseForTestnet): |
|
|
|
self.assertEqual('9bb9949974954613945756c48ca5525cd5cba1b667ccb10c7a53e1ed076a1117', tx.wtxid()) |
|
|
|
|
|
|
|
@needs_test_with_all_ecc_implementations |
|
|
|
@mock.patch.object(storage.WalletStorage, '_write') |
|
|
|
def test_sending_offline_xprv_online_addr_p2wpkh(self, mock_write): |
|
|
|
@mock.patch.object(wallet.Abstract_Wallet, 'save_db') |
|
|
|
def test_sending_offline_xprv_online_addr_p2wpkh(self, mock_save_db): |
|
|
|
wallet_offline = WalletIntegrityHelper.create_standard_wallet( |
|
|
|
# bip39: "qwe", der: m/84'/1'/0' |
|
|
|
keystore.from_xprv('vprv9K9hbuA23Bidgj1KRSHUZMa59jJLeZBpXPVn4RP7sBLArNhZxJjw4AX7aQmVTErDt4YFC11ptMLjbwxgrsH8GLQ1cx77KggWeVPeDBjr9xM'), |
|
|
@ -1992,8 +1992,8 @@ class TestWalletOfflineSigning(TestCaseForTestnet): |
|
|
|
self.assertEqual('3b7cc3c3352bbb43ddc086487ac696e09f2863c3d9e8636721851b8008a83ffa', tx.wtxid()) |
|
|
|
|
|
|
|
@needs_test_with_all_ecc_implementations |
|
|
|
@mock.patch.object(storage.WalletStorage, '_write') |
|
|
|
def test_sending_offline_hd_multisig_online_addr_p2sh(self, mock_write): |
|
|
|
@mock.patch.object(wallet.Abstract_Wallet, 'save_db') |
|
|
|
def test_sending_offline_hd_multisig_online_addr_p2sh(self, mock_save_db): |
|
|
|
# 2-of-3 legacy p2sh multisig |
|
|
|
wallet_offline1 = WalletIntegrityHelper.create_multisig_wallet( |
|
|
|
[ |
|
|
@ -2059,8 +2059,8 @@ class TestWalletOfflineSigning(TestCaseForTestnet): |
|
|
|
self.assertEqual('0e8fdc8257a85ebe7eeab14a53c2c258c61a511f64176b7f8fc016bc2263d307', tx.wtxid()) |
|
|
|
|
|
|
|
@needs_test_with_all_ecc_implementations |
|
|
|
@mock.patch.object(storage.WalletStorage, '_write') |
|
|
|
def test_sending_offline_hd_multisig_online_addr_p2wsh_p2sh(self, mock_write): |
|
|
|
@mock.patch.object(wallet.Abstract_Wallet, 'save_db') |
|
|
|
def test_sending_offline_hd_multisig_online_addr_p2wsh_p2sh(self, mock_save_db): |
|
|
|
# 2-of-2 p2sh-embedded segwit multisig |
|
|
|
wallet_offline1 = WalletIntegrityHelper.create_multisig_wallet( |
|
|
|
[ |
|
|
@ -2130,8 +2130,8 @@ class TestWalletOfflineSigning(TestCaseForTestnet): |
|
|
|
self.assertEqual('96d0bca1001778c54e4c3a07929fab5562c5b5a23fd1ca3aa3870cc5df2bf97d', tx.wtxid()) |
|
|
|
|
|
|
|
@needs_test_with_all_ecc_implementations |
|
|
|
@mock.patch.object(storage.WalletStorage, '_write') |
|
|
|
def test_sending_offline_hd_multisig_online_addr_p2wsh(self, mock_write): |
|
|
|
@mock.patch.object(wallet.Abstract_Wallet, 'save_db') |
|
|
|
def test_sending_offline_hd_multisig_online_addr_p2wsh(self, mock_save_db): |
|
|
|
# 2-of-3 p2wsh multisig |
|
|
|
wallet_offline1 = WalletIntegrityHelper.create_multisig_wallet( |
|
|
|
[ |
|
|
@ -2235,24 +2235,24 @@ class TestWalletHistory_SimpleRandomOrder(TestCaseForTestnet): |
|
|
|
w.create_new_address(for_change=True) |
|
|
|
return w |
|
|
|
|
|
|
|
@mock.patch.object(storage.WalletStorage, '_write') |
|
|
|
def test_restoring_old_wallet_txorder1(self, mock_write): |
|
|
|
@mock.patch.object(wallet.Abstract_Wallet, 'save_db') |
|
|
|
def test_restoring_old_wallet_txorder1(self, mock_save_db): |
|
|
|
w = self.create_old_wallet() |
|
|
|
for i in [2, 12, 7, 9, 11, 10, 16, 6, 17, 1, 13, 15, 5, 8, 4, 0, 14, 18, 3]: |
|
|
|
tx = Transaction(self.transactions[self.txid_list[i]]) |
|
|
|
w.receive_tx_callback(tx.txid(), tx, TX_HEIGHT_UNCONFIRMED) |
|
|
|
self.assertEqual(27633300, sum(w.get_balance())) |
|
|
|
|
|
|
|
@mock.patch.object(storage.WalletStorage, '_write') |
|
|
|
def test_restoring_old_wallet_txorder2(self, mock_write): |
|
|
|
@mock.patch.object(wallet.Abstract_Wallet, 'save_db') |
|
|
|
def test_restoring_old_wallet_txorder2(self, mock_save_db): |
|
|
|
w = self.create_old_wallet() |
|
|
|
for i in [9, 18, 2, 0, 13, 3, 1, 11, 4, 17, 7, 14, 12, 15, 10, 8, 5, 6, 16]: |
|
|
|
tx = Transaction(self.transactions[self.txid_list[i]]) |
|
|
|
w.receive_tx_callback(tx.txid(), tx, TX_HEIGHT_UNCONFIRMED) |
|
|
|
self.assertEqual(27633300, sum(w.get_balance())) |
|
|
|
|
|
|
|
@mock.patch.object(storage.WalletStorage, '_write') |
|
|
|
def test_restoring_old_wallet_txorder3(self, mock_write): |
|
|
|
@mock.patch.object(wallet.Abstract_Wallet, 'save_db') |
|
|
|
def test_restoring_old_wallet_txorder3(self, mock_save_db): |
|
|
|
w = self.create_old_wallet() |
|
|
|
for i in [5, 8, 17, 0, 9, 10, 12, 3, 15, 18, 2, 11, 14, 7, 16, 1, 4, 6, 13]: |
|
|
|
tx = Transaction(self.transactions[self.txid_list[i]]) |
|
|
@ -2283,10 +2283,10 @@ class TestWalletHistory_EvilGapLimit(TestCaseForTestnet): |
|
|
|
w = WalletIntegrityHelper.create_standard_wallet(ks, gap_limit=20, config=self.config) |
|
|
|
return w |
|
|
|
|
|
|
|
@mock.patch.object(storage.WalletStorage, '_write') |
|
|
|
def test_restoring_wallet_txorder1(self, mock_write): |
|
|
|
@mock.patch.object(wallet.Abstract_Wallet, 'save_db') |
|
|
|
def test_restoring_wallet_txorder1(self, mock_save_db): |
|
|
|
w = self.create_wallet() |
|
|
|
w.storage.put('stored_height', 1316917 + 100) |
|
|
|
w.db.put('stored_height', 1316917 + 100) |
|
|
|
for txid in self.transactions: |
|
|
|
tx = Transaction(self.transactions[txid]) |
|
|
|
w.add_transaction(tx) |
|
|
@ -2331,8 +2331,8 @@ class TestWalletHistory_DoubleSpend(TestCaseForTestnet): |
|
|
|
super().setUp() |
|
|
|
self.config = SimpleConfig({'electrum_path': self.electrum_path}) |
|
|
|
|
|
|
|
@mock.patch.object(storage.WalletStorage, '_write') |
|
|
|
def test_restoring_wallet_without_manual_delete(self, mock_write): |
|
|
|
@mock.patch.object(wallet.Abstract_Wallet, 'save_db') |
|
|
|
def test_restoring_wallet_without_manual_delete(self, mock_save_db): |
|
|
|
w = restore_wallet_from_text("small rapid pattern language comic denial donate extend tide fever burden barrel", |
|
|
|
path='if_this_exists_mocking_failed_648151893', |
|
|
|
gap_limit=5, |
|
|
@ -2345,8 +2345,8 @@ class TestWalletHistory_DoubleSpend(TestCaseForTestnet): |
|
|
|
# txn C is double-spending txn B, to a wallet address |
|
|
|
self.assertEqual(999890, sum(w.get_balance())) |
|
|
|
|
|
|
|
@mock.patch.object(storage.WalletStorage, '_write') |
|
|
|
def test_restoring_wallet_with_manual_delete(self, mock_write): |
|
|
|
@mock.patch.object(wallet.Abstract_Wallet, 'save_db') |
|
|
|
def test_restoring_wallet_with_manual_delete(self, mock_save_db): |
|
|
|
w = restore_wallet_from_text("small rapid pattern language comic denial donate extend tide fever burden barrel", |
|
|
|
path='if_this_exists_mocking_failed_648151893', |
|
|
|
gap_limit=5, |
|
|
|