Пример #1
0
async def test_proxy_peer_requests(request, event_bus, other_event_bus,
                                   event_loop, chaindb_20, client_and_server):
    server_event_bus = event_bus
    client_event_bus = other_event_bus
    client_peer, server_peer = client_and_server

    client_peer_pool = MockPeerPoolWithConnectedPeers(
        [client_peer], event_bus=client_event_bus)
    server_peer_pool = MockPeerPoolWithConnectedPeers(
        [server_peer], event_bus=server_event_bus)

    async with AsyncExitStack() as stack:
        await stack.enter_async_context(
            run_peer_pool_event_server(client_event_bus,
                                       client_peer_pool,
                                       handler_type=ETHPeerPoolEventServer))

        await stack.enter_async_context(
            run_peer_pool_event_server(server_event_bus,
                                       server_peer_pool,
                                       handler_type=ETHPeerPoolEventServer))

        await stack.enter_async_context(
            background_asyncio_service(
                ETHRequestServer(server_event_bus,
                                 TO_NETWORKING_BROADCAST_CONFIG,
                                 AsyncChainDB(chaindb_20.db))))

        client_proxy_peer_pool = ETHProxyPeerPool(
            client_event_bus, TO_NETWORKING_BROADCAST_CONFIG)
        await stack.enter_async_context(
            background_asyncio_service(client_proxy_peer_pool))

        proxy_peer_pool = ETHProxyPeerPool(server_event_bus,
                                           TO_NETWORKING_BROADCAST_CONFIG)
        await stack.enter_async_context(
            background_asyncio_service(proxy_peer_pool))

        proxy_peer = await client_proxy_peer_pool.ensure_proxy_peer(
            client_peer.session)

        headers = await proxy_peer.eth_api.get_block_headers(0, 1, 0, False)

        assert len(headers) == 1
        block_header = headers[0]
        assert block_header.block_number == 0

        receipts = await proxy_peer.eth_api.get_receipts(headers)
        assert len(receipts) == 1
        receipt = receipts[0]
        assert receipt[1][0] == block_header.receipt_root

        block_bundles = await proxy_peer.eth_api.get_block_bodies(headers)
        assert len(block_bundles) == 1
        first_bundle = block_bundles[0]
        assert first_bundle[1][0] == block_header.transaction_root

        node_data = await proxy_peer.eth_api.get_node_data(
            (block_header.state_root, ))
        assert node_data[0][0] == block_header.state_root
Пример #2
0
async def test_proxy_peer_requests_with_timeouts(request, event_bus,
                                                 other_event_bus, event_loop,
                                                 client_and_server):

    server_event_bus = event_bus
    client_event_bus = other_event_bus
    client_peer, server_peer = client_and_server

    client_peer_pool = MockPeerPoolWithConnectedPeers(
        [client_peer], event_bus=client_event_bus)
    server_peer_pool = MockPeerPoolWithConnectedPeers(
        [server_peer], event_bus=server_event_bus)

    async with contextlib.AsyncExitStack() as stack:
        await stack.enter_async_context(
            run_peer_pool_event_server(client_event_bus,
                                       client_peer_pool,
                                       handler_type=ETHPeerPoolEventServer))
        await stack.enter_async_context(
            run_peer_pool_event_server(server_event_bus,
                                       server_peer_pool,
                                       handler_type=ETHPeerPoolEventServer))

        # We just want an ETHRequestServer that doesn't answer us but we still have to run
        # *something* to at least subscribe to the events. Otherwise Lahja's safety check will yell
        # at us for sending requests into the void.
        for event_type in ETHRequestServer(None, None,
                                           None)._subscribed_events:
            server_event_bus.subscribe(event_type, lambda _: None)

        client_proxy_peer_pool = ETHProxyPeerPool(
            client_event_bus, TO_NETWORKING_BROADCAST_CONFIG)
        await stack.enter_async_context(
            background_asyncio_service(client_proxy_peer_pool))

        server_proxy_peer_pool = ETHProxyPeerPool(
            server_event_bus, TO_NETWORKING_BROADCAST_CONFIG)
        await stack.enter_async_context(
            background_asyncio_service(server_proxy_peer_pool))

        proxy_peer = await client_proxy_peer_pool.ensure_proxy_peer(
            client_peer.session)

        with pytest.raises(asyncio.TimeoutError):
            await proxy_peer.eth_api.get_block_headers(0,
                                                       1,
                                                       0,
                                                       False,
                                                       timeout=0.01)

        with pytest.raises(asyncio.TimeoutError):
            await proxy_peer.eth_api.get_receipts((), timeout=0.01)

        with pytest.raises(asyncio.TimeoutError):
            await proxy_peer.eth_api.get_block_bodies((), timeout=0.01)

        with pytest.raises(asyncio.TimeoutError):
            await proxy_peer.eth_api.get_node_data((), timeout=0.01)
