Exemplo n.º 1
0
def test_balance_proof_invalid_attributes():
    invalid_nonces = [-10, 0, UINT64_MAX + 1]
    invalid_transferred_amounts = [-1, UINT256_MAX + 1]
    invalid_locksroots = [urandom(31), urandom(33)]
    invalid_signatures = [urandom(64), urandom(66)]

    properties_unsigned = factories.BalanceProofProperties()
    properties_signed = factories.BalanceProofSignedStateProperties(
        signature=urandom(64))

    for properties in (properties_unsigned, properties_signed):
        for nonce in invalid_nonces:
            with pytest.raises(ValueError):
                factories.create(factories.replace(properties, nonce=nonce))

        for amount in invalid_transferred_amounts:
            with pytest.raises(ValueError):
                factories.create(
                    factories.replace(properties, transferred_amount=amount))

        for locksroot in invalid_locksroots:
            with pytest.raises(ValueError):
                factories.create(
                    factories.replace(properties, locksroot=locksroot))

    for signature in invalid_signatures:
        with pytest.raises(ValueError):
            factories.create(
                factories.replace(properties_signed, signature=signature))
Exemplo n.º 2
0
def test_get_secret():
    secret1 = factories.make_secret()
    secret2 = factories.make_secret()
    secrethash3 = factories.make_keccak_hash()
    secrethash4 = factories.make_keccak_hash()

    lock_state = HashTimeLockState(amount=10,
                                   expiration=10,
                                   secrethash=factories.UNIT_SECRETHASH)
    end_state = factories.create(factories.NettingChannelEndStateProperties())
    end_state = factories.replace(
        end_state,
        secrethashes_to_lockedlocks={secrethash3: lock_state},
        secrethashes_to_unlockedlocks={
            sha3(secret1): UnlockPartialProofState(lock=lock_state,
                                                   secret=secret1)
        },
        secrethashes_to_onchain_unlockedlocks={
            sha3(secret2): UnlockPartialProofState(lock=lock_state,
                                                   secret=secret2)
        },
    )

    assert get_secret(
        end_state,
        sha3(secret1)) == secret1  # known secret from offchain unlock
    assert get_secret(
        end_state,
        sha3(secret2)) == secret2  # known secret from offchain unlock
    assert get_secret(end_state,
                      secrethash3) is None  # known lock but not unlocked yet
    assert get_secret(end_state, secrethash4) is None  # unknown secrethash
Exemplo n.º 3
0
def test_events_for_onchain_secretreveal_with_unfit_channels():
    settle = factories.TransactionExecutionStatusProperties()
    settled = factories.create(
        factories.NettingChannelStateProperties(settle_transaction=settle))
    secret = factories.UNIT_SECRET
    block_hash = factories.make_block_hash()

    events = events_for_onchain_secretreveal(settled, secret, 10, block_hash)
    assert not events, "Secret reveal event should not be generated for settled channel"

    settle = factories.replace(settle,
                               result=TransactionExecutionStatus.FAILURE)
    unusable = factories.create(
        factories.NettingChannelStateProperties(settle_transaction=settle))

    events = events_for_onchain_secretreveal(unusable, secret, 10, block_hash)
    assert not events, "Secret reveal event should not be generated for unusable channel."
Exemplo n.º 4
0
 def update(self, amount, lock):
     self._pending_locks = channel.compute_locks_with(self._pending_locks, lock)
     if self.properties:
         self.properties = factories.replace(
             self.properties,
             locked_amount=self.properties.locked_amount + amount,
             locksroot=compute_locksroot(self._pending_locks),
             nonce=self.properties.nonce + 1,
         )
     else:
         self.properties = factories.BalanceProofProperties(
             transferred_amount=0,
             locked_amount=amount,
             nonce=1,
             locksroot=compute_locksroot(self._pending_locks),
             canonical_identifier=self._canonical_identifier,
         )
Exemplo n.º 5
0
 def update(self, amount, lockhash):
     self._merkletree = channel.compute_merkletree_with(
         self._merkletree, lockhash)
     if self.properties:
         self.properties = factories.replace(
             self.properties,
             locked_amount=self.properties.locked_amount + amount,
             locksroot=merkleroot(self._merkletree),
             nonce=self.properties.nonce + 1,
         )
     else:
         self.properties = factories.BalanceProofProperties(
             transferred_amount=0,
             locked_amount=amount,
             nonce=1,
             locksroot=merkleroot(self._merkletree),
             canonical_identifier=self._canonical_identifier,
         )
