Exemplo n.º 1
0
def test_handle_block_closed_channel():
    channel_state = factories.create(
        factories.NettingChannelStateProperties(
            close_transaction=TransactionExecutionStatus(
                finished_block_number=50,
                result=TransactionExecutionStatus.SUCCESS),
            settle_timeout=50,
        ))
    pseudo_random_generator = random.Random()
    block = Block(block_number=90,
                  gas_limit=100000,
                  block_hash=factories.make_block_hash())
    before_settle = handle_block(
        channel_state=channel_state,
        state_change=block,
        block_number=block.block_number,
        pseudo_random_generator=pseudo_random_generator,
    )
    assert get_status(before_settle.new_state) == ChannelState.STATE_CLOSED
    assert not before_settle.events

    block = Block(block_number=102,
                  gas_limit=100000,
                  block_hash=factories.make_block_hash())
    after_settle = handle_block(
        channel_state=before_settle.new_state,
        state_change=block,
        block_number=block.block_number,
        pseudo_random_generator=pseudo_random_generator,
    )
    assert get_status(after_settle.new_state) == ChannelState.STATE_SETTLING
    assert after_settle.events
Exemplo n.º 2
0
def test_handle_onchain_secretreveal():
    """ The target node must update the lock state when the secret is
    registered in the blockchain.
    """
    setup = make_target_state(block_number=1,
                              expiration=1 + factories.UNIT_REVEAL_TIMEOUT)
    assert factories.UNIT_SECRETHASH in setup.channel.partner_state.secrethashes_to_lockedlocks

    offchain_secret_reveal_iteration = target.state_transition(
        target_state=setup.new_state,
        state_change=ReceiveSecretReveal(UNIT_SECRET, setup.initiator),
        channel_state=setup.channel,
        pseudo_random_generator=setup.pseudo_random_generator,
        block_number=setup.block_number,
    )
    assert UNIT_SECRETHASH in setup.channel.partner_state.secrethashes_to_unlockedlocks
    assert UNIT_SECRETHASH not in setup.channel.partner_state.secrethashes_to_lockedlocks

    # Make sure that an emptyhash on chain reveal is rejected.
    block_number_prior_the_expiration = setup.expiration - 2
    onchain_reveal = ContractReceiveSecretReveal(
        transaction_hash=factories.make_address(),
        secret_registry_address=factories.make_address(),
        secrethash=EMPTY_HASH_KECCAK,
        secret=EMPTY_HASH,
        block_number=block_number_prior_the_expiration,
        block_hash=factories.make_block_hash(),
    )
    onchain_secret_reveal_iteration = target.state_transition(
        target_state=offchain_secret_reveal_iteration.new_state,
        state_change=onchain_reveal,
        channel_state=setup.channel,
        pseudo_random_generator=setup.pseudo_random_generator,
        block_number=block_number_prior_the_expiration,
    )
    unlocked_onchain = setup.channel.partner_state.secrethashes_to_onchain_unlockedlocks
    assert EMPTY_HASH_KECCAK not in unlocked_onchain

    # now let's go for the actual secret
    onchain_reveal.secret = UNIT_SECRET
    onchain_reveal.secrethash = UNIT_SECRETHASH
    onchain_secret_reveal_iteration = target.state_transition(
        target_state=offchain_secret_reveal_iteration.new_state,
        state_change=onchain_reveal,
        channel_state=setup.channel,
        pseudo_random_generator=setup.pseudo_random_generator,
        block_number=block_number_prior_the_expiration,
    )
    unlocked_onchain = setup.channel.partner_state.secrethashes_to_onchain_unlockedlocks
    assert UNIT_SECRETHASH in unlocked_onchain

    # Check that after we register a lock on-chain handling the block again will
    # not cause us to attempt an onchain re-register
    extra_block_handle_transition = target.handle_block(
        target_state=onchain_secret_reveal_iteration.new_state,
        channel_state=setup.channel,
        block_number=block_number_prior_the_expiration + 1,
        block_hash=factories.make_block_hash(),
    )
    assert len(extra_block_handle_transition.events) == 0