Пример #3
0
async def test_requests_when_peer_in_client_vanishs(request, event_bus,
                                                    other_event_bus,
                                                    event_loop, chaindb_20,
                                                    client_and_server):

    server_event_bus = event_bus
    client_event_bus = other_event_bus
    client_peer, server_peer = client_and_server

    client_peer_pool = MockPeerPoolWithConnectedPeers(
        [client_peer], event_bus=client_event_bus)
    server_peer_pool = MockPeerPoolWithConnectedPeers(
        [server_peer], event_bus=server_event_bus)

    async with contextlib.AsyncExitStack() as stack:
        await stack.enter_async_context(
            run_peer_pool_event_server(client_event_bus,
                                       client_peer_pool,
                                       handler_type=ETHPeerPoolEventServer))
        await stack.enter_async_context(
            run_peer_pool_event_server(server_event_bus,
                                       server_peer_pool,
                                       handler_type=ETHPeerPoolEventServer))

        await stack.enter_async_context(
            background_asyncio_service(
                ETHRequestServer(server_event_bus,
                                 TO_NETWORKING_BROADCAST_CONFIG,
                                 MainnetChain.vm_configuration,
                                 AsyncChainDB(chaindb_20.db))))
        client_proxy_peer_pool = ETHProxyPeerPool(
            client_event_bus, TO_NETWORKING_BROADCAST_CONFIG)
        await stack.enter_async_context(
            background_asyncio_service(client_proxy_peer_pool))

        server_proxy_peer_pool = ETHProxyPeerPool(
            server_event_bus, TO_NETWORKING_BROADCAST_CONFIG)
        await stack.enter_async_context(
            background_asyncio_service(server_proxy_peer_pool))

        proxy_peer = await client_proxy_peer_pool.ensure_proxy_peer(
            client_peer.session)

        # We remove the peer from the client and assume to see PeerConnectionLost exceptions raised
        client_peer_pool.connected_nodes.pop(client_peer.session)

        with pytest.raises(PeerConnectionLost):
            await proxy_peer.eth_api.get_block_headers(0, 1, 0, False)

        with pytest.raises(PeerConnectionLost):
            await proxy_peer.eth_api.get_receipts(())

        with pytest.raises(PeerConnectionLost):
            await proxy_peer.eth_api.get_block_bodies(())

        with pytest.raises(PeerConnectionLost):
            await proxy_peer.eth_api.get_node_data(())
Пример #4
0
async def two_connected_tx_pools(event_bus, other_event_bus, event_loop,
                                 funded_address_private_key,
                                 chain_with_block_validation, tx_validator,
                                 client_and_server):

    alice_event_bus = event_bus
    bob_event_bus = other_event_bus
    bob, alice = client_and_server

    bob_peer_pool = MockPeerPoolWithConnectedPeers([bob],
                                                   event_bus=bob_event_bus)
    alice_peer_pool = MockPeerPoolWithConnectedPeers([alice],
                                                     event_bus=alice_event_bus)

    async with contextlib.AsyncExitStack() as stack:
        await stack.enter_async_context(
            run_peer_pool_event_server(bob_event_bus,
                                       bob_peer_pool,
                                       handler_type=ETHPeerPoolEventServer))

        await stack.enter_async_context(
            run_peer_pool_event_server(alice_event_bus,
                                       alice_peer_pool,
                                       handler_type=ETHPeerPoolEventServer))

        bob_proxy_peer_pool = ETHProxyPeerPool(bob_event_bus,
                                               TO_NETWORKING_BROADCAST_CONFIG)
        await stack.enter_async_context(
            background_asyncio_service(bob_proxy_peer_pool))

        alice_proxy_peer_pool = ETHProxyPeerPool(
            alice_event_bus, TO_NETWORKING_BROADCAST_CONFIG)
        await stack.enter_async_context(
            background_asyncio_service(alice_proxy_peer_pool))

        alice_tx_pool = TxPool(
            alice_event_bus,
            alice_proxy_peer_pool,
            tx_validator,
        )
        await stack.enter_async_context(
            background_asyncio_service(alice_tx_pool))

        bob_tx_pool = TxPool(
            bob_event_bus,
            bob_proxy_peer_pool,
            tx_validator,
        )
        await stack.enter_async_context(background_asyncio_service(bob_tx_pool)
                                        )

        yield (
            alice,
            alice_event_bus,
            alice_tx_pool,
        ), (bob, bob_event_bus, bob_tx_pool)
