def deploy_monitoring_service( token_deploy_result: Callable[[], Contract], user_deposit_deploy_result: Callable[[], UserDeposit], service_registry_deploy_result: Callable[[], ServiceRegistry], token_network_registry_deploy_result: Callable[[], TokenNetworkRegistry], deploy_client: JSONRPCClient, contract_manager: ContractManager, proxy_manager: ProxyManager, ) -> MonitoringService: token_contract = token_deploy_result() token_network_registry_proxy = token_network_registry_deploy_result() user_deposit_proxy = user_deposit_deploy_result() service_registry_proxy = service_registry_deploy_result() contract, receipt = deploy_client.deploy_single_contract( contract_name=CONTRACT_MONITORING_SERVICE, contract=contract_manager.get_contract(CONTRACT_MONITORING_SERVICE), constructor_parameters=[ token_contract.address, service_registry_proxy.address, user_deposit_proxy.address, token_network_registry_proxy.address, ], ) return proxy_manager.monitoring_service( MonitoringServiceAddress(to_canonical_address(contract.address)), BlockNumber(receipt["blockNumber"]), )
def monitoring_service_address( self, block_identifier: BlockSpecification) -> MonitoringServiceAddress: return MonitoringServiceAddress( to_canonical_address( self.proxy.contract.functions.msc_address().call( block_identifier=block_identifier)))
def __init__( # pylint: disable=too-many-arguments self, web3: Web3, private_key: PrivateKey, db_filename: str, contracts: Dict[str, Contract], sync_start_block: BlockNumber, required_confirmations: BlockTimeout, poll_interval: float, min_reward: int = 0, ): self.web3 = web3 self.chain_id = ChainID(web3.eth.chainId) self.private_key = private_key self.address = private_key_to_address(private_key) self.poll_interval = poll_interval self.service_registry = contracts[CONTRACT_SERVICE_REGISTRY] self.token_network_registry = contracts[ CONTRACT_TOKEN_NETWORK_REGISTRY] web3.middleware_onion.add( construct_sign_and_send_raw_middleware(private_key)) monitoring_contract = contracts[CONTRACT_MONITORING_SERVICE] user_deposit_contract = contracts[CONTRACT_USER_DEPOSIT] self.database = Database( filename=db_filename, chain_id=self.chain_id, registry_address=to_canonical_address( self.token_network_registry.address), receiver=self.address, msc_address=MonitoringServiceAddress( to_canonical_address(monitoring_contract.address)), sync_start_block=sync_start_block, ) ms_state = self.database.load_state() self.context = Context( ms_state=ms_state, database=self.database, web3=self.web3, monitoring_service_contract=monitoring_contract, user_deposit_contract=user_deposit_contract, min_reward=min_reward, required_confirmations=required_confirmations, )
def load_deployment_addresses_from_contracts( contracts: Dict[str, Any]) -> DeploymentAddresses: return DeploymentAddresses( token_network_registry_address=TokenNetworkRegistryAddress( to_canonical_address( contracts[CONTRACT_TOKEN_NETWORK_REGISTRY]["address"])), secret_registry_address=SecretRegistryAddress( to_canonical_address( contracts[CONTRACT_SECRET_REGISTRY]["address"])), user_deposit_address=UserDepositAddress( to_canonical_address(contracts[CONTRACT_USER_DEPOSIT]["address"])), service_registry_address=ServiceRegistryAddress( to_canonical_address( contracts[CONTRACT_SERVICE_REGISTRY]["address"])), monitoring_service_address=MonitoringServiceAddress( to_canonical_address( contracts[CONTRACT_MONITORING_SERVICE]["address"])), one_to_n_address=OneToNAddress( to_canonical_address(contracts[CONTRACT_ONE_TO_N]["address"])), )
def request_monitoring_message(token_network, get_accounts, get_private_key) -> RequestMonitoring: c1, c2 = get_accounts(2) balance_proof_c2 = HashedBalanceProof( channel_identifier=ChannelID(1), token_network_address=TokenNetworkAddress(to_canonical_address(token_network.address)), chain_id=ChainID(61), nonce=Nonce(2), additional_hash="0x%064x" % 0, transferred_amount=TokenAmount(1), locked_amount=TokenAmount(0), locksroot=encode_hex(LOCKSROOT_OF_NO_LOCKS), priv_key=get_private_key(c2), ) return balance_proof_c2.get_request_monitoring( privkey=get_private_key(c1), reward_amount=TokenAmount(1), monitoring_service_contract_address=MonitoringServiceAddress(bytes([11] * 20)), )
from eth_utils import keccak from raiden.constants import EMPTY_SIGNATURE, UINT64_MAX, UINT256_MAX from raiden.messages.healthcheck import Ping from raiden.messages.monitoring_service import RequestMonitoring, SignedBlindedBalanceProof from raiden.messages.path_finding_service import PFSCapacityUpdate, PFSFeeUpdate from raiden.storage.serialization import DictSerializer from raiden.tests.utils import factories from raiden.tests.utils.tests import fixture_all_combinations from raiden.transfer.mediated_transfer.mediation_fee import FeeScheduleState from raiden.utils.packing import pack_balance_proof, pack_reward_proof, pack_signed_balance_proof from raiden.utils.signer import LocalSigner, recover from raiden.utils.typing import MonitoringServiceAddress, TokenAmount from raiden_contracts.constants import MessageTypeId MSC_ADDRESS = MonitoringServiceAddress(bytes([1] * 20)) PARTNER_PRIVKEY, PARTNER_ADDRESS = factories.make_privkey_address() PRIVKEY, ADDRESS = factories.make_privkey_address() signer = LocalSigner(PRIVKEY) def test_signature(): ping = Ping(nonce=0, current_protocol_version=0, signature=EMPTY_SIGNATURE) ping.sign(signer) assert ping.sender == ADDRESS def test_request_monitoring() -> None: properties = factories.BalanceProofSignedStateProperties( pkey=PARTNER_PRIVKEY) balance_proof = factories.create(properties)
from raiden.utils.typing import MonitoringServiceAddress KEYSTORE_FILE_NAME = "keystore.txt" KEYSTORE_PASSWORD = "******" TEST_MSC_ADDRESS = MonitoringServiceAddress(b"9" * 20)
def test_first_allowed_monitoring( web3: Web3, monitoring_service_contract, wait_for_blocks, service_registry, monitoring_service: MonitoringService, request_collector: RequestCollector, deposit_to_udc, create_channel, token_network, get_accounts, get_private_key, ): # pylint: disable=too-many-arguments,too-many-locals,protected-access query = create_ms_contract_events_query(web3, monitoring_service_contract.address) c1, c2 = get_accounts(2) # add deposit for c1 node_deposit = 10 deposit_to_udc(c1, node_deposit) assert service_registry.functions.hasValidRegistration(monitoring_service.address).call() # each client does a transfer channel_id = create_channel(c1, c2, settle_timeout=10)[0] shared_bp_args = dict( channel_identifier=channel_id, token_network_address=decode_hex(token_network.address), chain_id=monitoring_service.chain_id, additional_hash="0x%064x" % 0, locked_amount=TokenAmount(0), locksroot=encode_hex(LOCKSROOT_OF_NO_LOCKS), ) transferred_c1 = 5 balance_proof_c1 = HashedBalanceProof( nonce=Nonce(1), transferred_amount=transferred_c1, priv_key=get_private_key(c1), **shared_bp_args, ) transferred_c2 = 6 balance_proof_c2 = HashedBalanceProof( nonce=Nonce(2), transferred_amount=transferred_c2, priv_key=get_private_key(c2), **shared_bp_args, ) monitoring_service._process_new_blocks(web3.eth.blockNumber) assert len(monitoring_service.context.database.get_token_network_addresses()) > 0 # c1 asks MS to monitor the channel reward_amount = TokenAmount(1) request_monitoring = balance_proof_c2.get_request_monitoring( privkey=get_private_key(c1), reward_amount=reward_amount, monitoring_service_contract_address=MonitoringServiceAddress( to_canonical_address(monitoring_service_contract.address) ), ) request_collector.on_monitor_request(request_monitoring) # c2 closes the channel token_network.functions.closeChannel( channel_id, c1, c2, balance_proof_c1.balance_hash, balance_proof_c1.nonce, balance_proof_c1.additional_hash, balance_proof_c1.signature, balance_proof_c1.get_counter_signature(get_private_key(c2)), ).transact({"from": c2}) monitoring_service._process_new_blocks(web3.eth.blockNumber) triggered_events = monitoring_service.database.get_scheduled_events( max_trigger_block=BlockNumber(web3.eth.blockNumber + 10) ) assert len(triggered_events) == 1 monitor_trigger = triggered_events[0] channel = monitoring_service.database.get_channel( token_network_address=TokenNetworkAddress(to_canonical_address(token_network.address)), channel_id=channel_id, ) assert channel # Calling monitor too early must fail. To test this, we call it two block # before the trigger block. # This should be only one block before, but we trigger one block too late # to work around parity's gas estimation. See # https://github.com/raiden-network/raiden-services/pull/728 wait_for_blocks(monitor_trigger.trigger_block_number - web3.eth.blockNumber - 2) handle_event(monitor_trigger.event, monitoring_service.context) assert [e.event for e in query()] == [] # If our `monitor` call fails, we won't try again. Force a retry in this # test by clearing monitor_tx_hash. channel.monitor_tx_hash = None monitoring_service.database.upsert_channel(channel) # Now we can try again. The first try mined a new block, so now we're one # block further and `monitor` should succeed. handle_event(monitor_trigger.event, monitoring_service.context) assert [e.event for e in query()] == [MonitoringServiceEvent.NEW_BALANCE_PROOF_RECEIVED]
def test_e2e( # pylint: disable=too-many-arguments,too-many-locals web3, monitoring_service_contract, user_deposit_contract, wait_for_blocks, service_registry, monitoring_service: MonitoringService, request_collector: RequestCollector, deposit_to_udc, create_channel, token_network, get_accounts, get_private_key, ): """Test complete message lifecycle 1) client opens channel & submits monitoring request 2) other client closes channel 3) MS registers channelClose event 4) MS calls monitoring contract update 5) wait for channel settle 6) MS claims the reward """ query = create_ms_contract_events_query(web3, monitoring_service_contract.address) initial_balance = user_deposit_contract.functions.balances(monitoring_service.address).call() c1, c2 = get_accounts(2) # add deposit for c1 node_deposit = 10 deposit_to_udc(c1, node_deposit) assert service_registry.functions.hasValidRegistration(monitoring_service.address).call() # each client does a transfer channel_id = create_channel(c1, c2, settle_timeout=5)[0] shared_bp_args = dict( channel_identifier=channel_id, token_network_address=decode_hex(token_network.address), chain_id=monitoring_service.chain_id, additional_hash="0x%064x" % 0, locked_amount=TokenAmount(0), locksroot=encode_hex(LOCKSROOT_OF_NO_LOCKS), ) transferred_c1 = 5 balance_proof_c1 = HashedBalanceProof( nonce=Nonce(1), transferred_amount=transferred_c1, priv_key=get_private_key(c1), **shared_bp_args, ) transferred_c2 = 6 balance_proof_c2 = HashedBalanceProof( nonce=Nonce(2), transferred_amount=transferred_c2, priv_key=get_private_key(c2), **shared_bp_args, ) ms_greenlet = gevent.spawn(monitoring_service.start) # need to wait here till the MS has some time to react gevent.sleep(0.01) assert len(monitoring_service.context.database.get_token_network_addresses()) > 0 # c1 asks MS to monitor the channel reward_amount = TokenAmount(1) request_monitoring = balance_proof_c2.get_request_monitoring( privkey=get_private_key(c1), reward_amount=reward_amount, monitoring_service_contract_address=MonitoringServiceAddress( to_canonical_address(monitoring_service_contract.address) ), ) request_collector.on_monitor_request(request_monitoring) # c2 closes the channel token_network.functions.closeChannel( channel_id, c1, c2, balance_proof_c1.balance_hash, balance_proof_c1.nonce, balance_proof_c1.additional_hash, balance_proof_c1.signature, balance_proof_c1.get_counter_signature(get_private_key(c2)), ).transact({"from": c2}) # Wait until the MS reacts, which it does after giving the client some time # to update the channel itself. wait_for_blocks(2) # 1 block for close + 1 block for triggering the event # Now give the monitoring service a chance to submit the missing BP gevent.sleep(0.01) assert [e.event for e in query()] == [MonitoringServiceEvent.NEW_BALANCE_PROOF_RECEIVED] # wait for settle timeout # timeout is 5, but we've already waited 3 blocks before. Additionally one block is # added to handle parity running gas estimation on current instead of next. wait_for_blocks(3) # Let the MS claim its reward gevent.sleep(0.01) assert [e.event for e in query()] == [ MonitoringServiceEvent.NEW_BALANCE_PROOF_RECEIVED, MonitoringServiceEvent.REWARD_CLAIMED, ] final_balance = user_deposit_contract.functions.balances(monitoring_service.address).call() assert final_balance == (initial_balance + reward_amount) ms_greenlet.kill()
def deploy_smoketest_contracts( client: JSONRPCClient, chain_id: ChainID, contract_manager: ContractManager, token_address: AddressHex, ) -> Dict[str, Address]: if client.eth_node is EthClient.GETH: client.web3.geth.personal.unlockAccount(client.web3.eth.accounts[0], DEFAULT_PASSPHRASE) elif client.eth_node is EthClient.PARITY: client.web3.parity.personal.unlockAccount(client.web3.eth.accounts[0], DEFAULT_PASSPHRASE) contract_proxy, _ = client.deploy_single_contract( contract_name=CONTRACT_SECRET_REGISTRY, contract=contract_manager.get_contract(CONTRACT_SECRET_REGISTRY), constructor_parameters=None, ) secret_registry_address = Address( to_canonical_address(contract_proxy.address)) secret_registry_constructor_arguments = ( to_checksum_address(secret_registry_address), chain_id, TEST_SETTLE_TIMEOUT_MIN, TEST_SETTLE_TIMEOUT_MAX, UINT256_MAX, ) contract_proxy, _ = client.deploy_single_contract( contract_name=CONTRACT_TOKEN_NETWORK_REGISTRY, contract=contract_manager.get_contract( CONTRACT_TOKEN_NETWORK_REGISTRY), constructor_parameters=secret_registry_constructor_arguments, ) token_network_registry_address = Address( to_canonical_address(contract_proxy.address)) service_registry_constructor_arguments = ( token_address, EMPTY_ADDRESS, int(500e18), 6, 5, 180 * SECONDS_PER_DAY, 1000, 200 * SECONDS_PER_DAY, ) service_registry_contract, _ = client.deploy_single_contract( contract_name=CONTRACT_SERVICE_REGISTRY, contract=contract_manager.get_contract(CONTRACT_SERVICE_REGISTRY), constructor_parameters=service_registry_constructor_arguments, ) service_registry_address = Address( to_canonical_address(service_registry_contract.address)) user_deposit_contract, _ = client.deploy_single_contract( contract_name=CONTRACT_USER_DEPOSIT, contract=contract_manager.get_contract(CONTRACT_USER_DEPOSIT), constructor_parameters=(token_address, UINT256_MAX), ) user_deposit_address = Address( to_canonical_address(user_deposit_contract.address)) monitoring_service_contract, _ = client.deploy_single_contract( contract_name=CONTRACT_MONITORING_SERVICE, contract=contract_manager.get_contract(CONTRACT_MONITORING_SERVICE), constructor_parameters=( token_address, service_registry_address, user_deposit_address, token_network_registry_address, ), ) monitoring_service_address = Address( to_canonical_address(monitoring_service_contract.address)) one_to_n_contract, _ = client.deploy_single_contract( contract_name=CONTRACT_ONE_TO_N, contract=contract_manager.get_contract(CONTRACT_ONE_TO_N), constructor_parameters=(user_deposit_address, chain_id, service_registry_address), ) one_to_n_address = Address(to_canonical_address(one_to_n_contract.address)) proxy_manager = ProxyManager( rpc_client=client, contract_manager=contract_manager, metadata=ProxyManagerMetadata( token_network_registry_deployed_at=GENESIS_BLOCK_NUMBER, filters_start_at=GENESIS_BLOCK_NUMBER, ), ) user_deposit_proxy = UserDeposit( jsonrpc_client=client, user_deposit_address=UserDepositAddress( to_canonical_address(user_deposit_contract.address)), contract_manager=contract_manager, proxy_manager=proxy_manager, block_identifier=BLOCK_ID_LATEST, ) transaction_hash = user_deposit_proxy.init( monitoring_service_address=MonitoringServiceAddress( monitoring_service_address), one_to_n_address=OneToNAddress(one_to_n_address), given_block_identifier=BLOCK_ID_LATEST, ) assert is_tx_hash_bytes(transaction_hash) addresses = { CONTRACT_SECRET_REGISTRY: secret_registry_address, CONTRACT_TOKEN_NETWORK_REGISTRY: token_network_registry_address, CONTRACT_SERVICE_REGISTRY: service_registry_address, CONTRACT_USER_DEPOSIT: user_deposit_address, CONTRACT_MONITORING_SERVICE: monitoring_service_address, CONTRACT_ONE_TO_N: one_to_n_address, } return addresses
def deploy_smoketest_contracts( client: JSONRPCClient, proxy_manager: ProxyManager, chain_id: ChainID, contract_manager: ContractManager, token_address: AddressHex, ) -> Dict[str, Address]: client.web3.personal.unlockAccount(client.web3.eth.accounts[0], DEFAULT_PASSPHRASE) secret_registry_address = deploy_contract_web3( contract_name=CONTRACT_SECRET_REGISTRY, deploy_client=client, contract_manager=contract_manager, ) constructor_arguments = [ to_checksum_address(secret_registry_address), chain_id, TEST_SETTLE_TIMEOUT_MIN, TEST_SETTLE_TIMEOUT_MAX, UINT256_MAX, ] token_network_registry_address = deploy_contract_web3( contract_name=CONTRACT_TOKEN_NETWORK_REGISTRY, deploy_client=client, contract_manager=contract_manager, constructor_arguments=constructor_arguments, ) addresses = { CONTRACT_SECRET_REGISTRY: secret_registry_address, CONTRACT_TOKEN_NETWORK_REGISTRY: token_network_registry_address, } service_registry_address = deploy_contract_web3( contract_name=CONTRACT_SERVICE_REGISTRY, deploy_client=client, contract_manager=contract_manager, constructor_arguments=( token_address, EMPTY_ADDRESS, int(500e18), 6, 5, 180 * SECONDS_PER_DAY, 1000, 200 * SECONDS_PER_DAY, ), ) addresses[CONTRACT_SERVICE_REGISTRY] = service_registry_address user_deposit_address = deploy_contract_web3( contract_name=CONTRACT_USER_DEPOSIT, deploy_client=client, contract_manager=contract_manager, constructor_arguments=(token_address, UINT256_MAX), ) addresses[CONTRACT_USER_DEPOSIT] = user_deposit_address monitoring_service_address = deploy_contract_web3( contract_name=CONTRACT_MONITORING_SERVICE, deploy_client=client, contract_manager=contract_manager, constructor_arguments=( token_address, service_registry_address, user_deposit_address, token_network_registry_address, ), ) addresses[CONTRACT_MONITORING_SERVICE] = monitoring_service_address one_to_n_address = deploy_contract_web3( contract_name=CONTRACT_ONE_TO_N, deploy_client=client, contract_manager=contract_manager, constructor_arguments=(user_deposit_address, chain_id, service_registry_address), ) addresses[CONTRACT_ONE_TO_N] = one_to_n_address user_deposit_proxy = proxy_manager.user_deposit(UserDepositAddress(user_deposit_address)) user_deposit_proxy.init( monitoring_service_address=MonitoringServiceAddress(monitoring_service_address), one_to_n_address=OneToNAddress(one_to_n_address), given_block_identifier="latest", ) return addresses