Exemplo n.º 3
0
def test_contract_receive_channelnew_must_be_idempotent():
    block_number = 10
    block_hash = factories.make_block_hash()
    pseudo_random_generator = random.Random()

    token_network_id = factories.make_address()
    token_id = factories.make_address()
    token_network_state = TokenNetworkState(token_network_id, token_id)
    payment_network_identifier = factories.make_payment_network_identifier()

    amount = 30
    our_balance = amount + 50
    channel_state1 = factories.make_channel(our_balance=our_balance)
    channel_state2 = copy.deepcopy(channel_state1)

    state_change1 = ContractReceiveChannelNew(
        transaction_hash=factories.make_transaction_hash(),
        token_network_identifier=token_network_id,
        channel_state=channel_state1,
        block_number=block_number,
        block_hash=block_hash,
    )

    token_network.state_transition(
        payment_network_identifier=payment_network_identifier,
        token_network_state=token_network_state,
        state_change=state_change1,
        pseudo_random_generator=pseudo_random_generator,
        block_number=block_number,
        block_hash=block_hash,
    )

    state_change2 = ContractReceiveChannelNew(
        transaction_hash=factories.make_transaction_hash(),
        token_network_identifier=token_network_id,
        channel_state=channel_state2,
        block_number=block_number + 1,
        block_hash=factories.make_block_hash(),
    )

    # replay the ContractReceiveChannelNew state change
    iteration = token_network.state_transition(
        payment_network_identifier=payment_network_identifier,
        token_network_state=token_network_state,
        state_change=state_change2,
        pseudo_random_generator=pseudo_random_generator,
        block_number=block_number,
        block_hash=block_hash,
    )

    msg = 'the channel must not have been overwritten'
    channelmap_by_id = iteration.new_state.channelidentifiers_to_channels
    assert channelmap_by_id[channel_state1.identifier] == channel_state1, msg

    channelmap_by_address = iteration.new_state.partneraddresses_to_channelidentifiers
    partner_channels_ids = channelmap_by_address[
        channel_state1.partner_state.address]
    assert channel_state1.identifier in partner_channels_ids, msg
Exemplo n.º 4
0
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
Exemplo n.º 5
0
def test_contract_receive_channelnew_must_be_idempotent(channel_properties):
    block_number = 10
    block_hash = factories.make_block_hash()

    token_network_address = factories.make_address()
    token_id = factories.make_address()
    token_network_state = TokenNetworkState(
        address=token_network_address,
        token_address=token_id,
        network_graph=TokenNetworkGraphState(token_network_address),
    )

    pseudo_random_generator = random.Random()

    properties, _ = channel_properties
    channel_state1 = factories.create(properties)
    channel_state2 = deepcopy(channel_state1)

    state_change1 = ContractReceiveChannelNew(
        transaction_hash=factories.make_transaction_hash(),
        channel_state=channel_state1,
        block_number=block_number,
        block_hash=block_hash,
    )

    token_network.state_transition(
        token_network_state=token_network_state,
        state_change=state_change1,
        block_number=block_number,
        block_hash=block_hash,
        pseudo_random_generator=pseudo_random_generator,
    )

    state_change2 = ContractReceiveChannelNew(
        transaction_hash=factories.make_transaction_hash(),
        channel_state=channel_state2,
        block_number=block_number + 1,
        block_hash=factories.make_block_hash(),
    )

    # replay the ContractReceiveChannelNew state change
    iteration = token_network.state_transition(
        token_network_state=token_network_state,
        state_change=state_change2,
        block_number=block_number,
        block_hash=block_hash,
        pseudo_random_generator=pseudo_random_generator,
    )

    msg = "the channel must not have been overwritten"
    channelmap_by_id = iteration.new_state.channelidentifiers_to_channels
    assert channelmap_by_id[channel_state1.identifier] == channel_state1, msg

    channelmap_by_address = iteration.new_state.partneraddresses_to_channelidentifiers
    partner_channels_ids = channelmap_by_address[
        channel_state1.partner_state.address]
    assert channel_state1.identifier in partner_channels_ids, msg