Exemplo n.º 6
0
    def make_mediated_transfer_state_change(
            transfer_amount: int, allocated_fee_amount: FeeAmount,
            channel_capacity: TokenAmount) -> TransitionResult:
        transfer = factories.replace(factories.UNIT_TRANSFER_DESCRIPTION,
                                     amount=transfer_amount)
        channel_set = factories.make_channel_set_from_amounts(
            [channel_capacity])
        mediating_channel = channel_set.channels[0]
        pnrg = random.Random()

        nodeaddresses_to_networkstates = {
            mediating_channel.partner_state.address: NetworkState.REACHABLE
        }

        addresses_to_channel = {
            (
                UNIT_TOKEN_NETWORK_ADDRESS,
                mediating_channel.partner_state.address,
            ):
            mediating_channel
        }

        routes = [[
            factories.UNIT_OUR_ADDRESS,
            mediating_channel.partner_state.address,
            factories.UNIT_TRANSFER_TARGET,
        ]]

        init_action = factories.initiator_make_init_action(
            channels=channel_set,
            routes=routes,
            transfer=transfer,
            estimated_fee=allocated_fee_amount,
        )
        return initiator_manager.handle_init(
            payment_state=None,
            state_change=init_action,
            addresses_to_channel=addresses_to_channel,
            nodeaddresses_to_networkstates=nodeaddresses_to_networkstates,
            pseudo_random_generator=pnrg,
            block_number=BlockNumber(1),
        )
Exemplo n.º 7
0
def test_request_monitoring() -> None:
    properties = factories.BalanceProofSignedStateProperties(
        pkey=PARTNER_PRIVKEY)
    balance_proof = factories.create(properties)
    partner_signed_balance_proof = SignedBlindedBalanceProof.from_balance_proof_signed_state(
        balance_proof)
    request_monitoring = RequestMonitoring(
        balance_proof=partner_signed_balance_proof,
        non_closing_participant=ADDRESS,
        reward_amount=TokenAmount(55),
        signature=EMPTY_SIGNATURE,
        monitoring_service_contract_address=MSC_ADDRESS,
    )
    assert request_monitoring
    request_monitoring.sign(signer)
    as_dict = DictSerializer.serialize(request_monitoring)
    assert DictSerializer.deserialize(as_dict) == request_monitoring
    # RequestMonitoring can be created directly from BalanceProofSignedState
    direct_created = RequestMonitoring.from_balance_proof_signed_state(
        balance_proof=balance_proof,
        non_closing_participant=ADDRESS,
        reward_amount=TokenAmount(55),
        monitoring_service_contract_address=MSC_ADDRESS,
    )
    # `direct_created` is not signed while request_monitoring is
    assert DictSerializer().serialize(
        direct_created) != DictSerializer().serialize(request_monitoring)

    direct_created.sign(signer)
    # Instances created from same balance proof are equal
    assert direct_created == request_monitoring
    other_balance_proof = factories.create(
        factories.replace(properties, message_hash=keccak(b"2")))
    other_instance = RequestMonitoring.from_balance_proof_signed_state(
        balance_proof=other_balance_proof,
        non_closing_participant=ADDRESS,
        reward_amount=TokenAmount(55),
        monitoring_service_contract_address=MSC_ADDRESS,
    )
    other_instance.sign(signer)
    # different balance proof ==> non-equality
    assert other_instance != request_monitoring

    # test signature verification
    assert request_monitoring.non_closing_signature
    reward_proof_data = pack_reward_proof(
        token_network_address=request_monitoring.balance_proof.
        token_network_address,
        chain_id=request_monitoring.balance_proof.chain_id,
        reward_amount=request_monitoring.reward_amount,
        monitoring_service_contract_address=MSC_ADDRESS,
        non_closing_participant=ADDRESS,
        non_closing_signature=request_monitoring.non_closing_signature,
    )

    assert request_monitoring.reward_proof_signature
    assert recover(reward_proof_data,
                   request_monitoring.reward_proof_signature) == ADDRESS

    blinded_data = pack_signed_balance_proof(
        msg_type=MessageTypeId.BALANCE_PROOF_UPDATE,
        nonce=request_monitoring.balance_proof.nonce,
        balance_hash=request_monitoring.balance_proof.balance_hash,
        additional_hash=request_monitoring.balance_proof.additional_hash,
        canonical_identifier=factories.make_canonical_identifier(
            chain_identifier=request_monitoring.balance_proof.chain_id,
            token_network_address=request_monitoring.balance_proof.
            token_network_address,
            channel_identifier=request_monitoring.balance_proof.
            channel_identifier,
        ),
        partner_signature=request_monitoring.balance_proof.signature,
    )
    assert recover(blinded_data,
                   request_monitoring.non_closing_signature) == ADDRESS

    balance_proof_data = pack_balance_proof(
        nonce=request_monitoring.balance_proof.nonce,
        balance_hash=request_monitoring.balance_proof.balance_hash,
        additional_hash=request_monitoring.balance_proof.additional_hash,
        canonical_identifier=factories.make_canonical_identifier(
            chain_identifier=request_monitoring.balance_proof.chain_id,
            token_network_address=request_monitoring.balance_proof.
            token_network_address,
            channel_identifier=request_monitoring.balance_proof.
            channel_identifier,
        ),
    )
    assert (recover(
        balance_proof_data,
        request_monitoring.balance_proof.signature) == PARTNER_ADDRESS)

    assert request_monitoring.verify_request_monitoring(
        PARTNER_ADDRESS, ADDRESS)