Пример #5
0
async def test_get_pooled_transactions_request(request, event_bus,
                                               other_event_bus, event_loop,
                                               chaindb_20, client_and_server):
    server_event_bus = event_bus
    client_event_bus = other_event_bus
    client_peer, server_peer = client_and_server

    if get_highest_eth_protocol_version(client_peer) < ETHProtocolV65.version:
        pytest.skip("Test not applicable below eth/65")

    client_peer_pool = MockPeerPoolWithConnectedPeers(
        [client_peer], event_bus=client_event_bus)
    server_peer_pool = MockPeerPoolWithConnectedPeers(
        [server_peer], event_bus=server_event_bus)

    async with contextlib.AsyncExitStack() as stack:
        await stack.enter_async_context(
            run_peer_pool_event_server(client_event_bus,
                                       client_peer_pool,
                                       handler_type=ETHPeerPoolEventServer))

        await stack.enter_async_context(
            run_peer_pool_event_server(server_event_bus,
                                       server_peer_pool,
                                       handler_type=ETHPeerPoolEventServer))

        client_proxy_peer_pool = ETHProxyPeerPool(
            client_event_bus, TO_NETWORKING_BROADCAST_CONFIG)
        await stack.enter_async_context(
            background_asyncio_service(client_proxy_peer_pool))

        proxy_peer_pool = ETHProxyPeerPool(server_event_bus,
                                           TO_NETWORKING_BROADCAST_CONFIG)
        await stack.enter_async_context(
            background_asyncio_service(proxy_peer_pool))

        proxy_peer = await client_proxy_peer_pool.ensure_proxy_peer(
            client_peer.session)

        # The reason we run this test separately from the other request tests is because
        # GetPooledTransactions requests should be answered from the tx pool which the previous
        # test does not depend on.
        await stack.enter_async_context(
            background_asyncio_service(
                TxPool(server_event_bus, proxy_peer_pool, lambda _: True)))

        # The tx pool always answers these with an empty response
        txs = await proxy_peer.eth_api.get_pooled_transactions((decode_hex(
            '0x9ea39df6210064648ecbc465cd628fe52f69af53792e1c2f27840133435159d4'
        ), ))
        assert len(txs) == 0
Пример #6
0
async def test_proxy_peer_requests_with_timeouts(request, event_bus,
                                                 other_event_bus, event_loop,
                                                 client_and_server):

    server_event_bus = event_bus
    client_event_bus = other_event_bus
    client_peer, server_peer = client_and_server

    client_peer_pool = MockPeerPoolWithConnectedPeers(
        [client_peer], event_bus=client_event_bus)
    server_peer_pool = MockPeerPoolWithConnectedPeers(
        [server_peer], event_bus=server_event_bus)

    async with AsyncExitStack() as stack:
        await stack.enter_async_context(
            run_peer_pool_event_server(client_event_bus,
                                       client_peer_pool,
                                       handler_type=ETHPeerPoolEventServer))
        await stack.enter_async_context(
            run_peer_pool_event_server(server_event_bus,
                                       server_peer_pool,
                                       handler_type=ETHPeerPoolEventServer))

        client_proxy_peer_pool = ETHProxyPeerPool(
            client_event_bus, TO_NETWORKING_BROADCAST_CONFIG)
        await stack.enter_async_context(run_service(client_proxy_peer_pool))

        server_proxy_peer_pool = ETHProxyPeerPool(
            server_event_bus, TO_NETWORKING_BROADCAST_CONFIG)
        await stack.enter_async_context(run_service(server_proxy_peer_pool))

        proxy_peer = await client_proxy_peer_pool.ensure_proxy_peer(
            client_peer.session)

        with pytest.raises(asyncio.TimeoutError):
            await proxy_peer.eth_api.get_block_headers(0,
                                                       1,
                                                       0,
                                                       False,
                                                       timeout=0.01)

        with pytest.raises(asyncio.TimeoutError):
            await proxy_peer.eth_api.get_receipts((), timeout=0.01)

        with pytest.raises(asyncio.TimeoutError):
            await proxy_peer.eth_api.get_block_bodies((), timeout=0.01)

        with pytest.raises(asyncio.TimeoutError):
            await proxy_peer.eth_api.get_node_data((), timeout=0.01)