Exemplo n.º 6
0
def test_channel_cleared_after_our_unlock():
    pseudo_random_generator = random.Random()
    our_model, _ = create_model(balance=700, num_pending_locks=1)
    partner_model, partner_key1 = create_model(balance=700,
                                               num_pending_locks=0)
    channel_state = create_channel_from_models(our_model, partner_model,
                                               partner_key1)
    block_number = 1
    block_hash = make_block_hash()

    def make_unlock(unlock_end, partner_end):
        batch_unlock = ContractReceiveChannelBatchUnlock(
            transaction_hash=make_transaction_hash(),
            canonical_identifier=channel_state.canonical_identifier,
            receiver=partner_end.address,
            sender=unlock_end.address,
            locksroot=unlock_end.balance_proof.locksroot,
            unlocked_amount=10,
            returned_tokens=0,
            block_number=block_number,
            block_hash=block_hash,
        )
        return batch_unlock

    settle_channel = ContractReceiveChannelSettled(
        transaction_hash=make_transaction_hash(),
        canonical_identifier=channel_state.canonical_identifier,
        our_onchain_locksroot=compute_locksroot(
            channel_state.our_state.pending_locks),
        partner_onchain_locksroot=compute_locksroot(
            channel_state.partner_state.pending_locks),
        block_number=1,
        block_hash=make_block_hash(),
    )

    assert settle_channel.our_onchain_locksroot != LOCKSROOT_OF_NO_LOCKS
    assert settle_channel.partner_onchain_locksroot == LOCKSROOT_OF_NO_LOCKS

    iteration = channel.state_transition(
        channel_state=channel_state,
        state_change=settle_channel,
        block_number=block_number,
        block_hash=block_hash,
        pseudo_random_generator=pseudo_random_generator,
    )

    batch_unlock = make_unlock(channel_state.our_state,
                               channel_state.partner_state)
    iteration = channel.state_transition(
        channel_state=iteration.new_state,
        state_change=batch_unlock,
        block_number=block_number,
        block_hash=block_hash,
        pseudo_random_generator=pseudo_random_generator,
    )
    msg = "partner did not have any locks in the pending locks, channel should have been cleaned"
    assert iteration.new_state is None, msg
Exemplo n.º 7
0
def test_events_loaded_from_storage_should_deserialize(tmp_path):
    filename = Path(f"{tmp_path}/v{RAIDEN_DB_VERSION}_log.db")
    storage = SerializedSQLiteStorage(filename, serializer=JSONSerializer())

    # Satisfy the foreign-key constraint for state change ID
    ids = storage.write_state_changes([
        Block(
            block_number=BlockNumber(1),
            gas_limit=BlockGasLimit(1),
            block_hash=factories.make_block_hash(),
        )
    ])

    canonical_identifier = factories.make_canonical_identifier()
    recipient = factories.make_address()
    participant = factories.make_address()
    event = SendWithdrawRequest(
        recipient=recipient,
        canonical_identifier=canonical_identifier,
        message_identifier=factories.make_message_identifier(),
        total_withdraw=WithdrawAmount(1),
        participant=participant,
        expiration=BlockExpiration(10),
        nonce=Nonce(15),
    )
    storage.write_events([(ids[0], event)])

    stored_events = storage.get_events()
    assert stored_events[0] == event
Exemplo n.º 8
0
def test_serialize_contract_send_subclass(chain_state):
    """Serializing must preserve class

    Regression test for https://github.com/raiden-network/raiden/issues/6075
    """
    canonical_identifier = CanonicalIdentifier(
        chain_identifier=ChainID(1),
        token_network_address=TokenNetworkAddress(factories.make_address()),
        channel_identifier=factories.make_channel_identifier(),
    )
    chain_state.pending_transactions = [
        ContractSendChannelClose(
            canonical_identifier=canonical_identifier,
            triggered_by_block_hash=factories.make_block_hash(),
            balance_proof=None,
        )
    ]

    serialized_chain_state = JSONSerializer.serialize(chain_state)
    deserialized_chain_state = JSONSerializer.deserialize(
        serialized_chain_state)
    assert (
        chain_state.pending_transactions[0].__class__.__name__ ==
        deserialized_chain_state.pending_transactions[0].__class__.__name__)
    assert chain_state == deserialized_chain_state
Exemplo n.º 9
0
    def initialize(self, block_number, random, random_seed):
        self.random_seed = random_seed

        self.block_number = block_number
        self.block_hash = factories.make_block_hash()
        self.random = random
        self.private_key, self.address = factories.make_privkey_address()

        self.chain_state = ChainState(
            pseudo_random_generator=self.random,
            block_number=self.block_number,
            block_hash=self.block_hash,
            our_address=self.address,
            chain_id=factories.UNIT_CHAIN_ID,
        )

        self.token_network_id = factories.UNIT_TOKEN_NETWORK_ADDRESS
        self.token_id = factories.UNIT_TOKEN_ADDRESS
        self.token_network_state = TokenNetworkState(self.token_network_id,
                                                     self.token_id)

        self.payment_network_id = factories.make_payment_network_identifier()
        self.payment_network_state = PaymentNetworkState(
            self.payment_network_id, [self.token_network_state])

        self.chain_state.identifiers_to_paymentnetworks[
            self.payment_network_id] = self.payment_network_state

        self.chain_state.tokennetworkaddresses_to_paymentnetworkaddresses[
            self.token_network_id] = self.payment_network_id
        channels = [
            self.new_channel_with_transaction()
            for _ in range(self.initial_number_of_channels)
        ]
        return multiple(*channels)
