def test_handle_inittarget(): """ Init transfer must send a secret request if the expiration is valid. """ block_number = 1 pseudo_random_generator = random.Random() channels = make_channel_set([channel_properties]) transfer_properties = LockedTransferSignedStateProperties( amount=channels[0].partner_state.contract_balance, expiration=channels[0].reveal_timeout + block_number + 1, canonical_identifier=channels[0].canonical_identifier, transferred_amount=0, locked_amount=channels[0].partner_state.contract_balance, ) from_transfer = create(transfer_properties) state_change = ActionInitTarget(channels.get_route(0), from_transfer) iteration = target.handle_inittarget(state_change, channels[0], pseudo_random_generator, block_number) assert search_for_item( iteration.events, SendSecretRequest, { "payment_identifier": from_transfer.payment_identifier, "amount": from_transfer.lock.amount, "secrethash": from_transfer.lock.secrethash, "recipient": UNIT_TRANSFER_INITIATOR, }, ) assert search_for_item(iteration.events, SendProcessed, {})
def test_initiator_events(): assert not has_unlock_failure(app0) initiator_events = app0.wal.storage.get_events() secret_reveal = search_for_item(initiator_events, SendSecretReveal, {}) unlock_success = search_for_item(initiator_events, EventUnlockSuccess, {}) return secret_reveal and unlock_success
def test_regression_filters_must_be_installed_from_confirmed_block(raiden_network): """On restarts Raiden must install the filters from the last run's confirmed block instead of the latest known block. Regression test for: https://github.com/raiden-network/raiden/issues/2894. """ app0 = raiden_network[0] app0.raiden.alarm.stop() target_block_num = ( app0.raiden.rpc_client.block_number() + DEFAULT_NUMBER_OF_BLOCK_CONFIRMATIONS + 1 ) app0.raiden.proxy_manager.wait_until_block(target_block_num) latest_block = app0.raiden.rpc_client.get_block(block_identifier="latest") app0.raiden._callback_new_block(latest_block=latest_block) target_block_num = latest_block["number"] app0_state_changes = app0.raiden.wal.storage.get_statechanges_by_range(RANGE_ALL_STATE_CHANGES) assert search_for_item( app0_state_changes, Block, {"block_number": target_block_num - DEFAULT_NUMBER_OF_BLOCK_CONFIRMATIONS}, ) assert not search_for_item(app0_state_changes, Block, {"block_number": target_block_num})
def run_test_regression_filters_must_be_installed_from_confirmed_block(raiden_network): app0 = raiden_network[0] app0.raiden.alarm.stop() target_block_num = app0.raiden.chain.block_number() + DEFAULT_NUMBER_OF_BLOCK_CONFIRMATIONS + 1 app0.raiden.chain.wait_until_block(target_block_num) latest_block = app0.raiden.chain.get_block(block_identifier='latest') app0.raiden._callback_new_block(latest_block=latest_block) target_block_num = latest_block['number'] app0_state_changes = app0.raiden.wal.storage.get_statechanges_by_identifier( from_identifier=0, to_identifier='latest', ) assert search_for_item( app0_state_changes, Block, { 'block_number': target_block_num - DEFAULT_NUMBER_OF_BLOCK_CONFIRMATIONS, }, ) assert not search_for_item( app0_state_changes, Block, { 'block_number': target_block_num, }, )
def test_raiden_service_callback_new_block(raiden_network): """ Regression test for: https://github.com/raiden-network/raiden/issues/2894 """ app0 = raiden_network[0] app0.raiden.alarm.stop() target_block_num = app0.raiden.chain.block_number( ) + DEFAULT_NUMBER_OF_BLOCK_CONFIRMATIONS + 1 app0.raiden.chain.wait_until_block(target_block_num) latest_block = app0.raiden.chain.get_block(block_identifier='latest') app0.raiden._callback_new_block(latest_block=latest_block) target_block_num = latest_block['number'] app0_state_changes = app0.raiden.wal.storage.get_statechanges_by_identifier( from_identifier=0, to_identifier='latest', ) assert search_for_item(app0_state_changes, Block, { 'block_number': target_block_num - DEFAULT_NUMBER_OF_BLOCK_CONFIRMATIONS, }) assert not search_for_item(app0_state_changes, Block, { 'block_number': target_block_num, })
def test_regression_filters_must_be_installed_from_confirmed_block(raiden_network): """On restarts Raiden must install the filters from the last run's confirmed block instead of the latest known block. Regression test for: https://github.com/raiden-network/raiden/issues/2894. """ app0 = raiden_network[0] app0.raiden.alarm.stop() target_block_num = app0.raiden.chain.block_number() + DEFAULT_NUMBER_OF_BLOCK_CONFIRMATIONS + 1 app0.raiden.chain.wait_until_block(target_block_num) latest_block = app0.raiden.chain.get_block(block_identifier='latest') app0.raiden._callback_new_block(latest_block=latest_block) target_block_num = latest_block['number'] app0_state_changes = app0.raiden.wal.storage.get_statechanges_by_identifier( from_identifier=0, to_identifier='latest', ) assert search_for_item(app0_state_changes, Block, { 'block_number': target_block_num - DEFAULT_NUMBER_OF_BLOCK_CONFIRMATIONS, }) assert not search_for_item(app0_state_changes, Block, { 'block_number': target_block_num, })
def test_target_events(): target_events = app2.raiden.wal.storage.get_events() return ( search_for_item(target_events, SendSecretRequest, {}) and search_for_item(target_events, SendSecretReveal, {}) and search_for_item(target_events, EventUnlockClaimSuccess, {}) )
def test_target_receive_lock_expired(): lock_amount = 7 block_number = 1 pseudo_random_generator = random.Random() channels = make_channel_set([channel_properties2]) expiration = block_number + channels[0].settle_timeout - channels[ 0].reveal_timeout from_transfer = make_target_transfer(channels[0], amount=lock_amount, block_number=block_number) init = ActionInitTarget(channels.get_route(0), from_transfer) init_transition = target.state_transition( target_state=None, state_change=init, channel_state=channels[0], pseudo_random_generator=pseudo_random_generator, block_number=block_number, ) assert init_transition.new_state is not None assert init_transition.new_state.route == channels.get_route(0) assert init_transition.new_state.transfer == from_transfer balance_proof = create( BalanceProofSignedStateProperties( nonce=2, transferred_amount=from_transfer.balance_proof.transferred_amount, locked_amount=0, canonical_identifier=channels[0].canonical_identifier, message_hash=from_transfer.lock.secrethash, )) lock_expired_state_change = ReceiveLockExpired( balance_proof=balance_proof, secrethash=from_transfer.lock.secrethash, message_identifier=1) block_before_confirmed_expiration = expiration + DEFAULT_NUMBER_OF_BLOCK_CONFIRMATIONS - 1 iteration = target.state_transition( target_state=init_transition.new_state, state_change=lock_expired_state_change, channel_state=channels[0], pseudo_random_generator=pseudo_random_generator, block_number=block_before_confirmed_expiration, ) assert not search_for_item(iteration.events, SendProcessed, {}) block_lock_expired = block_before_confirmed_expiration + 1 iteration = target.state_transition( target_state=init_transition.new_state, state_change=lock_expired_state_change, channel_state=channels[0], pseudo_random_generator=pseudo_random_generator, block_number=block_lock_expired, ) assert search_for_item(iteration.events, SendProcessed, {})
def run_test_locked_transfer_secret_registered_onchain(raiden_network, token_addresses, secret_registry_address, retry_timeout): app0 = raiden_network[0] token_address = token_addresses[0] chain_state = views.state_from_app(app0) payment_network_id = app0.raiden.default_registry.address token_network_identifier = views.get_token_network_identifier_by_token_address( chain_state, payment_network_id, token_address) amount = 1 target = factories.UNIT_TRANSFER_INITIATOR identifier = 1 transfer_secret = sha3(target + b"1") secret_registry_proxy = app0.raiden.chain.secret_registry( secret_registry_address) secret_registry_proxy.register_secret(secret=transfer_secret) # Wait until our node has processed the block that the secret registration was mined at block_number = app0.raiden.get_block_number() wait_for_block( raiden=app0.raiden, block_number=block_number + DEFAULT_NUMBER_OF_BLOCK_CONFIRMATIONS, retry_timeout=retry_timeout, ) # Test that sending a transfer with a secret already registered on-chain fails with pytest.raises(RaidenUnrecoverableError): app0.raiden.start_mediated_transfer_with_secret( token_network_identifier=token_network_identifier, amount=amount, fee=0, target=target, identifier=identifier, payment_hash_invoice=EMPTY_PAYMENT_HASH_INVOICE, secret=transfer_secret, ) # Test that receiving a transfer with a secret already registered on chain fails expiration = 9999 locked_transfer = factories.create( factories.LockedTransferProperties( amount=amount, target=app0.raiden.address, expiration=expiration, secret=transfer_secret, )) message_handler = MessageHandler() message_handler.handle_message_lockedtransfer(app0.raiden, locked_transfer) state_changes = app0.raiden.wal.storage.get_statechanges_by_identifier( 0, "latest") transfer_statechange_dispatched = search_for_item( state_changes, ActionInitMediator, {}) or search_for_item( state_changes, ActionInitTarget, {}) assert not transfer_statechange_dispatched
def test_mediator_events(): assert not has_unlock_failure(app1) mediator_events = app1.wal.storage.get_events() unlock_success = search_for_item(mediator_events, EventUnlockSuccess, {}) unlock_claim_success = search_for_item(mediator_events, EventUnlockClaimSuccess, {}) return unlock_success and unlock_claim_success
def test_locked_transfer_secret_registered_onchain( raiden_network, token_addresses, secret_registry_address, retry_timeout ): app0 = raiden_network[0] token_address = token_addresses[0] chain_state = views.state_from_app(app0) token_network_registry_address = app0.raiden.default_registry.address token_network_address = views.get_token_network_address_by_token_address( chain_state, token_network_registry_address, token_address ) amount = TokenAmount(1) target = factories.UNIT_TRANSFER_INITIATOR identifier = PaymentID(1) transfer_secret = make_secret() secret_registry_proxy = app0.raiden.proxy_manager.secret_registry( secret_registry_address, block_identifier=chain_state.block_hash ) secret_registry_proxy.register_secret(secret=transfer_secret) # Wait until our node has processed the block that the secret registration was mined at block_number = app0.raiden.get_block_number() wait_for_block( raiden=app0.raiden, block_number=block_number + DEFAULT_NUMBER_OF_BLOCK_CONFIRMATIONS, retry_timeout=retry_timeout, ) # Test that sending a transfer with a secret already registered on-chain fails with pytest.raises(RaidenUnrecoverableError): app0.raiden.start_mediated_transfer_with_secret( token_network_address=token_network_address, amount=amount, target=target, identifier=identifier, secret=transfer_secret, ) # Test that receiving a transfer with a secret already registered on chain fails expiration = BlockExpiration(9999) locked_transfer = factories.create( factories.LockedTransferProperties( amount=amount, target=app0.raiden.address, expiration=expiration, secret=transfer_secret, ) ) message_handler = MessageHandler() message_handler.handle_message_lockedtransfer(app0.raiden, locked_transfer) state_changes = app0.raiden.wal.storage.get_statechanges_by_range(RANGE_ALL_STATE_CHANGES) transfer_statechange_dispatched = search_for_item( state_changes, ActionInitMediator, {} ) or search_for_item(state_changes, ActionInitTarget, {}) assert not transfer_statechange_dispatched
def test_regression_mediator_send_lock_expired_with_new_block(): """The mediator must send the lock expired, but it must **not** clear itself if it has not **received** the corresponding message. """ pseudo_random_generator = random.Random() channels = factories.mediator_make_channel_pair() payer_transfer = factories.make_signed_transfer_for( channels[0], LONG_EXPIRATION) init_iteration = mediator.state_transition( mediator_state=None, state_change=factories.mediator_make_init_action( channels, payer_transfer), channelidentifiers_to_channels=channels.channel_map, addresses_to_channel=channels.addresses_to_channel(), nodeaddresses_to_networkstates=channels.nodeaddresses_to_networkstates, pseudo_random_generator=pseudo_random_generator, block_number=5, block_hash=factories.make_block_hash(), ) assert init_iteration.new_state is not None send_transfer = search_for_item(init_iteration.events, SendLockedTransfer, {}) assert send_transfer transfer = send_transfer.transfer block_expiration_number = channel.get_sender_expiration_threshold( transfer.lock.expiration) block = Block( block_number=block_expiration_number, gas_limit=1, block_hash=factories.make_transaction_hash(), ) iteration = mediator.state_transition( mediator_state=init_iteration.new_state, state_change=block, channelidentifiers_to_channels=channels.channel_map, addresses_to_channel=channels.addresses_to_channel(), nodeaddresses_to_networkstates=channels.nodeaddresses_to_networkstates, pseudo_random_generator=pseudo_random_generator, block_number=block_expiration_number, block_hash=factories.make_block_hash(), ) msg = ("The payer's lock has also expired, " "but it must not be removed locally (without an Expired lock)") assert transfer.lock.secrethash in channels[ 0].partner_state.secrethashes_to_lockedlocks, msg msg = "The payer has not yet sent an expired lock, the task can not be cleared yet" assert iteration.new_state is not None, msg assert search_for_item(iteration.events, SendLockExpired, {"secrethash": transfer.lock.secrethash}) assert transfer.lock.secrethash not in channels[ 1].our_state.secrethashes_to_lockedlocks
def test_locked_transfer_secret_registered_onchain( raiden_network, token_addresses, secret_registry_address, ): app0 = raiden_network[0] token_address = token_addresses[0] chain_state = views.state_from_app(app0) payment_network_id = app0.raiden.default_registry.address token_network_identifier = views.get_token_network_identifier_by_token_address( chain_state, payment_network_id, token_address, ) amount = 1 target = UNIT_TRANSFER_INITIATOR identifier = 1 transfer_secret = sha3(target + b'1') secret_registry_proxy = app0.raiden.chain.secret_registry( secret_registry_address, ) secret_registry_proxy.register_secret(secret=transfer_secret, given_block_identifier='latest') # Test that sending a transfer with a secret already registered on-chain fails with pytest.raises(RaidenUnrecoverableError): app0.raiden.start_mediated_transfer_with_secret( token_network_identifier, amount, target, identifier, transfer_secret, ) expiration = 9999 transfer = make_signed_transfer( amount, UNIT_TRANSFER_INITIATOR, app0.raiden.address, expiration, transfer_secret, ) message_handler = MessageHandler() message_handler.handle_message_lockedtransfer( app0.raiden, transfer, ) state_changes = app0.raiden.wal.storage.get_statechanges_by_identifier( 0, 'latest') transfer_statechange_dispatched = ( search_for_item(state_changes, ActionInitMediator, {}) or search_for_item(state_changes, ActionInitTarget, {})) assert not transfer_statechange_dispatched
def test_handle_offchain_secretreveal_after_lock_expired(): """Test that getting the secret revealed after lock expiration for the target does not end up continuously emitting EventUnlockClaimFailed Target part for https://github.com/raiden-network/raiden/issues/3086 """ setup = make_target_state() lock_expiration_block_number = channel.get_sender_expiration_threshold( setup.new_state.transfer.lock, ) lock_expiration_block = Block( block_number=lock_expiration_block_number, gas_limit=1, block_hash=factories.make_transaction_hash(), ) iteration = target.state_transition( target_state=setup.new_state, state_change=lock_expiration_block, channel_state=setup.channel, pseudo_random_generator=setup.pseudo_random_generator, block_number=lock_expiration_block_number, ) state = iteration.new_state msg = 'At the expiration block we should get an EventUnlockClaimFailed' assert search_for_item(iteration.events, EventUnlockClaimFailed, {}), msg iteration = target.state_transition( target_state=state, state_change=ReceiveSecretReveal(UNIT_SECRET, setup.initiator), channel_state=setup.channel, pseudo_random_generator=setup.pseudo_random_generator, block_number=lock_expiration_block_number + 1, ) state = iteration.new_state next_block = Block( block_number=lock_expiration_block_number + 1, gas_limit=1, block_hash=factories.make_transaction_hash(), ) iteration = target.state_transition( target_state=state, state_change=next_block, channel_state=setup.channel, pseudo_random_generator=setup.pseudo_random_generator, block_number=lock_expiration_block_number + 1, ) msg = 'At the next block we should not get the same event' assert not search_for_item(iteration.events, EventUnlockClaimFailed, {}), msg
def run_test_regression_revealsecret_after_secret(raiden_network, token_addresses, transport_protocol): app0, app1, app2 = raiden_network token = token_addresses[0] identifier = 1 payment_network_identifier = app0.raiden.default_registry.address token_network_identifier = views.get_token_network_identifier_by_token_address( views.state_from_app(app0), payment_network_identifier, token) payment_status = app0.raiden.mediated_transfer_async( token_network_identifier, amount=1, target=app2.raiden.address, identifier=identifier) assert payment_status.payment_done.wait() event = search_for_item(app1.raiden.wal.storage.get_events(), SendSecretReveal, {}) assert event message_identifier = random.randint(0, UINT64_MAX) reveal_secret = RevealSecret(message_identifier=message_identifier, secret=event.secret) app2.raiden.sign(reveal_secret) if transport_protocol is TransportProtocol.UDP: reveal_data = reveal_secret.encode() host_port = None app1.raiden.transport.receive(reveal_data, host_port) elif transport_protocol is TransportProtocol.MATRIX: app1.raiden.transport._receive_message(reveal_secret) # pylint: disable=protected-access else: raise TypeError("Unknown TransportProtocol")
def test_events_for_onchain_secretreveal(): """ Secret must be registered on-chain when the unsafe region is reached and the secret is known. """ block_number = 10 expiration = block_number + 30 channels = make_channel_set([channel_properties]) from_transfer = make_target_transfer(channels[0], expiration=expiration) channel.handle_receive_lockedtransfer(channels[0], from_transfer) channel.register_offchain_secret(channels[0], UNIT_SECRET, UNIT_SECRETHASH) safe_to_wait = expiration - channels[0].reveal_timeout - 1 unsafe_to_wait = expiration - channels[0].reveal_timeout state = TargetTransferState(channels.get_route(0), from_transfer) events = target.events_for_onchain_secretreveal(state, channels[0], safe_to_wait) assert not events events = target.events_for_onchain_secretreveal(state, channels[0], unsafe_to_wait) msg = 'when its not safe to wait, the contract send must be emitted' assert search_for_item(events, ContractSendSecretReveal, {'secret': UNIT_SECRET}), msg msg = 'second call must not emit ContractSendSecretReveal again' assert not target.events_for_onchain_secretreveal(state, channels[0], unsafe_to_wait), msg
def test_regression_revealsecret_after_secret(raiden_network, token_addresses, transport_protocol): """ A RevealSecret message received after a Unlock message must be cleanly handled. """ app0, app1, app2 = raiden_network token = token_addresses[0] identifier = 1 token_network_registry_address = app0.raiden.default_registry.address token_network_address = views.get_token_network_address_by_token_address( views.state_from_app(app0), token_network_registry_address, token) payment_status = app0.raiden.mediated_transfer_async( token_network_address, amount=1, target=app2.raiden.address, identifier=identifier) with watch_for_unlock_failures(*raiden_network): assert payment_status.payment_done.wait() event = search_for_item(app1.raiden.wal.storage.get_events(), SendSecretReveal, {}) assert event reveal_secret = RevealSecret( message_identifier=make_message_identifier(), secret=event.secret, signature=EMPTY_SIGNATURE, ) app2.raiden.sign(reveal_secret) if transport_protocol is TransportProtocol.MATRIX: app1.raiden.transport._receive_message(reveal_secret) # pylint: disable=protected-access else: raise TypeError("Unknown TransportProtocol")
def test_regression_unavailable_nodes_must_be_properly_filtered(): """The list of available routes provided must be filtered based on the network status of the partner node. Regression test for: https://github.com/raiden-network/raiden/issues/3567 """ block_number = 5 pseudo_random_generator = random.Random() channels = factories.mediator_make_channel_pair() payer_transfer = factories.make_signed_transfer_for( channels[0], LONG_EXPIRATION) all_nodes_offline = { channel.partner_state.address: NODE_NETWORK_UNREACHABLE for channel in channels.channels } initial_iteration = mediator.state_transition( mediator_state=None, state_change=factories.mediator_make_init_action( channels, payer_transfer), channelidentifiers_to_channels=channels.channel_map, nodeaddresses_to_networkstates=all_nodes_offline, pseudo_random_generator=pseudo_random_generator, block_number=block_number, block_hash=factories.make_block_hash(), ) send_transfer = search_for_item(initial_iteration.events, SendLockedTransfer, {}) msg = ( 'All available routes are with unavailable nodes, therefore no send ' 'should be produced') assert send_transfer is None, msg
def test_recovery_blockchain_events(raiden_network, restart_node, token_addresses, network_wait): """ Close one of the two raiden apps that have a channel between them, have the counterparty close the channel and then make sure the restarted app sees the change """ app0, app1 = raiden_network token_address = token_addresses[0] app0.raiden.stop() new_transport = MatrixTransport( config=app0.raiden.config.transport, environment=app0.raiden.config.environment_type) app1_api = RaidenAPI(app1.raiden) app1_api.channel_close( registry_address=app0.raiden.default_registry.address, token_address=token_address, partner_address=app0.raiden.address, ) app0.stop() raiden_event_handler = RaidenEventHandler() message_handler = MessageHandler() app0_restart = App( config=app0.config, rpc_client=app0.raiden.rpc_client, proxy_manager=app0.raiden.proxy_manager, query_start_block=BlockNumber(0), default_registry=app0.raiden.default_registry, default_one_to_n_address=app0.raiden.default_one_to_n_address, default_secret_registry=app0.raiden.default_secret_registry, default_service_registry=app0.raiden.default_service_registry, default_msc_address=app0.raiden.default_msc_address, transport=new_transport, raiden_event_handler=raiden_event_handler, message_handler=message_handler, routing_mode=RoutingMode.PRIVATE, ) del app0 # from here on the app0_restart should be used restart_node(app0_restart) wal = app0_restart.raiden.wal assert wal # wait for the nodes' healthcheck to update the network statuses waiting.wait_for_healthy(app0_restart.raiden, app1.raiden.address, network_wait) waiting.wait_for_healthy(app1.raiden, app0_restart.raiden.address, network_wait) restarted_state_changes = wal.storage.get_statechanges_by_range( RANGE_ALL_STATE_CHANGES) assert search_for_item(restarted_state_changes, ContractReceiveChannelClosed, {})
def test_blockchain_event_processed_interleaved( raiden_network: List[App], token_addresses: List[TokenAddress], restart_node: RestartNode, ): """ Blockchain events must be transformed into state changes and processed by the state machine interleaved. Otherwise problems arise when the creation of the state change is dependent on the state of the state machine. Regression test for: https://github.com/raiden-network/raiden/issues/6444 """ app0, app1 = raiden_network app1.stop() api0 = RaidenAPI(app0.raiden) channel_id = api0.channel_open( registry_address=app0.raiden.default_registry.address, token_address=token_addresses[0], partner_address=app1.raiden.address, ) api0.channel_close( registry_address=app0.raiden.default_registry.address, token_address=token_addresses[0], partner_address=app1.raiden.address, ) # Restart node 1 restart_node(app1) wait_all_apps(raiden_network) # Check correct events assert app1.raiden.wal, "app1.wal not set" app1_state_changes = app1.raiden.wal.storage.get_statechanges_by_range(RANGE_ALL_STATE_CHANGES) assert search_for_item( app1_state_changes, ContractReceiveChannelNew, {"channel_identifier": channel_id} ) assert search_for_item( app1_state_changes, ContractReceiveChannelClosed, {"channel_identifier": channel_id} ) assert not search_for_item( app1_state_changes, ContractReceiveRouteClosed, {"channel_identifier": channel_id} )
def test_events(amount, address): return search_for_item( receiver_app.raiden.wal.storage.get_events(), EventPaymentReceivedSuccess, { 'amount': amount, 'initiator': address }, )
def run_test_node_can_settle_if_partner_does_not_call_update_transfer( raiden_network, number_of_nodes, token_addresses, network_wait, ): app0, app1 = raiden_network token_address = token_addresses[0] chain_state = views.state_from_app(app0) payment_network_id = app0.raiden.default_registry.address registry_address = app0.raiden.default_registry.address token_network_identifier = views.get_token_network_identifier_by_token_address( chain_state=chain_state, payment_network_id=payment_network_id, token_address=token_address, ) channel_identifier = get_channelstate(app0, app1, token_network_identifier).identifier transfer( initiator_app=app0, target_app=app1, token_address=token_address, amount=1, identifier=1, timeout=network_wait * number_of_nodes, ) # stop app1 - the test uses token_network_contract now app1.stop() RaidenAPI(app0.raiden).channel_close( registry_address=registry_address, token_address=token_address, partner_address=app1.raiden.address, ) # app1 won't update the channel waiting.wait_for_settle( raiden=app0.raiden, payment_network_id=registry_address, token_address=token_address, channel_ids=[channel_identifier], retry_timeout=app0.raiden.alarm.sleep_time, ) state_changes = app0.raiden.wal.storage.get_statechanges_by_identifier( from_identifier=0, to_identifier='latest', ) assert search_for_item( state_changes, ContractReceiveChannelSettled, { 'token_network_identifier': token_network_identifier, 'channel_identifier': channel_identifier, }, )
def wait_for_batch_unlock(app, token_network_id, participant, partner): unlock_event = None while not unlock_event: gevent.sleep(1) state_changes = app.raiden.wal.storage.get_statechanges_by_identifier( from_identifier=0, to_identifier='latest', ) unlock_event = search_for_item(state_changes, ContractReceiveChannelBatchUnlock, { 'token_network_identifier': token_network_id, 'participant': participant, 'partner': partner, })
def test_handle_inittarget_bad_expiration(): """ Init transfer must do nothing if the expiration is bad. """ block_number = 1 pseudo_random_generator = random.Random() channels = make_channel_set([channel_properties]) expiration = channels[0].reveal_timeout + block_number + 1 from_transfer = make_target_transfer(channels[0], expiration=expiration) channel.handle_receive_lockedtransfer(channels[0], from_transfer) state_change = ActionInitTarget(channels.get_route(0), from_transfer) iteration = target.handle_inittarget(state_change, channels[0], pseudo_random_generator, block_number) assert search_for_item(iteration.events, EventUnlockClaimFailed, {})
def wait_for_batch_unlock(app, token_network_address, receiver, sender): unlock_event = None while not unlock_event: gevent.sleep(1) state_changes = app.raiden.wal.storage.get_statechanges_by_range(RANGE_ALL_STATE_CHANGES) unlock_event = search_for_item( state_changes, ContractReceiveChannelBatchUnlock, { "token_network_address": token_network_address, "receiver": receiver, "sender": sender, }, )
def run_test_event_transfer_received_success( token_addresses, raiden_chain, ): sender_apps = raiden_chain[:-1] target_app = raiden_chain[-1] token_address = token_addresses[0] registry_address = target_app.raiden.default_registry.address target_address = target_app.raiden.address message_handler = WaitForMessage() target_app.raiden.message_handler = message_handler wait_for = list() for amount, app in enumerate(sender_apps, 1): secret = random_secret() wait = message_handler.wait_for_message( Unlock, {'secret': secret}, ) wait_for.append((wait, app.raiden.address, amount)) RaidenAPI(app.raiden).transfer_async( registry_address=registry_address, token_address=token_address, amount=amount, identifier=amount, target=target_address, secret=to_hex(secret), secret_hash=to_hex(sha3(secret)), ) for wait, sender, amount in wait_for: wait.wait() assert search_for_item( target_app.raiden.wal.storage.get_events(), EventPaymentReceivedSuccess, { 'amount': amount, 'identifier': amount, 'initiator': sender, 'payment_network_identifier': registry_address, # 'token_network_identifier': , }, )
def test_target_lock_is_expired_if_secret_is_not_registered_onchain(): lock_amount = 7 block_number = 1 pseudo_random_generator = random.Random() channels = make_channel_set([channel_properties2]) from_transfer = make_target_transfer(channels[0], amount=lock_amount, block_number=1) init = ActionInitTarget( from_hop=channels.get_hop(0), transfer=from_transfer, balance_proof=from_transfer.balance_proof, sender=from_transfer.balance_proof.sender, # pylint: disable=no-member ) init_transition = target.state_transition( target_state=None, state_change=init, channel_state=channels[0], pseudo_random_generator=pseudo_random_generator, block_number=block_number, ) assert init_transition.new_state is not None secret_reveal_iteration = target.state_transition( target_state=init_transition.new_state, state_change=ReceiveSecretReveal(UNIT_SECRET, channels[0].partner_state.address), channel_state=channels[0], pseudo_random_generator=pseudo_random_generator, block_number=block_number, ) expired_block_number = channel.get_receiver_expiration_threshold( from_transfer.lock.expiration) iteration = target.state_transition( target_state=secret_reveal_iteration.new_state, state_change=Block(expired_block_number, None, None), channel_state=channels[0], pseudo_random_generator=pseudo_random_generator, block_number=expired_block_number, ) assert search_for_item(iteration.events, EventUnlockClaimFailed, {})
def wait_for_batch_unlock( app: App, token_network_address: TokenNetworkAddress, receiver: Address, sender: Address ) -> None: unlock_event = None while not unlock_event: gevent.sleep(1) assert app.raiden.wal, MSG_BLOCKCHAIN_EVENTS assert app.raiden.alarm, MSG_BLOCKCHAIN_EVENTS state_changes = app.raiden.wal.storage.get_statechanges_by_range(RANGE_ALL_STATE_CHANGES) unlock_event = search_for_item( state_changes, ContractReceiveChannelBatchUnlock, { "token_network_address": token_network_address, "receiver": receiver, "sender": sender, }, )
def test_payer_enter_danger_zone_with_transfer_payed(): """ A mediator may have paid the next hop (payee), and didn't get paid by the previous hop (payer). When this happens, an assertion must not be hit, because it means the transfer must be unlocked on-chain. Issue: https://github.com/raiden-network/raiden/issues/1013 """ block_number = 5 pseudo_random_generator = random.Random() channels = factories.mediator_make_channel_pair() payer_transfer = factories.make_signed_transfer_for( channels[0], LONG_EXPIRATION) initial_iteration = mediator.state_transition( mediator_state=None, state_change=factories.mediator_make_init_action( channels, payer_transfer), channelidentifiers_to_channels=channels.channel_map, nodeaddresses_to_networkstates=channels.nodeaddresses_to_networkstates, pseudo_random_generator=pseudo_random_generator, block_number=block_number, block_hash=factories.make_block_hash(), ) send_transfer = search_for_item(initial_iteration.events, SendLockedTransfer, {}) assert send_transfer lock_expiration = send_transfer.transfer.lock.expiration new_state = initial_iteration.new_state for block_number in range(block_number, lock_expiration - channels[1].reveal_timeout): block_state_change = Block( block_number=block_number, gas_limit=1, block_hash=factories.make_transaction_hash(), ) block_iteration = mediator.handle_block( new_state, block_state_change, channels.channel_map, pseudo_random_generator, ) new_state = block_iteration.new_state # send the balance proof, transitioning the payee state to paid assert new_state.transfers_pair[0].payee_state == 'payee_pending' receive_secret = ReceiveSecretReveal( UNIT_SECRET, channels[1].partner_state.address, ) paid_iteration = mediator.state_transition( mediator_state=new_state, state_change=receive_secret, channelidentifiers_to_channels=channels.channel_map, nodeaddresses_to_networkstates=channels.nodeaddresses_to_networkstates, pseudo_random_generator=pseudo_random_generator, block_number=block_number, block_hash=factories.make_block_hash(), ) paid_state = paid_iteration.new_state assert paid_state.transfers_pair[0].payee_state == 'payee_balance_proof' # move to the block in which the payee lock expires. This must not raise an # assertion expired_block_number = lock_expiration + 1 expired_block_state_change = Block( block_number=expired_block_number, gas_limit=1, block_hash=factories.make_transaction_hash(), ) block_iteration = mediator.handle_block( mediator_state=paid_state, state_change=expired_block_state_change, channelidentifiers_to_channels=channels.channel_map, pseudo_random_generator=pseudo_random_generator, )
def test_regression_mediator_not_update_payer_state_twice(): """ Regression Test for https://github.com/raiden-network/raiden/issues/3086 Make sure that after a lock expired the mediator doesn't update the pair twice causing EventUnlockClaimFailed to be generated at every block. """ pseudo_random_generator = random.Random() pair = factories.mediator_make_channel_pair() payer_channel, payee_channel = pair.channels payer_route = factories.route_from_channel(payer_channel) payer_transfer = factories.make_signed_transfer_for( payer_channel, LONG_EXPIRATION) available_routes = [factories.route_from_channel(payee_channel)] init_state_change = ActionInitMediator( routes=available_routes, from_route=payer_route, from_transfer=payer_transfer, ) iteration = mediator.state_transition( mediator_state=None, state_change=init_state_change, channelidentifiers_to_channels=pair.channel_map, nodeaddresses_to_networkstates=pair.nodeaddresses_to_networkstates, pseudo_random_generator=pseudo_random_generator, block_number=5, block_hash=factories.make_block_hash(), ) assert iteration.new_state is not None current_state = iteration.new_state send_transfer = search_for_item(iteration.events, SendLockedTransfer, {}) assert send_transfer transfer = send_transfer.transfer block_expiration_number = channel.get_sender_expiration_threshold( transfer.lock) block = Block( block_number=block_expiration_number, gas_limit=1, block_hash=factories.make_transaction_hash(), ) iteration = mediator.state_transition( mediator_state=current_state, state_change=block, channelidentifiers_to_channels=pair.channel_map, nodeaddresses_to_networkstates=pair.nodeaddresses_to_networkstates, pseudo_random_generator=pseudo_random_generator, block_number=block_expiration_number, block_hash=factories.make_block_hash(), ) msg = 'At the expiration block we should get an EventUnlockClaimFailed' assert search_for_item(iteration.events, EventUnlockClaimFailed, {}), msg current_state = iteration.new_state next_block = Block( block_number=block_expiration_number + 1, gas_limit=1, block_hash=factories.make_transaction_hash(), ) # Initiator receives the secret reveal after the lock expired receive_secret = ReceiveSecretReveal( secret=UNIT_SECRET, sender=payee_channel.partner_state.address, ) iteration = mediator.state_transition( mediator_state=current_state, state_change=receive_secret, channelidentifiers_to_channels=pair.channel_map, nodeaddresses_to_networkstates=pair.nodeaddresses_to_networkstates, pseudo_random_generator=pseudo_random_generator, block_number=next_block.block_number, block_hash=next_block.block_hash, ) current_state = iteration.new_state lock = payer_transfer.lock secrethash = lock.secrethash assert secrethash in payer_channel.partner_state.secrethashes_to_lockedlocks assert current_state.transfers_pair[0].payee_state == 'payee_expired' assert not channel.is_secret_known(payer_channel.partner_state, secrethash) safe_to_wait, _ = mediator.is_safe_to_wait( lock_expiration=lock.expiration, reveal_timeout=payer_channel.reveal_timeout, block_number=lock.expiration + 10, ) assert not safe_to_wait iteration = mediator.state_transition( mediator_state=current_state, state_change=next_block, channelidentifiers_to_channels=pair.channel_map, nodeaddresses_to_networkstates=pair.nodeaddresses_to_networkstates, pseudo_random_generator=pseudo_random_generator, block_number=block_expiration_number, block_hash=factories.make_block_hash(), ) msg = 'At the next block we should not get the same event' assert not search_for_item(iteration.events, EventUnlockClaimFailed, {}), msg