From 43e76efcc5f86de7ec43c4524ff45f6986ed0680 Mon Sep 17 00:00:00 2001 From: Dan Wendlandt Date: Tue, 20 Nov 2012 12:59:20 -0800 Subject: [PATCH] fix broken logic of only using hasattr to check for get_x_counts bug 1081259 Change-Id: I1dad596830685968ae47394e0e85afe1b72ab544 --- quantum/quantum_plugin_base_v2.py | 20 ++++++++++++++------ quantum/quota.py | 4 ++-- quantum/tests/unit/test_api_v2.py | 17 +++++++++++++++++ 3 files changed, 33 insertions(+), 8 deletions(-) diff --git a/quantum/quantum_plugin_base_v2.py b/quantum/quantum_plugin_base_v2.py index 61b8fa437a..3ba9a4283e 100644 --- a/quantum/quantum_plugin_base_v2.py +++ b/quantum/quantum_plugin_base_v2.py @@ -23,6 +23,8 @@ methods that needs to be implemented by a v2 Quantum Plug-in. from abc import ABCMeta, abstractmethod +from quantum.common import exceptions + class QuantumPluginBaseV2(object): @@ -87,7 +89,6 @@ class QuantumPluginBaseV2(object): """ pass - @abstractmethod def get_subnets_count(self, context, filters=None): """ Return the number of subnets. The result depends on the identity of @@ -101,8 +102,11 @@ class QuantumPluginBaseV2(object): match comparison for that value. Each result returned by this function will have matched one of the values for each key in filters. + + NOTE: this method is optional, as it was not part of the originally + defined plugin API. """ - pass + raise exceptions.NotImplementedError() @abstractmethod def delete_subnet(self, context, id): @@ -172,7 +176,6 @@ class QuantumPluginBaseV2(object): """ pass - @abstractmethod def get_networks_count(self, context, filters=None): """ Return the number of networks. The result depends on the identity @@ -186,8 +189,11 @@ class QuantumPluginBaseV2(object): match comparison for that value. Each result returned by this function will have matched one of the values for each key in filters. + + NOTE: this method is optional, as it was not part of the originally + defined plugin API. """ - pass + raise exceptions.NotImplementedError() @abstractmethod def delete_network(self, context, id): @@ -257,7 +263,6 @@ class QuantumPluginBaseV2(object): """ pass - @abstractmethod def get_ports_count(self, context, filters=None): """ Return the number of ports. The result depends on the identity of @@ -271,8 +276,11 @@ class QuantumPluginBaseV2(object): match comparison for that value. Each result returned by this function will have matched one of the values for each key in filters. + + NOTE: this method is optional, as it was not part of the originally + defined plugin API. """ - pass + raise exceptions.NotImplementedError() @abstractmethod def delete_port(self, context, id): diff --git a/quantum/quota.py b/quantum/quota.py index f0b3f8fc65..22efcc9813 100644 --- a/quantum/quota.py +++ b/quantum/quota.py @@ -272,10 +272,10 @@ def _count_resource(context, plugin, resources, tenant_id): # using a DB's optimized counting features. We try to use that one # if present. Otherwise just use regular getter to retrieve all objects # and count in python, allowing older plugins to still be supported - if hasattr(plugin, count_getter_name): + try: obj_count_getter = getattr(plugin, count_getter_name) return obj_count_getter(context, filters={'tenant_id': [tenant_id]}) - else: + except (exceptions.NotImplementedError, AttributeError): obj_getter = getattr(plugin, "get_%s" % resources) obj_list = obj_getter(context, filters={'tenant_id': [tenant_id]}) return len(obj_list) if obj_list else 0 diff --git a/quantum/tests/unit/test_api_v2.py b/quantum/tests/unit/test_api_v2.py index 02a7f4848e..654dbdd4f4 100644 --- a/quantum/tests/unit/test_api_v2.py +++ b/quantum/tests/unit/test_api_v2.py @@ -762,6 +762,23 @@ class QuotaTest(APIv2TestBase): self.assertTrue("Quota exceeded for resources" in res.json['QuantumError']) + def test_create_network_quota_no_counts(self): + cfg.CONF.set_override('quota_network', 1, group='QUOTAS') + initial_input = {'network': {'name': 'net1', 'tenant_id': _uuid()}} + full_input = {'network': {'admin_state_up': True, 'subnets': []}} + full_input['network'].update(initial_input['network']) + + instance = self.plugin.return_value + instance.get_networks_count.side_effect = ( + q_exc.NotImplementedError()) + instance.get_networks.return_value = ["foo"] + res = self.api.post_json( + _get_path('networks'), initial_input, expect_errors=True) + instance.get_networks_count.assert_called_with(mock.ANY, + filters=mock.ANY) + self.assertTrue("Quota exceeded for resources" in + res.json['QuantumError']) + def test_create_network_quota_without_limit(self): cfg.CONF.set_override('quota_network', -1, group='QUOTAS') initial_input = {'network': {'name': 'net1', 'tenant_id': _uuid()}}