Changeset View
Changeset View
Standalone View
Standalone View
test/functional/example_test.py
Show First 20 Lines • Show All 128 Lines • ▼ Show 20 Lines | def custom_method(self): | ||||
self.log.info("Running custom_method") | self.log.info("Running custom_method") | ||||
def run_test(self): | def run_test(self): | ||||
"""Main test logic""" | """Main test logic""" | ||||
# Create P2P connections will wait for a verack to make sure the | # Create P2P connections will wait for a verack to make sure the | ||||
# connection is fully up | # connection is fully up | ||||
self.nodes[0].add_p2p_connection(BaseNode()) | peer_messaging = self.nodes[0].add_p2p_connection(BaseNode()) | ||||
# Generating a block on one of the nodes will get us out of IBD | # Generating a block on one of the nodes will get us out of IBD | ||||
blocks = [int(self.nodes[0].generate(nblocks=1)[0], 16)] | blocks = [int(self.nodes[0].generate(nblocks=1)[0], 16)] | ||||
self.sync_all(self.nodes[0:2]) | self.sync_all(self.nodes[0:2]) | ||||
# Notice above how we called an RPC by calling a method with the same | # Notice above how we called an RPC by calling a method with the same | ||||
# name on the node object. Notice also how we used a keyword argument | # name on the node object. Notice also how we used a keyword argument | ||||
# to specify a named RPC argument. Neither of those are defined on the | # to specify a named RPC argument. Neither of those are defined on the | ||||
Show All 24 Lines | def run_test(self): | ||||
# control the blocks and transactions. | # control the blocks and transactions. | ||||
block = create_block( | block = create_block( | ||||
self.tip, create_coinbase( | self.tip, create_coinbase( | ||||
height + 1), self.block_time) | height + 1), self.block_time) | ||||
block.solve() | block.solve() | ||||
block_message = msg_block(block) | block_message = msg_block(block) | ||||
# Send message is used to send a P2P message to the node over our | # Send message is used to send a P2P message to the node over our | ||||
# P2PInterface | # P2PInterface | ||||
self.nodes[0].p2p.send_message(block_message) | peer_messaging.send_message(block_message) | ||||
self.tip = block.sha256 | self.tip = block.sha256 | ||||
blocks.append(self.tip) | blocks.append(self.tip) | ||||
self.block_time += 1 | self.block_time += 1 | ||||
height += 1 | height += 1 | ||||
self.log.info( | self.log.info( | ||||
"Wait for node1 to reach current tip (height 11) using RPC") | "Wait for node1 to reach current tip (height 11) using RPC") | ||||
self.nodes[1].waitforblockheight(11) | self.nodes[1].waitforblockheight(11) | ||||
self.log.info("Connect node2 and node1") | self.log.info("Connect node2 and node1") | ||||
connect_nodes(self.nodes[1], self.nodes[2]) | connect_nodes(self.nodes[1], self.nodes[2]) | ||||
self.log.info("Wait for node2 to receive all the blocks from node1") | self.log.info("Wait for node2 to receive all the blocks from node1") | ||||
self.sync_all() | self.sync_all() | ||||
self.log.info("Add P2P connection to node2") | self.log.info("Add P2P connection to node2") | ||||
self.nodes[0].disconnect_p2ps() | self.nodes[0].disconnect_p2ps() | ||||
self.nodes[2].add_p2p_connection(BaseNode()) | peer_receiving = self.nodes[2].add_p2p_connection(BaseNode()) | ||||
self.log.info("Test that node2 propagates all the blocks to us") | self.log.info("Test that node2 propagates all the blocks to us") | ||||
getdata_request = msg_getdata() | getdata_request = msg_getdata() | ||||
for block in blocks: | for block in blocks: | ||||
getdata_request.inv.append(CInv(MSG_BLOCK, block)) | getdata_request.inv.append(CInv(MSG_BLOCK, block)) | ||||
self.nodes[2].p2p.send_message(getdata_request) | peer_receiving.send_message(getdata_request) | ||||
# wait_until() will loop until a predicate condition is met. Use it to test properties of the | # wait_until() will loop until a predicate condition is met. Use it to test properties of the | ||||
# P2PInterface objects. | # P2PInterface objects. | ||||
self.nodes[2].p2p.wait_until( | peer_receiving.wait_until( | ||||
lambda: sorted(blocks) == sorted(list( | lambda: sorted(blocks) == sorted(list( | ||||
self.nodes[2].p2p.block_receive_map.keys())), | peer_receiving.block_receive_map.keys())), | ||||
timeout=5) | timeout=5) | ||||
self.log.info("Check that each block was received only once") | self.log.info("Check that each block was received only once") | ||||
# The network thread uses a global lock on data access to the P2PConnection objects when sending and receiving | # The network thread uses a global lock on data access to the P2PConnection objects when sending and receiving | ||||
# messages. The test thread should acquire the global lock before accessing any P2PConnection data to avoid locking | # messages. The test thread should acquire the global lock before accessing any P2PConnection data to avoid locking | ||||
# and synchronization issues. Note p2p.wait_until() acquires this | # and synchronization issues. Note p2p.wait_until() acquires this | ||||
# global lock internally when testing the predicate. | # global lock internally when testing the predicate. | ||||
with p2p_lock: | with p2p_lock: | ||||
for block in self.nodes[2].p2p.block_receive_map.values(): | for block in peer_receiving.block_receive_map.values(): | ||||
assert_equal(block, 1) | assert_equal(block, 1) | ||||
if __name__ == '__main__': | if __name__ == '__main__': | ||||
ExampleTest().main() | ExampleTest().main() |