Exemplo n.º 10
0
    def __init__(self,
                 message_handler=None,
                 state_transition=None,
                 private_key=None):
        if private_key is None:
            self.private_key, self.address = factories.make_privkey_address()
        else:
            self.private_key = private_key
            self.address = privatekey_to_address(private_key)

        self.chain = MockChain(network_id=17, node_address=self.address)
        self.signer = LocalSigner(self.private_key)

        self.message_handler = message_handler

        self.user_deposit = Mock()

        if state_transition is None:
            state_transition = node.state_transition

        serializer = JSONSerializer
        state_manager = StateManager(state_transition, None)
        storage = SerializedSQLiteStorage(":memory:", serializer)
        self.wal = WriteAheadLog(state_manager, storage)

        state_change = ActionInitChain(
            pseudo_random_generator=random.Random(),
            block_number=0,
            block_hash=factories.make_block_hash(),
            our_address=self.chain.node_address,
            chain_id=self.chain.network_id,
        )

        self.wal.log_and_dispatch(state_change)
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
Exemplo n.º 12
0
def test_channel_closed_must_clear_ordered_messages(chain_state,
                                                    token_network_state,
                                                    netting_channel_state):
    recipient = netting_channel_state.partner_state.address
    message_identifier = random.randint(0, 2**16)
    amount = 10

    queue_identifier = QueueIdentifier(
        recipient=recipient,
        canonical_identifier=netting_channel_state.canonical_identifier)

    # Regression test:
    # The code delivered_message handler worked only with a queue of one
    # element
    message = factories.create(
        factories.LockedTransferProperties(
            message_identifier=message_identifier,
            token=token_network_state.token_address,
            canonical_identifier=netting_channel_state.canonical_identifier,
            transferred_amount=amount,
            recipient=recipient,
        ))

    chain_state.queueids_to_queues[queue_identifier] = [message]

    closed = state_change.ContractReceiveChannelClosed(
        transaction_hash=EMPTY_HASH,
        transaction_from=recipient,
        canonical_identifier=netting_channel_state.canonical_identifier,
        block_number=1,
        block_hash=factories.make_block_hash(),
    )

    iteration = node.handle_state_change(chain_state, closed)
    assert queue_identifier not in iteration.new_state.queueids_to_queues
Exemplo n.º 13
0
def test_actioninitchain_restore():
    """ ActionInitChain *must* restore the previous pseudo random generator
    state.

    Message identifiers are used for confirmation messages, e.g. delivered and
    processed messages, therefore it's important for each message identifier to
    not collide with a previous identifier, for this reason the PRNG is used.

    Additionally, during restarts the state changes are reapplied, and it's
    really important for the re-execution of the state changes to be
    deterministic, otherwise undefined behavior may happen. For this reason the
    state of the PRNG must be restored.

    If the above is not respected, the message ids generated during restart
    will not match the previous IDs and the message queues won't be properly
    cleared up.
    """
    pseudo_random_generator = random.Random()
    block_number = 577
    our_address = factories.make_address()
    chain_id = 777

    original_obj = state_change.ActionInitChain(
        pseudo_random_generator=pseudo_random_generator,
        block_number=block_number,
        block_hash=factories.make_block_hash(),
        our_address=our_address,
        chain_id=chain_id,
    )

    decoded_obj = JSONSerializer.deserialize(
        JSONSerializer.serialize(original_obj))

    assert original_obj == decoded_obj
