def test_read_has_constant_number_of_queries(self): # Patch middleware so it does not affect query counting. self.patch( middleware.ExternalComponentsMiddleware, "_check_rack_controller_connectivity", ) for _ in range(3): make_complex_fabric() uri = get_fabrics_uri() num_queries1, response1 = count_queries(self.client.get, uri) for _ in range(3): make_complex_fabric() num_queries2, response2 = count_queries(self.client.get, uri) # Make sure the responses are ok as it's not useful to compare the # number of queries if they are not. parsed_result_1 = json_load_bytes(response1.content) parsed_result_2 = json_load_bytes(response2.content) self.assertEqual( [http.client.OK, http.client.OK, 4, 7], [ response1.status_code, response2.status_code, len(parsed_result_1), len(parsed_result_2), ], ) self.assertEqual(num_queries1, num_queries2)
def test_list_num_queries_is_the_expected_number(self): # Prevent RBAC from making a query. self.useFixture(RBACForceOffFixture()) admin = factory.make_admin() handler = UserHandler(admin, {}, None) for _ in range(3): factory.make_User() queries_one, _ = count_queries(handler.list, {"limit": 1}) queries_total, _ = count_queries(handler.list, {}) # This check is to notify the developer that a change was made that # affects the number of queries performed when doing a user listing. # It is important to keep this number as low as possible. A larger # number means regiond has to do more work slowing down its process # and slowing down the client waiting for the response. self.assertEqual( queries_one, 1, "Number of queries has changed; make sure this is expected.", ) self.assertEqual( queries_total, 1, "Number of queries has changed; make sure this is expected.", )
def test_consistent_query_count(self): source = factory.make_BootSource(keyring_data=b"1234") image_mapping = BootImageMapping() for _ in range(random.randint(20, 50)): self.make_release(image_mapping) # Add all the items to the cache, always 5. queries, _ = count_queries( bootsources._update_cache, source.to_dict_without_selections(), image_mapping, ) self.assertEquals(5, queries) # Now that they all already exist, it should only be 4 queries. queries, _ = count_queries( bootsources._update_cache, source.to_dict_without_selections(), image_mapping, ) self.assertEquals(4, queries) # Do it again just to be sure. queries, _ = count_queries( bootsources._update_cache, source.to_dict_without_selections(), image_mapping, ) self.assertEquals(4, queries)
def test_list_uses_consistent_queries(self): user = factory.make_User() handler = SubnetHandler(user, {}, None) subnet = factory.make_Subnet() factory.make_Interface(iftype=INTERFACE_TYPE.UNKNOWN, subnet=subnet) self.assertIsNone(handler.cache.get("staticroutes")) queries_one, _ = count_queries(handler.list, {}) for _ in range(10): subnet = factory.make_Subnet() for x in range(5): node = factory.make_Node_with_Interface_on_Subnet( subnet=subnet, status=NODE_STATUS.READY) iface = node.interface_set.first() factory.make_StaticIPAddress( alloc_type=IPADDRESS_TYPE.STICKY, subnet=subnet, interface=iface, ) self.assertIsNotNone(handler.cache["staticroutes"]) del handler.cache["staticroutes"] queries_all, _ = count_queries(handler.list, {}) self.assertEquals(queries_one, queries_all) self.assertIsNotNone(handler.cache["staticroutes"]) self.assertEquals(4, queries_one)
def test_list_num_queries_is_independent_of_num_devices(self): # Prevent RBAC from making a query. self.useFixture(RBACForceOffFixture()) owner = factory.make_User() handler = SwitchHandler(owner, {}, None) for _ in range(10): device = factory.make_Device(owner=owner) factory.make_Switch(node=device) query_10_count, _ = count_queries(handler.list, {}) for _ in range(10): device = factory.make_Device(owner=owner) factory.make_Switch(node=device) query_20_count, _ = count_queries(handler.list, {}) # This check is to notify the developer that a change was made that # affects the number of queries performed when doing a node listing. # It is important to keep this number as low as possible. A larger # number means regiond has to do more work slowing down its process # and slowing down the client waiting for the response. self.assertEqual( query_10_count, query_20_count, "Number of queries has changed; make sure this is expected.", )
def test_GET_rack_controllers_query_count(self): # Patch middleware so it does not affect query counting. self.patch( middleware.ExternalComponentsMiddleware, '_check_rack_controller_connectivity') self.become_admin() tag = factory.make_Tag() for _ in range(3): rack = factory.make_RackController() rack.tags.add(tag) num_queries1, response1 = count_queries( self.client.get, self.get_tag_uri(tag), {'op': 'rack_controllers'}) for _ in range(3): rack = factory.make_RackController() rack.tags.add(tag) num_queries2, response2 = count_queries( self.client.get, self.get_tag_uri(tag), {'op': 'rack_controllers'}) # Make sure the responses are ok as it's not useful to compare the # number of queries if they are not. parsed_result_1 = json.loads( response1.content.decode(settings.DEFAULT_CHARSET)) parsed_result_2 = json.loads( response2.content.decode(settings.DEFAULT_CHARSET)) self.assertEqual( [http.client.OK, http.client.OK, 3, 6], [ response1.status_code, response2.status_code, len(extract_system_ids(parsed_result_1)), len(extract_system_ids(parsed_result_2)), ]) self.assertEquals(num_queries1, num_queries2 - (3 * 3))
def test_query_num_queries_is_independent_of_num_nodes_and_events(self): # 1 query for all the select_related's. expected_queries = 1 events_per_node = 5 num_nodes_per_group = 5 events_per_group = num_nodes_per_group * events_per_node self.make_nodes_in_group_with_events( num_nodes_per_group, events_per_node) handler = events_module.EventsHandler() query_1_count, query_1_result = ( count_queries(handler.query, RequestFixture( {'op': 'query', 'level': 'DEBUG'}, ['op', 'level']))) self.make_nodes_in_group_with_events( num_nodes_per_group, events_per_node) query_2_count, query_2_result = ( count_queries(handler.query, RequestFixture( {'op': 'query', 'level': 'DEBUG'}, ['op', 'level']))) # This check is to notify the developer that a change was made that # affects the number of queries performed when doing an event listing. # If this happens, consider your prefetching and adjust accordingly. self.assertEqual(events_per_group, int(query_1_result['count'])) self.assertEqual( expected_queries, query_1_count, "Number of queries has changed; make sure this is expected.") self.assertEqual(events_per_group * 2, int(query_2_result['count'])) self.assertEqual( expected_queries, query_2_count, "Number of queries is not independent of the number of nodes.")
def test_list_num_queries_is_the_expected_number(self): owner = factory.make_admin() for _ in range(10): node = factory.make_RegionRackController(owner=owner) commissioning_script_set = factory.make_ScriptSet( node=node, result_type=RESULT_TYPE.COMMISSIONING) testing_script_set = factory.make_ScriptSet( node=node, result_type=RESULT_TYPE.TESTING) node.current_commissioning_script_set = commissioning_script_set node.current_testing_script_set = testing_script_set node.save() for __ in range(10): factory.make_ScriptResult(status=SCRIPT_STATUS.PASSED, script_set=commissioning_script_set) factory.make_ScriptResult(status=SCRIPT_STATUS.PASSED, script_set=testing_script_set) handler = ControllerHandler(owner, {}, None) queries_one, _ = count_queries(handler.list, {'limit': 1}) queries_total, _ = count_queries(handler.list, {}) # This check is to notify the developer that a change was made that # affects the number of queries performed when doing a node listing. # It is important to keep this number as low as possible. A larger # number means regiond has to do more work slowing down its process # and slowing down the client waiting for the response. self.assertEqual( queries_one, 3, "Number of queries has changed; make sure this is expected.") self.assertEqual( queries_total, 3, "Number of queries has changed; make sure this is expected.")
def test_GET_nodes_query_count(self): # Patch middleware so it does not affect query counting. self.patch( middleware.ExternalComponentsMiddleware, "_check_rack_controller_connectivity", ) tag = factory.make_Tag() for _ in range(3): machine = factory.make_Node_with_Interface_on_Subnet() machine.tags.add(tag) # XXX ltrager 2019-08-16 - Work around for LP:1840491 Node.objects.update(boot_disk=None) for _ in range(3): device = factory.make_Device() device.tags.add(tag) num_queries1, response1 = count_queries( self.client.get, self.get_tag_uri(tag), {"op": "nodes"} ) for _ in range(3): machine = factory.make_Node_with_Interface_on_Subnet() machine.tags.add(tag) # XXX ltrager 2019-08-16 - Work around for LP:1840491 Node.objects.update(boot_disk=None) for _ in range(3): device = factory.make_Device() device.tags.add(tag) num_queries2, response2 = count_queries( self.client.get, self.get_tag_uri(tag), {"op": "nodes"} ) # Make sure the responses are ok as it's not useful to compare the # number of queries if they are not. parsed_result_1 = json.loads( response1.content.decode(settings.DEFAULT_CHARSET) ) parsed_result_2 = json.loads( response2.content.decode(settings.DEFAULT_CHARSET) ) self.assertEqual( [http.client.OK, http.client.OK, 6, 12], [ response1.status_code, response2.status_code, len(extract_system_ids(parsed_result_1)), len(extract_system_ids(parsed_result_2)), ], ) # Because of fields `status_action`, `status_message`, # `default_gateways`, `health_status`, 'special_filesystems' and # 'resource_pool' the number of queries is not the same but it is # proportional to the number of machines. self.assertEqual(num_queries1, num_queries2 - (3 * 7))
def test_list_constant_queries(self): user = factory.make_User() handler = SpaceHandler(user, {}, None) for _ in range(10): space = factory.make_Space() node = factory.make_Node(interface=True) interface = node.get_boot_interface() subnet = factory.make_Subnet(space=space, vlan=interface.vlan) factory.make_StaticIPAddress(subnet=subnet, interface=interface) queries_one, _ = count_queries(handler.list, {"limit": 1}) queries_multiple, _ = count_queries(handler.list, {}) self.assertEqual(queries_one, queries_multiple)
def test_list_uses_consistent_queries(self): user = factory.make_User() handler = SubnetHandler(user, {}, None) for _ in range(20): factory.make_Subnet() self.assertIsNone(handler.cache.get("staticroutes")) queries_one, _ = count_queries(handler.list, {"limit": 1}) self.assertIsNotNone(handler.cache["staticroutes"]) del handler.cache["staticroutes"] queries_all, _ = count_queries(handler.list, {}) self.assertEquals(queries_one, queries_all) self.assertIsNotNone(handler.cache["staticroutes"]) self.assertEquals(5, queries_one)
def test_query_num_queries_is_independent_of_num_nodes_and_events(self): # Prevent RBAC from making a query. self.useFixture(RBACForceOffFixture()) expected_queries = 1 events_per_node = 5 num_nodes_per_group = 5 events_per_group = num_nodes_per_group * events_per_node self.make_nodes_in_group_with_events(num_nodes_per_group, events_per_node) handler = events_module.EventsHandler() query_1_count, query_1_result = count_queries( handler.query, RequestFixture({ "op": "query", "level": "DEBUG" }, ["op", "level"]), ) self.make_nodes_in_group_with_events(num_nodes_per_group, events_per_node) query_2_count, query_2_result = count_queries( handler.query, RequestFixture({ "op": "query", "level": "DEBUG" }, ["op", "level"]), ) # This check is to notify the developer that a change was made that # affects the number of queries performed when doing an event listing. # If this happens, consider your prefetching and adjust accordingly. self.assertEqual(events_per_group, int(query_1_result["count"])) self.assertEqual( expected_queries, query_1_count, "Number of queries has changed; make sure this is expected.", ) self.assertEqual(events_per_group * 2, int(query_2_result["count"])) self.assertEqual( query_1_count, query_2_count, "Number of queries is not independent of the number of nodes.", )
def test_list_constant_queries(self): user = factory.make_User() handler = FabricHandler(user, {}, None) for _ in range(10): fabric = factory.make_Fabric() vlan = fabric.get_default_vlan() for _ in range(3): node = factory.make_Node(interface=True) interface = node.get_boot_interface() interface.vlan = vlan interface.save() queries_one, _ = count_queries(handler.list, {"limit": 1}) queries_multiple, _ = count_queries(handler.list, {}) self.assertEqual(queries_one, queries_multiple)
def test_list_num_queries_is_independent_of_num_devices(self): owner = factory.make_User() handler = DeviceHandler(owner, {}) self.make_devices(10, owner=owner) query_10_count, _ = count_queries(handler.list, {}) self.make_devices(10, owner=owner) query_20_count, _ = count_queries(handler.list, {}) # This check is to notify the developer that a change was made that # affects the number of queries performed when doing a node listing. # It is important to keep this number as low as possible. A larger # number means regiond has to do more work slowing down its process # and slowing down the client waiting for the response. self.assertEqual( query_10_count, query_20_count, "Number of queries is not independent to the number of nodes.")
def test_get_uses_consistent_queries(self): user = factory.make_User() handler = SubnetHandler(user, {}, None) subnet = factory.make_Subnet() self.assertIsNone(handler.cache.get("staticroutes")) queries, _ = count_queries(handler.get, {"id": subnet.id}) self.assertEquals(5, queries) self.assertIsNotNone(handler.cache["staticroutes"])
def test_GET_nodes_query_count(self): # Patch middleware so it does not affect query counting. self.patch( middleware.ExternalComponentsMiddleware, '_check_rack_controller_connectivity') tag = factory.make_Tag() for _ in range(3): machine = factory.make_Node_with_Interface_on_Subnet() machine.tags.add(tag) for _ in range(3): device = factory.make_Device() device.tags.add(tag) num_queries1, response1 = count_queries( self.client.get, self.get_tag_uri(tag), {'op': 'nodes'}) for _ in range(3): machine = factory.make_Node_with_Interface_on_Subnet() machine.tags.add(tag) for _ in range(3): device = factory.make_Device() device.tags.add(tag) num_queries2, response2 = count_queries( self.client.get, self.get_tag_uri(tag), {'op': 'nodes'}) # Make sure the responses are ok as it's not useful to compare the # number of queries if they are not. parsed_result_1 = json.loads( response1.content.decode(settings.DEFAULT_CHARSET)) parsed_result_2 = json.loads( response2.content.decode(settings.DEFAULT_CHARSET)) self.assertEqual( [http.client.OK, http.client.OK, 3, 6], [ response1.status_code, response2.status_code, len(extract_system_ids(parsed_result_1)), len(extract_system_ids(parsed_result_2)), ]) # Because of fields `status_action`, `status_message`, # `default_gateways`, and `health_status` the number of queries is not # the same but it is proportional to the number of machines. self.assertEquals(num_queries1, num_queries2 - (3 * 4))
def test_list_num_queries_is_independent_of_num_devices(self): # Prevent RBAC from making a query. self.useFixture(RBACForceOffFixture()) owner = factory.make_User() handler = DeviceHandler(owner, {}, None) ip_assignment = factory.pick_enum(DEVICE_IP_ASSIGNMENT_TYPE) self.make_devices(10, owner=owner, ip_assignment=ip_assignment) query_10_count, _ = count_queries(handler.list, {}) self.make_devices(10, owner=owner, ip_assignment=ip_assignment) query_20_count, _ = count_queries(handler.list, {}) # This check is to notify the developer that a change was made that # affects the number of queries performed when doing a node listing. # It is important to keep this number as low as possible. A larger # number means regiond has to do more work slowing down its process # and slowing down the client waiting for the response. self.assertEqual( query_10_count, query_20_count, "Number of queries is not independent to the number of nodes.")
def test_get_query_count(self): user = factory.make_User() handler = ZoneHandler(user, {}) zone = factory.make_Zone() for _ in range(3): factory.make_Node(zone=zone) for _ in range(3): factory.make_Device(zone=zone) for _ in range(3): factory.make_RackController(zone=zone) for _ in range(3): factory.make_RegionController(zone=zone) count, _ = count_queries(handler.get, {"id": zone.id}) self.assertEqual(count, 3)
def test_get_num_queries_is_the_expected_number(self): owner = factory.make_User() handler = DeviceHandler(owner, {}) device = self.make_device_with_ip_address( owner=owner, ip_assignment=DEVICE_IP_ASSIGNMENT_TYPE.STATIC) queries, _ = count_queries(handler.get, {"system_id": device.system_id}) # This check is to notify the developer that a change was made that # affects the number of queries performed when doing a node get. # It is important to keep this number as low as possible. A larger # number means regiond has to do more work slowing down its process # and slowing down the client waiting for the response. self.assertEqual( queries, 19, "Number of queries has changed; make sure this is expected.")
def get_config(*args, **kwargs): explicit_count = kwargs.pop('query_count', None) count, result = count_queries(orig_get_config, *args, **kwargs) if explicit_count is None: # If you need to adjust this value up be sure that 100% you cannot # lower this value. If you want to adjust this value down, big +1! assert count <= 23, ( '%d > 22; Query count should remain below 22 queries ' 'at all times.' % count) else: # This test sets an explicit count. This should *ONLY* be used if # the test is taking a rare path that requires the query count to # some what greater. assert count == explicit_count, ( '%d != %d; Query count should remain below %d queries ' 'at all times.' % (count, explicit_count, explicit_count)) return result
def test_client_twice_no_query(self): first, client1 = count_queries(lambda: rbac.client) second, client2 = count_queries(lambda: rbac.client) self.assertIsNone(client1) self.assertIsNone(client2) self.assertEqual((1, 0), (first, second))