Browse Source

fix test/unified/test_segwit.py

add_frost_channel_encryption
zebra-lucky 4 months ago
parent
commit
d5213ec45a
  1. 7
      test/unified/common.py
  2. 271
      test/unified/test_segwit.py

7
test/unified/common.py

@ -50,7 +50,7 @@ async def make_sign_and_push(ins_full,
output_addr = await wallet_service.get_new_addr( output_addr = await wallet_service.get_new_addr(
1, 1,
BaseWallet.ADDRESS_TYPE_INTERNAL) if not output_addr else output_addr BaseWallet.ADDRESS_TYPE_INTERNAL) if not output_addr else output_addr
change_addr = wallet_service.get_new_addr( change_addr = await wallet_service.get_new_addr(
0, 0,
BaseWallet.ADDRESS_TYPE_INTERNAL) if not change_addr else change_addr BaseWallet.ADDRESS_TYPE_INTERNAL) if not change_addr else change_addr
fee_est = estimate_tx_fee(len(ins), 2) if estimate_fee else 10000 fee_est = estimate_tx_fee(len(ins), 2) if estimate_fee else 10000
@ -135,8 +135,9 @@ async def make_wallets(n,
amt = mean_amt - sdev_amt / 2.0 + deviation amt = mean_amt - sdev_amt / 2.0 + deviation
if amt < 0: amt = 0.001 if amt < 0: amt = 0.001
amt = float(Decimal(amt).quantize(Decimal(10)**-8)) amt = float(Decimal(amt).quantize(Decimal(10)**-8))
jm_single().bc_interface.grab_coins(wallet_service.get_new_addr( dest_addr = await wallet_service.get_new_addr(
j, BaseWallet.ADDRESS_TYPE_INTERNAL), amt) j, BaseWallet.ADDRESS_TYPE_INTERNAL)
jm_single().bc_interface.grab_coins(dest_addr , amt)
return wallets return wallets

271
test/unified/test_segwit.py

@ -6,140 +6,153 @@ from common import make_wallets
from pprint import pformat from pprint import pformat
import jmbitcoin as btc import jmbitcoin as btc
import pytest import pytest
from unittest_parametrize import parametrize, ParametrizedTestCase
from jmbase import get_log, hextobin from jmbase import get_log, hextobin
from jmclient import load_test_config, jm_single, LegacyWallet, BaseWallet from jmclient import load_test_config, jm_single, LegacyWallet, BaseWallet
from common import TrialAsyncioTestCase
pytestmark = pytest.mark.usefixtures("setup_regtest_bitcoind")
log = get_log() log = get_log()
def test_segwit_valid_txs(setup_segwit): class SegWitTests(TrialAsyncioTestCase, ParametrizedTestCase):
with open("test/tx_segwit_valid.json", "r") as f:
json_data = f.read() async def asyncSetUp(self):
valid_txs = json.loads(json_data) load_test_config()
for j in valid_txs: jm_single().bc_interface.tick_forward_chain_interval = 1
if len(j) < 2:
continue async def test_segwit_valid_txs(self):
deserialized_tx = btc.CMutableTransaction.deserialize(hextobin(j[1])) with open("test/tx_segwit_valid.json", "r") as f:
print(pformat(deserialized_tx)) json_data = f.read()
assert deserialized_tx.serialize() == hextobin(j[1]) valid_txs = json.loads(json_data)
#TODO use bcinterface to decoderawtransaction for j in valid_txs:
#and compare the json values if len(j) < 2:
continue
@pytest.mark.parametrize( deserialized_tx = btc.CMutableTransaction.deserialize(hextobin(j[1]))
"wallet_structure, in_amt, amount, segwit_amt, segwit_ins, o_ins", [ print(pformat(deserialized_tx))
([[1, 0, 0, 0, 0]], 1, 1000000, 1, [0, 1, 2], []), assert deserialized_tx.serialize() == hextobin(j[1])
([[4, 0, 0, 0, 1]], 3, 100000000, 1, [0, 2], [1, 3]), #TODO use bcinterface to decoderawtransaction
([[4, 0, 0, 0, 1]], 3, 100000000, 1, [0, 5], [1, 2, 3, 4]), #and compare the json values
([[4, 0, 0, 0, 0]], 2, 200000007, 0.3, [0, 1, 4, 5], [2, 3, 6]),
]) @parametrize(
def test_spend_p2sh_p2wpkh_multi(setup_segwit, wallet_structure, in_amt, amount, "wallet_structure, in_amt, amount, segwit_amt, segwit_ins, o_ins", [
segwit_amt, segwit_ins, o_ins): ([[1, 0, 0, 0, 0]], 1, 1000000, 1, [0, 1, 2], []),
"""Creates a wallet from which non-segwit inputs/ ([[4, 0, 0, 0, 1]], 3, 100000000, 1, [0, 2], [1, 3]),
outputs can be created, constructs one or more ([[4, 0, 0, 0, 1]], 3, 100000000, 1, [0, 5], [1, 2, 3, 4]),
p2wpkh in p2sh spendable utxos (by paying into the ([[4, 0, 0, 0, 0]], 2, 200000007, 0.3, [0, 1, 4, 5], [2, 3, 6]),
corresponding address) and tests spending them ])
in combination. async def test_spend_p2sh_p2wpkh_multi(self, wallet_structure, in_amt, amount,
wallet_structure is in accordance with commontest.make_wallets, see docs there segwit_amt, segwit_ins, o_ins):
in_amt is the amount to pay into each address into the wallet (non-segwit adds) """Creates a wallet from which non-segwit inputs/
amount (in satoshis) is how much we will pay to the output address outputs can be created, constructs one or more
segwit_amt in BTC is the amount we will fund each new segwit address with p2wpkh in p2sh spendable utxos (by paying into the
segwit_ins is a list of input indices (where to place the funding segwit utxos) corresponding address) and tests spending them
other_ins is a list of input indices (where to place the funding non-sw utxos) in combination.
""" wallet_structure is in accordance with commontest.make_wallets, see docs there
MIXDEPTH = 0 in_amt is the amount to pay into each address into the wallet (non-segwit adds)
amount (in satoshis) is how much we will pay to the output address
# set up wallets and inputs segwit_amt in BTC is the amount we will fund each new segwit address with
nsw_wallet_service = make_wallets(1, wallet_structure, in_amt, segwit_ins is a list of input indices (where to place the funding segwit utxos)
walletclass=LegacyWallet)[0]['wallet'] other_ins is a list of input indices (where to place the funding non-sw utxos)
nsw_wallet_service.sync_wallet(fast=True) """
sw_wallet_service = make_wallets(1, [[len(segwit_ins), 0, 0, 0, 0]], segwit_amt)[0]['wallet'] MIXDEPTH = 0
sw_wallet_service.sync_wallet(fast=True)
# set up wallets and inputs
nsw_utxos = nsw_wallet_service.get_utxos_by_mixdepth()[MIXDEPTH] wallet_services = await make_wallets(
sw_utxos = sw_wallet_service.get_utxos_by_mixdepth()[MIXDEPTH] 1, wallet_structure, in_amt, walletclass=LegacyWallet)
assert len(o_ins) <= len(nsw_utxos), "sync failed" nsw_wallet_service = wallet_services[0]['wallet']
assert len(segwit_ins) <= len(sw_utxos), "sync failed" await nsw_wallet_service.sync_wallet(fast=True)
sw_wallet_services = await make_wallets(
total_amt_in_sat = 0 1, [[len(segwit_ins), 0, 0, 0, 0]], segwit_amt)
sw_wallet_service = sw_wallet_services[0]['wallet']
nsw_ins = {} await sw_wallet_service.sync_wallet(fast=True)
for nsw_in_index in o_ins:
total_amt_in_sat += in_amt * 10**8 nsw_utxos_by_md = await nsw_wallet_service.get_utxos_by_mixdepth()
nsw_ins[nsw_in_index] = nsw_utxos.popitem() nsw_utxos = nsw_utxos_by_md[MIXDEPTH]
sw_utxos_by_md = await sw_wallet_service.get_utxos_by_mixdepth()
sw_ins = {} sw_utxos = sw_utxos_by_md[MIXDEPTH]
for sw_in_index in segwit_ins: assert len(o_ins) <= len(nsw_utxos), "sync failed"
total_amt_in_sat += int(segwit_amt * 10**8) assert len(segwit_ins) <= len(sw_utxos), "sync failed"
sw_ins[sw_in_index] = sw_utxos.popitem()
total_amt_in_sat = 0
all_ins = {}
all_ins.update(nsw_ins) nsw_ins = {}
all_ins.update(sw_ins) for nsw_in_index in o_ins:
total_amt_in_sat += in_amt * 10**8
# sanity checks nsw_ins[nsw_in_index] = nsw_utxos.popitem()
assert len(all_ins) == len(nsw_ins) + len(sw_ins), \
"test broken, duplicate index" sw_ins = {}
for k in all_ins: for sw_in_index in segwit_ins:
assert 0 <= k < len(all_ins), "test broken, missing input index" total_amt_in_sat += int(segwit_amt * 10**8)
sw_ins[sw_in_index] = sw_utxos.popitem()
# FIXME: encoding mess, mktx should accept binary input formats
tx_ins = [] all_ins = {}
for i, (txin, data) in sorted(all_ins.items(), key=lambda x: x[0]): all_ins.update(nsw_ins)
tx_ins.append(txin) all_ins.update(sw_ins)
# create outputs # sanity checks
FEE = 50000 assert len(all_ins) == len(nsw_ins) + len(sw_ins), \
assert FEE < total_amt_in_sat - amount, "test broken, not enough funds" "test broken, duplicate index"
for k in all_ins:
cj_script = nsw_wallet_service.get_new_script(MIXDEPTH + 1, assert 0 <= k < len(all_ins), "test broken, missing input index"
BaseWallet.ADDRESS_TYPE_INTERNAL)
change_script = nsw_wallet_service.get_new_script(MIXDEPTH, # FIXME: encoding mess, mktx should accept binary input formats
BaseWallet.ADDRESS_TYPE_INTERNAL) tx_ins = []
change_amt = total_amt_in_sat - amount - FEE for i, (txin, data) in sorted(all_ins.items(), key=lambda x: x[0]):
tx_ins.append(txin)
tx_outs = [
{'address': nsw_wallet_service.script_to_addr(cj_script), # create outputs
'value': amount}, FEE = 50000
{'address': nsw_wallet_service.script_to_addr(change_script), assert FEE < total_amt_in_sat - amount, "test broken, not enough funds"
'value': change_amt}]
tx = btc.mktx(tx_ins, tx_outs) cj_script = await nsw_wallet_service.get_new_script(
MIXDEPTH + 1, BaseWallet.ADDRESS_TYPE_INTERNAL)
# import new addresses to bitcoind change_script = await nsw_wallet_service.get_new_script(
jm_single().bc_interface.import_addresses( MIXDEPTH, BaseWallet.ADDRESS_TYPE_INTERNAL)
[nsw_wallet_service.script_to_addr(x) change_amt = total_amt_in_sat - amount - FEE
for x in [cj_script, change_script]], nsw_wallet_service.get_wallet_name())
tx_outs = [
# sign tx {'address': await nsw_wallet_service.script_to_addr(cj_script),
scripts = {} 'value': amount},
for nsw_in_index in o_ins: {'address': await nsw_wallet_service.script_to_addr(change_script),
inp = nsw_ins[nsw_in_index][1] 'value': change_amt}]
scripts[nsw_in_index] = (inp['script'], inp['value']) tx = btc.mktx(tx_ins, tx_outs)
success, msg = nsw_wallet_service.sign_tx(tx, scripts)
assert success, msg # import new addresses to bitcoind
jm_single().bc_interface.import_addresses(
scripts = {} [(await nsw_wallet_service.script_to_addr(x))
for sw_in_index in segwit_ins: for x in [cj_script, change_script]],
inp = sw_ins[sw_in_index][1] nsw_wallet_service.get_wallet_name())
scripts[sw_in_index] = (inp['script'], inp['value'])
success, msg = sw_wallet_service.sign_tx(tx, scripts) # sign tx
assert success, msg scripts = {}
for nsw_in_index in o_ins:
print(tx) inp = nsw_ins[nsw_in_index][1]
scripts[nsw_in_index] = (inp['script'], inp['value'])
# push and verify success, msg = await nsw_wallet_service.sign_tx(tx, scripts)
txid = jm_single().bc_interface.pushtx(tx.serialize()) assert success, msg
assert txid
scripts = {}
balances = jm_single().bc_interface.get_received_by_addr( for sw_in_index in segwit_ins:
[nsw_wallet_service.script_to_addr(cj_script), inp = sw_ins[sw_in_index][1]
nsw_wallet_service.script_to_addr(change_script)])['data'] scripts[sw_in_index] = (inp['script'], inp['value'])
assert balances[0]['balance'] == amount success, msg = await sw_wallet_service.sign_tx(tx, scripts)
assert balances[1]['balance'] == change_amt assert success, msg
print(tx)
@pytest.fixture(scope="module")
def setup_segwit(): # push and verify
load_test_config() txid = jm_single().bc_interface.pushtx(tx.serialize())
jm_single().bc_interface.tick_forward_chain_interval = 1 assert txid
balances = jm_single().bc_interface.get_received_by_addr(
[(await nsw_wallet_service.script_to_addr(cj_script)),
(await nsw_wallet_service.script_to_addr(change_script))])['data']
assert balances[0]['balance'] == amount
assert balances[1]['balance'] == change_amt
''' '''

Loading…
Cancel
Save