Пример #7
0
    def do_start(self) -> None:

        trinity_config = self.boot_info.trinity_config
        db = DBClient.connect(trinity_config.database_ipc_path)

        app_config = trinity_config.get_app_config(Eth1AppConfig)
        chain_config = app_config.get_chain_config()

        chain = chain_config.full_chain_class(db)

        if self.boot_info.trinity_config.network_id == MAINNET_NETWORK_ID:
            validator = DefaultTransactionValidator(chain,
                                                    BYZANTIUM_MAINNET_BLOCK)
        elif self.boot_info.trinity_config.network_id == ROPSTEN_NETWORK_ID:
            validator = DefaultTransactionValidator(chain,
                                                    BYZANTIUM_ROPSTEN_BLOCK)
        else:
            raise ValueError(
                "The TxPool component only supports MainnetChain or RopstenChain"
            )

        proxy_peer_pool = ETHProxyPeerPool(self.event_bus,
                                           TO_NETWORKING_BROADCAST_CONFIG)

        self.tx_pool = TxPool(self.event_bus, proxy_peer_pool, validator)
        asyncio.ensure_future(
            exit_with_services(self.tx_pool, self._event_bus_service))
        asyncio.ensure_future(self.tx_pool.run())
Пример #8
0
 async def do_run(self, event_bus: EndpointAPI) -> None:
     proxy_peer_pool = ETHProxyPeerPool(event_bus,
                                        TO_NETWORKING_BROADCAST_CONFIG)
     async with background_trio_service(proxy_peer_pool):
         service = NewBlockService(event_bus, proxy_peer_pool)
         async with background_trio_service(service) as manager:
             await manager.wait_finished()
Пример #9
0
    def do_start(self) -> None:

        trinity_config = self.boot_info.trinity_config
        db_manager = create_db_consumer_manager(
            trinity_config.database_ipc_path)
        db = db_manager.get_db()  # type: ignore

        app_config = trinity_config.get_app_config(Eth1AppConfig)
        chain_config = app_config.get_chain_config()

        chain = chain_config.full_chain_class(db)

        if self.boot_info.trinity_config.network_id == MAINNET_NETWORK_ID:
            validator = DefaultTransactionValidator(chain,
                                                    BYZANTIUM_MAINNET_BLOCK)
        elif self.boot_info.trinity_config.network_id == ROPSTEN_NETWORK_ID:
            validator = DefaultTransactionValidator(chain,
                                                    BYZANTIUM_ROPSTEN_BLOCK)
        else:
            # TODO: We could hint the user about e.g. a --tx-pool-no-validation flag to run the
            # tx pool without tx validation in this case
            raise ValueError(
                "The TxPool plugin only supports MainnetChain or RopstenChain")

        proxy_peer_pool = ETHProxyPeerPool(self.event_bus,
                                           TO_NETWORKING_BROADCAST_CONFIG)

        self.tx_pool = TxPool(self.event_bus, proxy_peer_pool, validator)
        asyncio.ensure_future(self.tx_pool.run())
Пример #10
0
    async def do_run(cls, boot_info: BootInfo, event_bus: EndpointAPI) -> None:
        trinity_config = boot_info.trinity_config
        db = DBClient.connect(trinity_config.database_ipc_path)

        app_config = trinity_config.get_app_config(Eth1AppConfig)
        chain_config = app_config.get_chain_config()

        chain = chain_config.full_chain_class(db)

        if boot_info.trinity_config.network_id == MAINNET_NETWORK_ID:
            validator = DefaultTransactionValidator(chain,
                                                    PETERSBURG_MAINNET_BLOCK)
        elif boot_info.trinity_config.network_id == ROPSTEN_NETWORK_ID:
            validator = DefaultTransactionValidator(chain,
                                                    PETERSBURG_ROPSTEN_BLOCK)
        else:
            raise Exception("This code path should not be reachable")

        proxy_peer_pool = ETHProxyPeerPool(event_bus,
                                           TO_NETWORKING_BROADCAST_CONFIG)

        tx_pool = TxPool(event_bus, proxy_peer_pool, validator)

        async with run_service(tx_pool):
            await tx_pool.cancellation()