Exemplo n.º 8
0
def test_request_monitoring():
    properties = factories.BalanceProofSignedStateProperties(
        pkey=PARTNER_PRIVKEY)
    balance_proof = factories.create(properties)
    partner_signed_balance_proof = SignedBlindedBalanceProof.from_balance_proof_signed_state(
        balance_proof)
    request_monitoring = RequestMonitoring(
        onchain_balance_proof=partner_signed_balance_proof, reward_amount=55)
    assert request_monitoring
    with pytest.raises(ValueError):
        request_monitoring.to_dict()
    request_monitoring.sign(signer)
    as_dict = request_monitoring.to_dict()
    assert RequestMonitoring.from_dict(as_dict) == request_monitoring
    request_monitoring_packed = request_monitoring.packed()
    request_monitoring.pack(request_monitoring_packed)
    assert RequestMonitoring.unpack(
        request_monitoring_packed) == request_monitoring
    # RequestMonitoring can be created directly from BalanceProofSignedState
    direct_created = RequestMonitoring.from_balance_proof_signed_state(
        balance_proof, reward_amount=55)
    with pytest.raises(ValueError):
        # equality test uses `validated` packed format
        assert direct_created == request_monitoring

    direct_created.sign(signer)
    # Instances created from same balance proof are equal
    assert direct_created == request_monitoring
    other_balance_proof = factories.create(
        factories.replace(properties, message_hash=sha3(b"2")))
    other_instance = RequestMonitoring.from_balance_proof_signed_state(
        other_balance_proof, reward_amount=55)
    other_instance.sign(signer)
    # different balance proof ==> non-equality
    assert other_instance != request_monitoring

    # test signature verification
    reward_proof_data = pack_reward_proof(
        canonical_identifier=factories.make_canonical_identifier(
            chain_identifier=request_monitoring.balance_proof.chain_id,
            token_network_address=request_monitoring.balance_proof.
            token_network_address,
            channel_identifier=request_monitoring.balance_proof.
            channel_identifier,
        ),
        reward_amount=request_monitoring.reward_amount,
        nonce=request_monitoring.balance_proof.nonce,
    )

    assert recover(reward_proof_data,
                   request_monitoring.reward_proof_signature) == ADDRESS

    blinded_data = pack_balance_proof_update(
        nonce=request_monitoring.balance_proof.nonce,
        balance_hash=request_monitoring.balance_proof.balance_hash,
        additional_hash=request_monitoring.balance_proof.additional_hash,
        canonical_identifier=factories.make_canonical_identifier(
            chain_identifier=request_monitoring.balance_proof.chain_id,
            token_network_address=request_monitoring.balance_proof.
            token_network_address,
            channel_identifier=request_monitoring.balance_proof.
            channel_identifier,
        ),
        partner_signature=request_monitoring.balance_proof.signature,
    )
    assert recover(blinded_data,
                   request_monitoring.non_closing_signature) == ADDRESS

    balance_proof_data = pack_balance_proof(
        nonce=request_monitoring.balance_proof.nonce,
        balance_hash=request_monitoring.balance_proof.balance_hash,
        additional_hash=request_monitoring.balance_proof.additional_hash,
        canonical_identifier=factories.make_canonical_identifier(
            chain_identifier=request_monitoring.balance_proof.chain_id,
            token_network_address=request_monitoring.balance_proof.
            token_network_address,
            channel_identifier=request_monitoring.balance_proof.
            channel_identifier,
        ),
    )
    assert (recover(
        balance_proof_data,
        request_monitoring.balance_proof.signature) == PARTNER_ADDRESS)

    assert request_monitoring.verify_request_monitoring(
        PARTNER_ADDRESS, ADDRESS)
