async def test_incremental_header_sync(request, event_loop, headerdb_mainnet_100): # Here, server will be a peer with a pre-populated headerdb, and we'll use it to send Announce # msgs to the client, which will then ask the server for any headers it's missing until their # headerdbs are in sync. light_chain, _, server = await get_lightchain_with_peers( request, event_loop, get_fresh_mainnet_headerdb()) # We start the client/server with fresh headerdbs above because we don't want them to start # syncing straight away -- instead we want to manually trigger incremental syncs by having the # server send Announce messages. We're now ready to give our server a populated headerdb. server.headerdb = headerdb_mainnet_100 # The server now announces block #10 as the new head... server.send_announce(head_number=10) # ... and we wait for the client to process that and request all headers it's missing up to # block #10. header_10 = server.headerdb.get_canonical_block_header_by_number(10) await wait_for_head(light_chain.headerdb, header_10) assert_canonical_chains_are_equal(light_chain.headerdb, server.headerdb, 10) # Now the server announces block 100 as its current head... server.send_announce(head_number=100) # ... and the client should then fetch headers from 10-100. header_100 = server.headerdb.get_canonical_block_header_by_number(100) await wait_for_head(light_chain.headerdb, header_100) assert_canonical_chains_are_equal(light_chain.headerdb, server.headerdb, 100)
async def get_lightchain_with_peers(request, event_loop, server_peer_headerdb): """Return a MainnetLightPeerChain instance with a client/server peer pair. The server is a LESPeerServer instance that can be used to send Announce and BlockHeaders messages, and the client will be registered with the LightPeerChain so that a sync request is added to the LightPeerChain's queue every time a new Announce message is received. """ headerdb = get_fresh_mainnet_headerdb() light_chain = MainnetLightPeerChain(headerdb, MockPeerPool()) asyncio.ensure_future(light_chain.run()) await asyncio.sleep(0) # Yield control to give the LightPeerChain a chance to start def finalizer(): event_loop.run_until_complete(light_chain.cancel()) request.addfinalizer(finalizer) client, server = await get_client_and_server_peer_pair( request, event_loop, headerdb, server_peer_headerdb) light_chain.register_peer(client) return light_chain, client, server