Exemplo n.º 14
0
def setup_storage(db_path):
    storage = SerializedSQLiteStorage(str(db_path), JSONSerializer())

    chain_state_data = Path(__file__).parent / 'data/v16_chainstate.json'
    chain_state = chain_state_data.read_text()

    storage.write_state_change(
        ActionInitChain(
            pseudo_random_generator=random.Random(),
            block_number=1,
            block_hash=factories.make_block_hash(),
            our_address=factories.make_address(),
            chain_id=1,
        ),
        datetime.utcnow().isoformat(timespec='milliseconds'),
    )

    cursor = storage.conn.cursor()
    cursor.execute(
        """
        INSERT INTO state_snapshot(identifier, statechange_id, data)
        VALUES(1, 1, ?)
        """,
        (chain_state, ),
    )
    storage.conn.commit()
    return storage
Exemplo n.º 15
0
    def initialize(self, block_number, random, random_seed):
        self.random_seed = random_seed

        self.block_number = block_number
        self.block_hash = factories.make_block_hash()
        self.random = random
        self.private_key, self.address = factories.make_privkey_address()

        self.chain_state = ChainState(
            pseudo_random_generator=self.random,
            block_number=self.block_number,
            block_hash=self.block_hash,
            our_address=self.address,
            chain_id=factories.UNIT_CHAIN_ID,
        )

        self.token_network_id = factories.make_address()
        self.token_id = factories.make_address()
        self.token_network_state = TokenNetworkState(self.token_network_id,
                                                     self.token_id)

        self.payment_network_id = factories.make_payment_network_identifier()
        self.payment_network_state = PaymentNetworkState(
            self.payment_network_id,
            [self.token_network_state],
        )

        self.chain_state.identifiers_to_paymentnetworks[
            self.payment_network_id] = self.payment_network_state

        return self.new_channel_with_transaction()
Exemplo n.º 16
0
def test_handle_new_token_network(chain_state, token_network_address):
    token_address = factories.make_address()
    token_network = TokenNetworkState(
        address=token_network_address,
        token_address=token_address,
        network_graph=TokenNetworkGraphState(token_network_address=token_network_address),
    )
    token_network_registry_address = factories.make_address()
    state_change = ContractReceiveNewTokenNetwork(
        token_network_registry_address=token_network_registry_address,
        token_network=token_network,
        transaction_hash=factories.make_transaction_hash(),
        block_hash=factories.make_block_hash(),
        block_number=factories.make_block_number(),
    )
    transition_result = handle_contract_receive_new_token_network(
        chain_state=chain_state, state_change=state_change
    )
    new_chain_state = transition_result.new_state
    token_network_registry = new_chain_state.identifiers_to_tokennetworkregistries[
        token_network_registry_address
    ]
    assert token_network_registry.address == token_network_registry_address
    assert not transition_result.events
    assert get_networks(
        chain_state=chain_state,
        token_network_registry_address=token_network_registry_address,
        token_address=token_address,
    ) == (token_network_registry, token_network)
Exemplo n.º 17
0
def test_write_read_log() -> None:
    wal = new_wal(state_transition_noop)

    block_number = BlockNumber(1337)
    block_hash = make_block_hash()
    block = Block(block_number=block_number,
                  gas_limit=BlockGasLimit(1),
                  block_hash=block_hash)
    unlocked_amount = TokenAmount(10)
    returned_amount = TokenAmount(5)
    participant = make_address()
    partner = make_address()
    locksroot = make_locksroot()
    contract_receive_unlock = ContractReceiveChannelBatchUnlock(
        transaction_hash=make_transaction_hash(),
        canonical_identifier=make_canonical_identifier(
            token_network_address=make_address()),
        receiver=participant,
        sender=partner,
        locksroot=locksroot,
        unlocked_amount=unlocked_amount,
        returned_tokens=returned_amount,
        block_number=block_number,
        block_hash=block_hash,
    )

    state_changes1 = wal.storage.get_statechanges_by_range(
        RANGE_ALL_STATE_CHANGES)
    count1 = len(state_changes1)

    dispatch(wal, [block])

    state_changes2 = wal.storage.get_statechanges_by_range(
        RANGE_ALL_STATE_CHANGES)
    count2 = len(state_changes2)
    assert count1 + 1 == count2

    dispatch(wal, [contract_receive_unlock])

    state_changes3 = wal.storage.get_statechanges_by_range(
        RANGE_ALL_STATE_CHANGES)
    count3 = len(state_changes3)
    assert count2 + 1 == count3

    result1, result2 = state_changes3[-2:]
    assert isinstance(result1, Block)
    assert result1.block_number == block_number

    assert isinstance(result2, ContractReceiveChannelBatchUnlock)
    assert result2.receiver == participant
    assert result2.sender == partner
    assert result2.locksroot == locksroot
    assert result2.unlocked_amount == unlocked_amount
    assert result2.returned_tokens == returned_amount

    # Make sure state snapshot can only go for corresponding state change ids
    with pytest.raises(sqlite3.IntegrityError):
        wal.storage.write_state_snapshot(State(), StateChangeID(make_ulid()),
                                         1)