Exemplo n.º 9
0
def test_message_handler():
    """
    Test for MessageHandler.on_message and the different methods it dispatches into.
    Each of them results in a call to a RaidenService method, which is checked with a Mock.
    """

    our_address = factories.make_address()
    sender_privkey, sender = factories.make_privkey_address()
    signer = LocalSigner(sender_privkey)
    message_handler = MessageHandler()
    mock_raiden = Mock(
        address=our_address, default_secret_registry=Mock(is_secret_registered=lambda **_: False)
    )

    properties = factories.LockedTransferProperties(sender=sender, pkey=sender_privkey)
    locked_transfer = factories.create(properties)
    message_handler.on_message(mock_raiden, locked_transfer)
    assert_method_call(mock_raiden, "mediate_mediated_transfer", locked_transfer)

    locked_transfer_for_us = factories.create(factories.replace(properties, target=our_address))
    message_handler.on_message(mock_raiden, locked_transfer_for_us)
    assert_method_call(mock_raiden, "target_mediated_transfer", locked_transfer_for_us)

    mock_raiden.default_secret_registry.is_secret_registered = lambda **_: True
    message_handler.on_message(mock_raiden, locked_transfer)
    assert not mock_raiden.mediate_mediated_transfer.called
    assert not mock_raiden.target_mediated_transfer.called
    mock_raiden.default_secret_registry.is_secret_registered = lambda **_: False

    params = dict(
        payment_identifier=13, amount=14, expiration=15, secrethash=factories.UNIT_SECRETHASH
    )
    secret_request = SecretRequest(
        message_identifier=16, signature=factories.EMPTY_SIGNATURE, **params
    )
    secret_request.sign(signer)
    receive = ReceiveSecretRequest(sender=sender, **params)
    message_handler.on_message(mock_raiden, secret_request)
    assert_method_call(mock_raiden, "handle_and_track_state_changes", [receive])

    secret = factories.make_secret()
    reveal_secret = RevealSecret(
        message_identifier=100, signature=factories.EMPTY_SIGNATURE, secret=secret
    )
    reveal_secret.sign(signer)
    receive = ReceiveSecretReveal(sender=sender, secret=secret)
    message_handler.on_message(mock_raiden, reveal_secret)
    assert_method_call(mock_raiden, "handle_and_track_state_changes", [receive])

    properties: factories.UnlockProperties = factories.create_properties(
        factories.UnlockProperties()
    )
    unlock = factories.create(properties)
    unlock.sign(signer)
    balance_proof = factories.make_signed_balance_proof_from_unsigned(
        factories.create(properties.balance_proof), signer, unlock.message_hash
    )
    receive = ReceiveUnlock(
        message_identifier=properties.message_identifier,
        secret=properties.secret,
        balance_proof=balance_proof,
        sender=sender,
    )
    message_handler.on_message(mock_raiden, unlock)
    assert_method_call(mock_raiden, "handle_and_track_state_changes", [receive])

    properties: factories.LockExpiredProperties = factories.create_properties(
        factories.LockExpiredProperties()
    )
    lock_expired = factories.create(properties)
    lock_expired.sign(signer)
    balance_proof = factories.make_signed_balance_proof_from_unsigned(
        factories.create(properties.balance_proof), signer, lock_expired.message_hash
    )
    receive = ReceiveLockExpired(
        balance_proof=balance_proof,
        message_identifier=properties.message_identifier,
        secrethash=properties.secrethash,  # pylint: disable=no-member
        sender=sender,
    )
    message_handler.on_message(mock_raiden, lock_expired)
    assert_method_call(mock_raiden, "handle_and_track_state_changes", [receive])

    delivered = Delivered(delivered_message_identifier=1, signature=factories.EMPTY_SIGNATURE)
    delivered.sign(signer)
    receive = ReceiveDelivered(message_identifier=1, sender=sender)
    message_handler.on_message(mock_raiden, delivered)
    assert_method_call(mock_raiden, "handle_and_track_state_changes", [receive])

    processed = Processed(message_identifier=42, signature=factories.EMPTY_SIGNATURE)
    processed.sign(signer)
    receive = ReceiveProcessed(message_identifier=42, sender=sender)
    message_handler.on_message(mock_raiden, processed)
    assert_method_call(mock_raiden, "handle_and_track_state_changes", [receive])