Пример #11
0
    async def do_run(cls, boot_info: BootInfo, event_bus: EndpointAPI) -> None:
        trinity_config = boot_info.trinity_config
        db = DBClient.connect(trinity_config.database_ipc_path)
        with db:
            app_config = trinity_config.get_app_config(Eth1AppConfig)
            chain_config = app_config.get_chain_config()

            chain = chain_config.full_chain_class(db)

            if boot_info.trinity_config.network_id == MAINNET_NETWORK_ID:
                validator = DefaultTransactionValidator(
                    chain, ISTANBUL_MAINNET_BLOCK)
            elif boot_info.trinity_config.network_id == ROPSTEN_NETWORK_ID:
                validator = DefaultTransactionValidator(
                    chain, ISTANBUL_ROPSTEN_BLOCK)
            elif boot_info.trinity_config.network_id == GOERLI_NETWORK_ID:
                validator = DefaultTransactionValidator(
                    chain, ISTANBUL_GOERLI_BLOCK)
            else:
                raise Exception("This code path should not be reachable")

            proxy_peer_pool = ETHProxyPeerPool(event_bus,
                                               TO_NETWORKING_BROADCAST_CONFIG)
            async with background_asyncio_service(proxy_peer_pool):
                tx_pool = TxPool(event_bus, proxy_peer_pool, validator)
                async with background_asyncio_service(tx_pool) as manager:
                    await manager.wait_finished()
Пример #12
0
async def test_get_peers(event_bus, response, expected_count):
    do_mock = mock_request_response(GetConnectedPeersRequest, response, event_bus)

    async with do_mock:
        proxy_peer_pool = ETHProxyPeerPool(event_bus, TO_NETWORKING_BROADCAST_CONFIG)
        async with run_service(proxy_peer_pool):
            peers = await proxy_peer_pool.get_peers()
            assert len(peers) == expected_count
Пример #13
0
 async def do_run(self, event_bus: EndpointAPI) -> None:
     if self._boot_info.args.enable_metrics:
         metrics_service = metrics_service_from_args(self._boot_info.args)
     else:
         metrics_service = NOOP_METRICS_SERVICE
     proxy_peer_pool = ETHProxyPeerPool(event_bus, TO_NETWORKING_BROADCAST_CONFIG)
     async with background_trio_service(proxy_peer_pool):
         async with background_trio_service(metrics_service):
             service = NewBlockService(
                 event_bus, proxy_peer_pool, metrics_service.registry, self._boot_info)
             async with background_trio_service(service) as manager:
                 await manager.wait_finished()
Пример #14
0
async def test_adds_new_peers(event_bus):

    do_mock = mock_request_response(
        GetConnectedPeersRequest,
        GetConnectedPeersResponseFactory.from_sessions((TEST_NODES[0],)),
        event_bus,
    )
    async with do_mock:
        proxy_peer_pool = ETHProxyPeerPool(event_bus, TO_NETWORKING_BROADCAST_CONFIG)
        async with run_service(proxy_peer_pool):

            assert len(await proxy_peer_pool.get_peers()) == 1

            await event_bus.broadcast(PeerJoinedEvent(TEST_NODES[1]))
            # Give the peer a moment to pickup the peer
            await asyncio.sleep(0.01)

            assert len(await proxy_peer_pool.get_peers()) == 2
Пример #15
0
async def test_does_not_propagate_invalid_tx(event_bus,
                                             funded_address_private_key,
                                             chain_with_block_validation,
                                             tx_validator):
    chain = chain_with_block_validation

    initial_two_peers = TEST_NODES[:2]
    node_one = initial_two_peers[0]
    node_two = initial_two_peers[1]

    async with AsyncExitStack() as stack:
        await stack.enter_async_context(
            mock_request_response(
                GetConnectedPeersRequest,
                GetConnectedPeersResponse(initial_two_peers),
                event_bus,
            ))

        peer_pool = ETHProxyPeerPool(event_bus, TO_NETWORKING_BROADCAST_CONFIG)
        await stack.enter_async_context(run_service(peer_pool))

        tx_pool = TxPool(event_bus, peer_pool, tx_validator)
        await stack.enter_async_context(background_asyncio_service(tx_pool))

        await asyncio.sleep(0.01)

        txs_broadcasted_by_peer1 = [
            create_random_tx(chain, funded_address_private_key,
                             is_valid=False),
            create_random_tx(chain, funded_address_private_key)
        ]

        outgoing_tx, got_txns = observe_outgoing_transactions(event_bus)

        # Peer1 sends some txs
        await event_bus.broadcast(
            TransactionsEvent(session=node_one,
                              command=Transactions(txs_broadcasted_by_peer1)))
        await asyncio.wait_for(got_txns.wait(), timeout=0.1)

        # Check that Peer2 received only the second tx which is valid
        assert outgoing_tx == [
            (node_two, (txs_broadcasted_by_peer1[1], )),
        ]