Exemplo n.º 18
0
def create_fake_web3_for_block_hash(number_of_blocks: int = 0) -> Tuple[FakeWeb3, Dict[int, Any]]:
    block_to_blockhash = {}
    for block in range(0, number_of_blocks):
        block_to_blockhash[block] = HexBytes(make_block_hash())

    fake_web3 = FakeWeb3(block_to_blockhash)

    return fake_web3, block_to_blockhash
Exemplo n.º 19
0
def test_is_transaction_effect_satisfied(chain_state, token_network_id, netting_channel_state):
    canonical_identifier = netting_channel_state.canonical_identifier
    assert token_network_id == canonical_identifier.token_network_address
    transaction = ContractSendChannelBatchUnlock(
        canonical_identifier=canonical_identifier,
        participant=netting_channel_state.partner_state.address,
        triggered_by_block_hash=make_block_hash(),
    )
    state_change = ContractReceiveChannelBatchUnlock(
        transaction_hash=UNIT_SECRETHASH,
        canonical_identifier=canonical_identifier,
        participant=HOP1,
        partner=HOP2,
        locksroot=EMPTY_MERKLE_ROOT,
        unlocked_amount=0,
        returned_tokens=0,
        block_number=1,
        block_hash=make_block_hash(),
    )
    # unlock for a channel in which this node is not a participant must return False
    assert not is_transaction_effect_satisfied(chain_state, transaction, state_change)

    # now call normally with us being the partner and not the participant
    state_change.partner = netting_channel_state.partner_state.address
    state_change.participant = netting_channel_state.our_state.address
    assert not is_transaction_effect_satisfied(chain_state, transaction, state_change)
    # finally call with us being the participant and not the partner which should check out
    state_change.participant = netting_channel_state.partner_state.address
    state_change.partner = netting_channel_state.our_state.address

    # ContractSendChannelBatchUnlock would only be satisfied if both sides are unlocked
    # and if the channel was cleared
    assert not is_transaction_effect_satisfied(chain_state, transaction, state_change)

    channel_settled = ContractReceiveChannelSettled(
        transaction_hash=bytes(32),
        canonical_identifier=canonical_identifier,
        our_onchain_locksroot=EMPTY_MERKLE_ROOT,
        partner_onchain_locksroot=EMPTY_MERKLE_ROOT,
        block_number=1,
        block_hash=make_block_hash(),
    )

    iteration = state_transition(chain_state=chain_state, state_change=channel_settled)

    assert is_transaction_effect_satisfied(iteration.new_state, transaction, state_change)
Exemplo n.º 20
0
def test_handle_contract_send_channelunlock_already_unlocked():
    """This is a test for the scenario where the onchain unlock has
    already happened when we get to handle our own send unlock
    transaction.

    Regression test for https://github.com/raiden-network/raiden/issues/3152
    """
    channel_identifier = 1
    token_network_identifier = make_address()
    token_address = make_address()
    participant = make_address()
    raiden = MockRaidenService()

    def detail_participants(participant1, participant2, block_identifier, channel_identifier):
        transferred_amount = 1
        locked_amount = 1
        locksroot = make_32bytes()
        balance_hash = hash_balance_data(transferred_amount, locked_amount, locksroot)
        our_details = ParticipantDetails(
            address=raiden.address,
            deposit=5,
            withdrawn=0,
            is_closer=False,
            balance_hash=balance_hash,
            nonce=1,
            locksroot=locksroot,
            locked_amount=locked_amount,
        )

        transferred_amount = 1
        locked_amount = 1
        # Let's mock here that partner locksroot is 0x0
        locksroot = EMPTY_HASH
        balance_hash = hash_balance_data(transferred_amount, locked_amount, locksroot)
        partner_details = ParticipantDetails(
            address=participant,
            deposit=5,
            withdrawn=0,
            is_closer=True,
            balance_hash=balance_hash,
            nonce=1,
            locksroot=locksroot,
            locked_amount=locked_amount,
        )
        return ParticipantsDetails(our_details, partner_details)

    # make sure detail_participants returns partner data with a locksroot of 0x0
    raiden.chain.token_network.detail_participants = detail_participants

    event = ContractSendChannelBatchUnlock(
        token_address=token_address,
        token_network_identifier=token_network_identifier,
        channel_identifier=channel_identifier,
        participant=participant,
        triggered_by_block_hash=make_block_hash(),
    )
    # This should not throw an unrecoverable error
    RaidenEventHandler().on_raiden_event(raiden=raiden, event=event)
