def test_blink_fail_mempool(net, mike, alice, bob): """This test does a regular transfer then attempts to blink the same funds via a local node with a flushed txpool; the blink should get rejected by the quorum.""" assert alice.balances() == (0, 0) assert bob.balances() == (0, 0) mike.transfer(alice, coins(40)) net.mine(sync=True) assert alice.balances() == coins(40, 40) alice.transfer(bob, coins(25)) time.sleep(0.5) # Allow propagation to network assert alice.node.json_rpc("flush_txpool").json()['result']['status'] == 'OK' assert 'result' in alice.json_rpc("rescan_spent").json() # A non-blink should go through, since it only validates on the local node, and we just clear # its mempool: alice.transfer(bob, coins(7)) # Clear it again, then try a blink: assert alice.node.json_rpc("flush_txpool").json()['result']['status'] == 'OK' assert 'result' in alice.json_rpc("rescan_spent").json() from daemons import TransferFailed with pytest.raises(TransferFailed, match='rejected by quorum') as exc_info: double_spend = alice.transfer(bob, coins(5), blink=True) # Has to spend the same input, since we only have one input
def test_blink_sweep(net, mike, alice, bob): """Similar to the above, but tests blinking a sweep_all""" assert alice.balances() == (0, 0) assert bob.balances() == (0, 0) # Prepare two sweeps: one small one of just a few inputs that goes from bob -> alice, and one # huge one that requires multiple txes that alice blinks to bob. # # We want to pile in enough transfers that alice has to submit multiple txes to sweep to bob: # Normal tx limit is 100kB, and we hit that limit at around 130 inputs, so we'll send 150 to # alice. transfers = [[{"address": alice.address(), "amount": coins(1)}] * 15] * 10 transfers.append([{"address": bob.address(), "amount": coins(3)}] * 3) for t in transfers: r = mike.json_rpc("transfer_split", { "destinations": t, "priority": 0 }).json() if 'error' in r: raise TransferFailed( "Transfer failed: {}".format(r['error']['message']), r) # Confirm the transfers net.mine(sync=True) assert alice.balances() == coins(150, 150) assert bob.balances() == coins(9, 9) sweep_a = bob.transfer(alice, sweep=True, priority=5) assert len(sweep_a['amount_list']) == 1 amount_a = sweep_a['amount_list'][0] assert amount_a == coins(9) - sweep_a['fee_list'][0] assert bob.balances() == (0, 0) time.sleep(0.5) alice.refresh() assert alice.balances() == (coins(150) + amount_a, coins(150)) sweep_b = alice.transfer(bob, sweep=True, priority=5) assert len(sweep_b['amount_list']) > 1 amount_b = sum(sweep_b['amount_list']) assert amount_b == coins(150) - sum(sweep_b['fee_list']) assert alice.balances() == (amount_a, 0) time.sleep(0.5) bob.refresh() assert bob.balances() == (amount_b, 0) net.mine(sync=True) assert alice.balances() == (amount_a, amount_a) assert bob.balances() == (amount_b, amount_b)
def test_basic_blink(net, alice, bob, mike): """Tests sending a basic blink (alongside a non-blink tx) and verifies the it is accepted and received as expected.""" a1 = alice.balances() mike.transfer(alice, coins(100)) net.mine(5, sync=True) a2 = alice.balances() assert diff(a1, a2) == coins(100, 0) net.mine(5, sync=True) a2 = alice.balances() assert diff(a1, a2) == coins(100, 100) b1 = bob.balances() sent_blink = alice.transfer(bob, coins(10), blink=True) assert sent_blink['amount_list'] == [coins(10)] assert len(sent_blink['tx_hash_list']) == 1 sent_normal = mike.transfer(bob, coins(3), blink=False) assert sent_normal['amount_list'] == [coins(3)] assert len(sent_normal['tx_hash_list']) == 1 time.sleep(0.5) # Should be more than enough time to propagate between 24 localhost nodes bob.refresh() recv_blink, recv_normal = bob.find_transfers(x['tx_hash_list'][0] for x in (sent_blink, sent_normal)) assert recv_blink is not None assert recv_normal is not None exp_blink = {'type': 'in', 'address': bob.address(), 'amount': coins(10), 'blink_mempool': True, 'was_blink': True} exp_normal = {'type': 'pool', 'address': bob.address(), 'amount': coins(3), 'blink_mempool': False, 'was_blink': False} assert exp_blink.items() <= recv_blink.items() assert exp_normal.items() <= recv_normal.items() assert diff(b1, bob.balances()) == coins(10, 0) # Blink balance shows up now, mempool after being mined. net.mine(1, sync=True) assert diff(b1, bob.balances()) == coins(13, 0) recv_blink, recv_normal = bob.find_transfers(x['tx_hash_list'][0] for x in (sent_blink, sent_normal)) exp_blink['blink_mempool'] = False assert exp_blink.items() <= recv_blink.items() exp_normal['type'] = 'in' assert exp_normal.items() <= recv_normal.items() net.mine(8, sync=True) assert diff(b1, bob.balances()) == coins(13, 0) recv_blink, recv_normal = bob.find_transfers(x['tx_hash_list'][0] for x in (sent_blink, sent_normal)) assert exp_blink.items() <= recv_blink.items() assert exp_normal.items() <= recv_normal.items() net.mine(1, sync=True) assert diff(b1, bob.balances()) == coins(13, 13) recv_blink, recv_normal = bob.find_transfers(x['tx_hash_list'][0] for x in (sent_blink, sent_normal)) assert exp_blink.items() <= recv_blink.items() assert exp_normal.items() <= recv_normal.items()