Пример #16
0
    async def do_run(self, event_bus: EndpointAPI) -> None:
        boot_info = self._boot_info
        trinity_config = boot_info.trinity_config
        db = DBClient.connect(trinity_config.database_ipc_path)
        with db:
            app_config = trinity_config.get_app_config(Eth1AppConfig)
            chain_config = app_config.get_chain_config()

            chain = chain_config.full_chain_class(db)

            validator = DefaultTransactionValidator.from_network_id(
                chain,
                boot_info.trinity_config.network_id,
            )

            proxy_peer_pool = ETHProxyPeerPool(event_bus, TO_NETWORKING_BROADCAST_CONFIG)
            async with background_asyncio_service(proxy_peer_pool):
                tx_pool = TxPool(event_bus, proxy_peer_pool, validator)
                async with background_asyncio_service(tx_pool) as manager:
                    await manager.wait_finished()
Пример #17
0
async def test_removes_peers(event_bus):
    do_mock = mock_request_response(
        GetConnectedPeersRequest,
        GetConnectedPeersResponseFactory.from_sessions(TEST_NODES[:2]),
        event_bus,
    )

    async with do_mock:
        proxy_peer_pool = ETHProxyPeerPool(event_bus, TO_NETWORKING_BROADCAST_CONFIG)
        async with run_service(proxy_peer_pool):

            assert len(await proxy_peer_pool.get_peers()) == 2

            await event_bus.broadcast(PeerLeftEvent(TEST_NODES[0]))
            # Give the peer a moment to remove the peer
            await asyncio.sleep(0.01)

            peers = await proxy_peer_pool.get_peers()
            assert len(peers) == 1
            assert peers[0].session == TEST_NODES[1]
Пример #18
0
async def test_proxy_peer_requests(request, event_bus, other_event_bus,
                                   event_loop, chaindb_20, client_and_server):
    server_event_bus = event_bus
    client_event_bus = other_event_bus
    client_peer, server_peer = client_and_server

    client_peer_pool = MockPeerPoolWithConnectedPeers(
        [client_peer], event_bus=client_event_bus)
    server_peer_pool = MockPeerPoolWithConnectedPeers(
        [server_peer], event_bus=server_event_bus)

    async with contextlib.AsyncExitStack() as stack:
        await stack.enter_async_context(
            run_peer_pool_event_server(client_event_bus,
                                       client_peer_pool,
                                       handler_type=ETHPeerPoolEventServer))

        await stack.enter_async_context(
            run_peer_pool_event_server(server_event_bus,
                                       server_peer_pool,
                                       handler_type=ETHPeerPoolEventServer))

        base_db = chaindb_20.db
        await stack.enter_async_context(
            background_asyncio_service(
                ETHRequestServer(
                    server_event_bus,
                    TO_NETWORKING_BROADCAST_CONFIG,
                    AsyncChainDB(base_db),
                )))
        await stack.enter_async_context(
            background_asyncio_service(
                WitRequestServer(
                    server_event_bus,
                    TO_NETWORKING_BROADCAST_CONFIG,
                    base_db,
                )))

        client_proxy_peer_pool = ETHProxyPeerPool(
            client_event_bus, TO_NETWORKING_BROADCAST_CONFIG)
        await stack.enter_async_context(
            background_asyncio_service(client_proxy_peer_pool))

        proxy_peer_pool = ETHProxyPeerPool(server_event_bus,
                                           TO_NETWORKING_BROADCAST_CONFIG)
        await stack.enter_async_context(
            background_asyncio_service(proxy_peer_pool))

        proxy_peer = await client_proxy_peer_pool.ensure_proxy_peer(
            client_peer.session)

        headers = await proxy_peer.eth_api.get_block_headers(0, 1, 0, False)

        assert len(headers) == 1
        block_header = headers[0]
        assert block_header.block_number == 0

        receipts = await proxy_peer.eth_api.get_receipts(headers)
        assert len(receipts) == 1
        receipt = receipts[0]
        assert receipt[1][0] == block_header.receipt_root

        block_bundles = await proxy_peer.eth_api.get_block_bodies(headers)
        assert len(block_bundles) == 1
        first_bundle = block_bundles[0]
        assert first_bundle[1][0] == block_header.transaction_root

        node_data = await proxy_peer.eth_api.get_node_data(
            (block_header.state_root, ))
        assert node_data[0][0] == block_header.state_root

        block_hash = block_header.hash
        node_hashes = tuple(Hash32Factory.create_batch(5))
        # Populate the server's witness DB so that it can reply to our request.
        wit_db = AsyncWitnessDB(base_db)
        wit_db.persist_witness_hashes(block_hash, node_hashes)
        response = await proxy_peer.wit_api.get_block_witness_hashes(block_hash
                                                                     )
        assert set(response) == set(node_hashes)