Exemplo n.º 21
0
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(
        target_state=state,
        channel_state=channels[0],
        block_number=safe_to_wait,
        block_hash=factories.make_block_hash(),
    )
    assert not events

    events = target.events_for_onchain_secretreveal(
        target_state=state,
        channel_state=channels[0],
        block_number=unsafe_to_wait,
        block_hash=factories.make_block_hash(),
    )

    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(
        target_state=state,
        channel_state=channels[0],
        block_number=unsafe_to_wait,
        block_hash=factories.make_block_hash(),
    ), msg
Exemplo n.º 22
0
def test_channel_cleared_after_our_unlock():
    our_model, _ = create_model(balance=700, merkletree_width=1)
    partner_model, partner_key1 = create_model(balance=700, merkletree_width=0)
    channel_state = create_channel_from_models(our_model, partner_model,
                                               partner_key1)
    block_number = 1
    block_hash = make_block_hash()

    def make_unlock(unlock_end, partner_end):
        batch_unlock = ContractReceiveChannelBatchUnlock(
            transaction_hash=make_transaction_hash(),
            canonical_identifier=channel_state.canonical_identifier,
            participant=partner_end.address,
            partner=unlock_end.address,
            locksroot=unlock_end.balance_proof.locksroot,
            unlocked_amount=10,
            returned_tokens=0,
            block_number=block_number,
            block_hash=block_hash,
        )
        return batch_unlock

    settle_channel = ContractReceiveChannelSettled(
        transaction_hash=make_transaction_hash(),
        canonical_identifier=channel_state.canonical_identifier,
        our_onchain_locksroot=merkleroot(channel_state.our_state.merkletree),
        partner_onchain_locksroot=merkleroot(
            channel_state.partner_state.merkletree),
        block_number=1,
        block_hash=make_block_hash(),
    )

    assert settle_channel.our_onchain_locksroot is not EMPTY_MERKLE_ROOT
    assert settle_channel.partner_onchain_locksroot is EMPTY_MERKLE_ROOT

    iteration = channel.state_transition(channel_state, settle_channel,
                                         block_number, block_hash)

    batch_unlock = make_unlock(channel_state.our_state,
                               channel_state.partner_state)
    iteration = channel.state_transition(iteration.new_state, batch_unlock,
                                         block_number, block_hash)
    msg = "partner did not have any locks in the merkletree, channel should have been cleaned"
    assert iteration.new_state is None, msg
Exemplo n.º 23
0
def chain_state(our_address):
    block_number = BlockNumber(1)

    return ChainState(
        pseudo_random_generator=random.Random(),
        block_number=block_number,
        block_hash=factories.make_block_hash(),
        our_address=our_address,
        chain_id=UNIT_CHAIN_ID,
    )
Exemplo n.º 24
0
    def settle_channel(self, partner):
        channel = self.address_to_channel[partner]

        channel_settled_state_change = ContractReceiveChannelSettled(
            transaction_hash=factories.make_transaction_hash(),
            token_network_identifier=channel.token_network_identifier,
            channel_identifier=channel.identifier,
            block_number=self.block_number + 1,
            block_hash=factories.make_block_hash(),
        )

        node.state_transition(self.chain_state, channel_settled_state_change)
Exemplo n.º 25
0
    def new_channel_with_transaction(self):
        partner_address = self.new_channel()

        channel_new_state_change = ContractReceiveChannelNew(
            transaction_hash=factories.make_transaction_hash(),
            channel_state=self.address_to_channel[partner_address],
            block_number=self.block_number,
            block_hash=factories.make_block_hash(),
        )
        node.state_transition(self.chain_state, channel_new_state_change)

        return partner_address
Exemplo n.º 26
0
def test_is_transaction_expired():
    expiration = 24
    block_number = expiration + 1
    transaction = ContractSendChannelUpdateTransfer(
        expiration=expiration,
        balance_proof=None,
        triggered_by_block_hash=factories.make_block_hash(),
    )
    assert is_transaction_expired(transaction, block_number)
    transaction = ContractSendSecretReveal(
        expiration=expiration,
        secret=factories.UNIT_SECRET,
        triggered_by_block_hash=factories.make_block_hash(),
    )
    assert is_transaction_expired(transaction, block_number)

    transaction = ContractSendSecretReveal(
        expiration=block_number,
        secret=factories.UNIT_SECRET,
        triggered_by_block_hash=factories.make_block_hash(),
    )
    assert not is_transaction_expired(transaction, block_number)
Exemplo n.º 27
0
def setup_storage(db_path):
    storage = SerializedSQLiteStorage(str(db_path), JSONSerializer())
    storage.write_state_change(
        ActionInitChain(
            pseudo_random_generator=random.Random(),
            block_number=1,
            block_hash=factories.make_block_hash(),
            our_address=factories.make_address(),
            chain_id=1,
        ),
        datetime.utcnow().isoformat(timespec='milliseconds'),
    )
    return storage
Exemplo n.º 28
0
def test_is_transaction_effect_satisfied(
    chain_state,
    token_network_state,
    token_network_id,
    netting_channel_state,
):
    transaction = ContractSendChannelBatchUnlock(
        token_address=token_network_state.token_address,
        token_network_identifier=token_network_id,
        channel_identifier=netting_channel_state.identifier,
        participant=HOP2,
        triggered_by_block_hash=make_block_hash(),
    )
    state_change = ContractReceiveChannelBatchUnlock(
        transaction_hash=UNIT_SECRETHASH,
        token_network_identifier=token_network_id,
        participant=HOP1,
        partner=HOP2,
        locksroot=EMPTY_MERKLE_ROOT,
        unlocked_amount=0,
        returned_tokens=0,
        block_number=1,
        block_hash=make_block_hash(),
    )
    # unlock for a channel in which this node is not a participant must return False
    assert not is_transaction_effect_satisfied(chain_state, transaction,
                                               state_change)

    # now call normally with us being the partner and not the participant
    state_change.partner = netting_channel_state.our_state.address
    state_change.participant = netting_channel_state.partner_state.address
    assert not is_transaction_effect_satisfied(chain_state, transaction,
                                               state_change)
    # finally call with us being the participant and not the partner which should check out
    state_change.participant = netting_channel_state.our_state.address
    state_change.partner = netting_channel_state.partner_state.address
    assert is_transaction_effect_satisfied(chain_state, transaction,
                                           state_change)
Exemplo n.º 29
0
def test_update_channel_reveal_timeout():
    pseudo_random_generator = random.Random()
    channel_state = factories.create(
        factories.NettingChannelStateProperties(settle_timeout=500,
                                                reveal_timeout=50))

    invalid_reveal_timeout = 260
    valid_reveal_timeout = 250

    set_reveal_timeout = ActionChannelSetRevealTimeout(
        canonical_identifier=channel_state.canonical_identifier,
        reveal_timeout=invalid_reveal_timeout,
    )

    iteration = channel.state_transition(
        channel_state=channel_state,
        state_change=set_reveal_timeout,
        block_number=1,
        block_hash=make_block_hash(),
        pseudo_random_generator=pseudo_random_generator,
    )

    assert iteration.new_state == channel_state
    assert isinstance(iteration.events[0], EventInvalidActionSetRevealTimeout)

    set_reveal_timeout = ActionChannelSetRevealTimeout(
        canonical_identifier=channel_state.canonical_identifier,
        reveal_timeout=250)

    iteration = channel.state_transition(
        channel_state=channel_state,
        state_change=set_reveal_timeout,
        block_number=1,
        block_hash=make_block_hash(),
        pseudo_random_generator=pseudo_random_generator,
    )

    assert iteration.new_state.reveal_timeout == valid_reveal_timeout
Exemplo n.º 30
0
    def new_channel_with_transaction(self):
        partner_address = self.new_channel()

        channel_new_state_change = ContractReceiveChannelNew(
            transaction_hash=factories.make_transaction_hash(),
            channel_state=self.address_to_channel[partner_address],
            block_number=self.block_number,
            block_hash=factories.make_block_hash(),
        )
        node.state_transition(self.chain_state, channel_new_state_change, None)
        self.chain_state.nodeaddresses_to_networkstates[
            partner_address] = NODE_NETWORK_REACHABLE

        return partner_address