Пример #19
0
async def test_can_instantiate_proxy_pool(event_bus):
    ETHProxyPeerPool(event_bus, TO_NETWORKING_BROADCAST_CONFIG)
Пример #20
0
async def test_tx_propagation(event_bus,
                              funded_address_private_key,
                              chain_with_block_validation,
                              tx_validator):

    initial_two_peers = TEST_NODES[:2]
    node_one = initial_two_peers[0]
    node_two = initial_two_peers[1]

    async with AsyncExitStack() as stack:
        await stack.enter_async_context(mock_request_response(
            GetConnectedPeersRequest,
            GetConnectedPeersResponseFactory.from_sessions(initial_two_peers),
            event_bus,
        ))

        peer_pool = ETHProxyPeerPool(event_bus, TO_NETWORKING_BROADCAST_CONFIG)
        await stack.enter_async_context(run_service(peer_pool))

        tx_pool = TxPool(event_bus, peer_pool, tx_validator)
        await stack.enter_async_context(background_asyncio_service(tx_pool))

        await asyncio.sleep(0.01)

        txs_broadcasted_by_peer1 = [
            create_random_tx(chain_with_block_validation, funded_address_private_key)
        ]

        # this needs to go here to ensure that the subscription is *after*
        # the one installed by the transaction pool so that the got_txns
        # event will get set after the other handlers have been called.
        outgoing_tx, got_txns = observe_outgoing_transactions(event_bus)

        # Peer1 sends some txs
        await event_bus.broadcast(
            TransactionsEvent(session=node_one, command=Transactions(txs_broadcasted_by_peer1))
        )

        await asyncio.wait_for(got_txns.wait(), timeout=0.1)

        assert outgoing_tx == [
            (node_two, tuple(txs_broadcasted_by_peer1)),
        ]
        # Clear the recording, we asserted all we want and would like to have a fresh start
        outgoing_tx.clear()

        # Peer1 sends same txs again
        await event_bus.broadcast(
            TransactionsEvent(session=node_one, command=Transactions(txs_broadcasted_by_peer1))
        )
        await asyncio.wait_for(got_txns.wait(), timeout=0.1)
        # Check that Peer2 doesn't receive them again
        assert len(outgoing_tx) == 0

        # Peer2 sends exact same txs back
        await event_bus.broadcast(
            TransactionsEvent(session=node_two, command=Transactions(txs_broadcasted_by_peer1))
        )
        await asyncio.wait_for(got_txns.wait(), timeout=0.1)

        # Check that Peer1 won't get them as that is where they originally came from
        assert len(outgoing_tx) == 0

        txs_broadcasted_by_peer2 = [
            create_random_tx(chain_with_block_validation, funded_address_private_key),
            txs_broadcasted_by_peer1[0]
        ]

        # Peer2 sends old + new tx
        await event_bus.broadcast(
            TransactionsEvent(session=node_two, command=Transactions(txs_broadcasted_by_peer2))
        )
        await asyncio.wait_for(got_txns.wait(), timeout=0.1)
        # Not sure why this sleep is needed....
        await asyncio.sleep(0.01)

        # Check that Peer1 receives only the one tx that it didn't know about
        assert outgoing_tx == [
            (node_one, (txs_broadcasted_by_peer2[0],)),
        ]