From: Brent Eagles Date: Tue, 17 Feb 2015 17:15:25 +0000 (-0330) Subject: Refactor RESOURCE_ATTRIBUTE_MAP cleanup X-Git-Url: https://review.fuel-infra.org/gitweb?a=commitdiff_plain;h=35acb27da0a762184129d97d43a7b93c9daddf91;p=openstack-build%2Fneutron-build.git Refactor RESOURCE_ATTRIBUTE_MAP cleanup This patch adds a AttributeMapMemento class that can be used for restoring the RESOURCE_ATTRIBUTE_MAP on test tear down. Tests containing their own cleanup code have been modified to use it instead. Change-Id: I7ce5182bdfb8f541741a327feada63a29ddac2ae --- diff --git a/neutron/tests/functional/api/test_policies.py b/neutron/tests/functional/api/test_policies.py index c9d4a99dc..c73400a26 100644 --- a/neutron/tests/functional/api/test_policies.py +++ b/neutron/tests/functional/api/test_policies.py @@ -13,7 +13,6 @@ # License for the specific language governing permissions and limitations # under the License. -import copy import os.path from neutron import context @@ -23,6 +22,7 @@ from neutron.api import extensions from neutron.api.v2 import attributes from neutron.tests import base +from neutron.tests import tools TEST_PATH = os.path.dirname(os.path.abspath(__file__)) @@ -40,8 +40,7 @@ class APIPolicyTestCase(base.BaseTestCase): def setUp(self): super(APIPolicyTestCase, self).setUp() - - self.ATTRIBUTE_MAP_COPY = copy.copy(attributes.RESOURCE_ATTRIBUTE_MAP) + self.useFixture(tools.AttributeMapMemento()) self.extension_path = os.path.abspath(os.path.join( TEST_PATH, "../../../extensions")) policy.reset() @@ -94,6 +93,5 @@ class APIPolicyTestCase(base.BaseTestCase): True) def tearDown(self): - if self.ATTRIBUTE_MAP_COPY: - attributes.RESOURCE_ATTRIBUTE_MAP = self.ATTRIBUTE_MAP_COPY + policy.reset() super(APIPolicyTestCase, self).tearDown() diff --git a/neutron/tests/tools.py b/neutron/tests/tools.py index 16aa49680..449dd574a 100644 --- a/neutron/tests/tools.py +++ b/neutron/tests/tools.py @@ -13,6 +13,40 @@ # License for the specific language governing permissions and limitations # under the License. +import fixtures + +from neutron.api.v2 import attributes + + +class AttributeMapMemento(fixtures.Fixture): + """Create a copy of the resource attribute map so it can be restored during + test cleanup. + + There are a few reasons why this is not included in a class derived + from BaseTestCase: + + - Test cases may need more control about when the backup is + made, especially if they are not direct descendants of + BaseTestCase. + + - Inheritance is a bit of overkill for this facility and it's a + stretch to rationalize the "is a" criteria. + """ + def setUp(self): + # Shallow copy is not a proper choice for keeping a backup copy as + # the RESOURCE_ATTRIBUTE_MAP map is modified in place through the + # 0th level keys. Ideally deepcopy() would be used but this seems + # to result in test failures. A compromise is to copy one level + # deeper than a shallow copy. + super(AttributeMapMemento, self).setUp() + self.contents_backup = {} + for resource, attrs in attributes.RESOURCE_ATTRIBUTE_MAP.iteritems(): + self.contents_backup[resource] = attrs.copy() + self.addCleanup(self.restore) + + def restore(self): + attributes.RESOURCE_ATTRIBUTE_MAP = self.contents_backup + """setup_mock_calls and verify_mock_calls are convenient methods to setup a sequence of mock calls. diff --git a/neutron/tests/unit/api/v2/test_base.py b/neutron/tests/unit/api/v2/test_base.py index 6630781fe..fb7828b7b 100644 --- a/neutron/tests/unit/api/v2/test_base.py +++ b/neutron/tests/unit/api/v2/test_base.py @@ -37,6 +37,7 @@ from neutron import policy from neutron import quota from neutron.tests import base from neutron.tests import fake_notifier +from neutron.tests import tools from neutron.tests.unit import testlib_api @@ -1106,10 +1107,7 @@ class SubresourceTest(base.BaseTestCase): plugin = 'neutron.tests.unit.api.v2.test_base.TestSubresourcePlugin' extensions.PluginAwareExtensionManager._instance = None - # Save the global RESOURCE_ATTRIBUTE_MAP - self.saved_attr_map = {} - for resource, attrs in attributes.RESOURCE_ATTRIBUTE_MAP.iteritems(): - self.saved_attr_map[resource] = attrs.copy() + self.useFixture(tools.AttributeMapMemento()) self.config_parse() self.setup_coreplugin(plugin) @@ -1136,8 +1134,6 @@ class SubresourceTest(base.BaseTestCase): def tearDown(self): router.SUB_RESOURCES = {} - # Restore the global RESOURCE_ATTRIBUTE_MAP - attributes.RESOURCE_ATTRIBUTE_MAP = self.saved_attr_map super(SubresourceTest, self).tearDown() def test_index_sub_resource(self): @@ -1382,10 +1378,7 @@ class ExtensionTestCase(base.BaseTestCase): # Ensure existing ExtensionManager is not used extensions.PluginAwareExtensionManager._instance = None - # Save the global RESOURCE_ATTRIBUTE_MAP - self.saved_attr_map = {} - for resource, attrs in attributes.RESOURCE_ATTRIBUTE_MAP.iteritems(): - self.saved_attr_map[resource] = attrs.copy() + self.useFixture(tools.AttributeMapMemento()) # Create the default configurations self.config_parse() @@ -1412,8 +1405,6 @@ class ExtensionTestCase(base.BaseTestCase): super(ExtensionTestCase, self).tearDown() self.api = None self.plugin = None - # Restore the global RESOURCE_ATTRIBUTE_MAP - attributes.RESOURCE_ATTRIBUTE_MAP = self.saved_attr_map def test_extended_create(self): net_id = _uuid() diff --git a/neutron/tests/unit/db/test_db_base_plugin_v2.py b/neutron/tests/unit/db/test_db_base_plugin_v2.py index e8ef97e8f..e262887af 100644 --- a/neutron/tests/unit/db/test_db_base_plugin_v2.py +++ b/neutron/tests/unit/db/test_db_base_plugin_v2.py @@ -41,6 +41,7 @@ from neutron.db import db_base_plugin_v2 from neutron.db import models_v2 from neutron import manager from neutron.tests import base +from neutron.tests import tools from neutron.tests.unit.api import test_extensions from neutron.tests.unit import testlib_api @@ -93,14 +94,7 @@ class NeutronDbPluginV2TestCase(testlib_api.WebTestCase): extensions.PluginAwareExtensionManager._instance = None # Save the attributes map in case the plugin will alter it # loading extensions - # Note(salvatore-orlando): shallow copy is not good enough in - # this case, but copy.deepcopy does not seem to work, since it - # causes test failures - self._attribute_map_bk = {} - for item in attributes.RESOURCE_ATTRIBUTE_MAP: - self._attribute_map_bk[item] = (attributes. - RESOURCE_ATTRIBUTE_MAP[item]. - copy()) + self.useFixture(tools.AttributeMapMemento()) self._tenant_id = 'test-tenant' if not plugin: @@ -162,8 +156,6 @@ class NeutronDbPluginV2TestCase(testlib_api.WebTestCase): self._skip_native_pagination = None self._skip_native_sortin = None self.ext_api = None - # Restore the original attribute map - attributes.RESOURCE_ATTRIBUTE_MAP = self._attribute_map_bk super(NeutronDbPluginV2TestCase, self).tearDown() def setup_config(self): diff --git a/neutron/tests/unit/extensions/base.py b/neutron/tests/unit/extensions/base.py index 2fa03024e..a4d020691 100644 --- a/neutron/tests/unit/extensions/base.py +++ b/neutron/tests/unit/extensions/base.py @@ -26,14 +26,13 @@ import webtest from neutron.api import extensions from neutron.api.v2 import attributes from neutron import quota +from neutron.tests import tools from neutron.tests.unit.api import test_extensions from neutron.tests.unit.api.v2 import test_base from neutron.tests.unit import testlib_api class ExtensionTestCase(testlib_api.WebTestCase): - def _resotre_attr_map(self): - attributes.RESOURCE_ATTRIBUTE_MAP = self._saved_attr_map def _setUpExtension(self, plugin, service_type, resource_attribute_map, extension_class, @@ -51,10 +50,7 @@ class ExtensionTestCase(testlib_api.WebTestCase): # Ensure existing ExtensionManager is not used extensions.PluginAwareExtensionManager._instance = None - # Save the global RESOURCE_ATTRIBUTE_MAP - self._saved_attr_map = attributes.RESOURCE_ATTRIBUTE_MAP.copy() - # Restore the global RESOURCE_ATTRIBUTE_MAP - self.addCleanup(self._resotre_attr_map) + self.useFixture(tools.AttributeMapMemento()) # Create the default configurations self.config_parse() diff --git a/neutron/tests/unit/extensions/test_agent.py b/neutron/tests/unit/extensions/test_agent.py index f3bcb5c34..39e48e98e 100644 --- a/neutron/tests/unit/extensions/test_agent.py +++ b/neutron/tests/unit/extensions/test_agent.py @@ -29,6 +29,7 @@ from neutron.db import agents_db from neutron.db import db_base_plugin_v2 from neutron.extensions import agent from neutron.openstack.common import uuidutils +from neutron.tests import tools from neutron.tests.unit.api.v2 import test_base from neutron.tests.unit.db import test_db_base_plugin_v2 @@ -187,19 +188,11 @@ class AgentDBTestCase(AgentDBTestMixIn, plugin = 'neutron.tests.unit.extensions.test_agent.TestAgentPlugin' # for these tests we need to enable overlapping ips cfg.CONF.set_default('allow_overlapping_ips', True) - # Save the original RESOURCE_ATTRIBUTE_MAP - self.saved_attr_map = {} - for resource, attrs in attributes.RESOURCE_ATTRIBUTE_MAP.iteritems(): - self.saved_attr_map[resource] = attrs.copy() + self.useFixture(tools.AttributeMapMemento()) ext_mgr = AgentTestExtensionManager() - self.addCleanup(self.restore_resource_attribute_map) super(AgentDBTestCase, self).setUp(plugin=plugin, ext_mgr=ext_mgr) self.adminContext = context.get_admin_context() - def restore_resource_attribute_map(self): - # Restore the originak RESOURCE_ATTRIBUTE_MAP - attributes.RESOURCE_ATTRIBUTE_MAP = self.saved_attr_map - def test_create_agent(self): data = {'agent': {}} _req = self.new_create_request('agents', data, self.fmt) diff --git a/neutron/tests/unit/extensions/test_providernet.py b/neutron/tests/unit/extensions/test_providernet.py index a1645e21f..d17f93909 100644 --- a/neutron/tests/unit/extensions/test_providernet.py +++ b/neutron/tests/unit/extensions/test_providernet.py @@ -19,13 +19,13 @@ from webob import exc as web_exc import webtest from neutron.api import extensions -from neutron.api.v2 import attributes from neutron.api.v2 import router from neutron import context from neutron.extensions import providernet as pnet from neutron import manager from neutron.openstack.common import uuidutils from neutron import quota +from neutron.tests import tools from neutron.tests.unit.api import test_extensions from neutron.tests.unit.api.v2 import test_base from neutron.tests.unit import testlib_api @@ -57,10 +57,7 @@ class ProvidernetExtensionTestCase(testlib_api.WebTestCase): # Ensure existing ExtensionManager is not used extensions.PluginAwareExtensionManager._instance = None - # Save the global RESOURCE_ATTRIBUTE_MAP - self.saved_attr_map = {} - for resource, attrs in attributes.RESOURCE_ATTRIBUTE_MAP.iteritems(): - self.saved_attr_map[resource] = attrs.copy() + self.useFixture(tools.AttributeMapMemento()) # Update the plugin and extensions path self.setup_coreplugin(plugin) @@ -77,17 +74,12 @@ class ProvidernetExtensionTestCase(testlib_api.WebTestCase): ext_mgr = ProviderExtensionManager() self.ext_mdw = test_extensions.setup_extensions_middleware(ext_mgr) self.addCleanup(self._plugin_patcher.stop) - self.addCleanup(self._restore_attribute_map) self.api = webtest.TestApp(router.APIRouter()) quota.QUOTAS._driver = None cfg.CONF.set_override('quota_driver', 'neutron.quota.ConfDriver', group='QUOTAS') - def _restore_attribute_map(self): - # Restore the global RESOURCE_ATTRIBUTE_MAP - attributes.RESOURCE_ATTRIBUTE_MAP = self.saved_attr_map - def _prepare_net_data(self): return {'name': 'net1', pnet.NETWORK_TYPE: 'sometype', diff --git a/neutron/tests/unit/extensions/test_quotasv2.py b/neutron/tests/unit/extensions/test_quotasv2.py index 349706b55..af87c4a76 100644 --- a/neutron/tests/unit/extensions/test_quotasv2.py +++ b/neutron/tests/unit/extensions/test_quotasv2.py @@ -22,7 +22,6 @@ from webob import exc import webtest from neutron.api import extensions -from neutron.api.v2 import attributes from neutron.common import config from neutron.common import constants from neutron.common import exceptions @@ -30,6 +29,7 @@ from neutron import context from neutron.db import quota_db from neutron import quota from neutron.tests import base +from neutron.tests import tools from neutron.tests.unit.api.v2 import test_base from neutron.tests.unit import testlib_api @@ -45,10 +45,7 @@ class QuotaExtensionTestCase(testlib_api.WebTestCase): # Ensure existing ExtensionManager is not used extensions.PluginAwareExtensionManager._instance = None - # Save the global RESOURCE_ATTRIBUTE_MAP - self.saved_attr_map = {} - for resource, attrs in attributes.RESOURCE_ATTRIBUTE_MAP.iteritems(): - self.saved_attr_map[resource] = attrs.copy() + self.useFixture(tools.AttributeMapMemento()) # Create the default configurations self.config_parse() @@ -75,8 +72,6 @@ class QuotaExtensionTestCase(testlib_api.WebTestCase): def tearDown(self): self.api = None self.plugin = None - # Restore the global RESOURCE_ATTRIBUTE_MAP - attributes.RESOURCE_ATTRIBUTE_MAP = self.saved_attr_map super(QuotaExtensionTestCase, self).tearDown() def _test_quota_default_values(self, expected_values): diff --git a/neutron/tests/unit/plugins/cisco/n1kv/test_n1kv_plugin.py b/neutron/tests/unit/plugins/cisco/n1kv/test_n1kv_plugin.py index b388e083f..787f0345d 100644 --- a/neutron/tests/unit/plugins/cisco/n1kv/test_n1kv_plugin.py +++ b/neutron/tests/unit/plugins/cisco/n1kv/test_n1kv_plugin.py @@ -33,6 +33,7 @@ from neutron.plugins.cisco.extensions import network_profile from neutron.plugins.cisco.extensions import policy_profile from neutron.plugins.cisco.n1kv import n1kv_client from neutron.plugins.cisco.n1kv import n1kv_neutron_plugin +from neutron.tests import tools from neutron.tests.unit import _test_extension_portbindings as test_bindings from neutron.tests.unit.api.v2 import test_base from neutron.tests.unit.db import test_db_base_plugin_v2 as test_plugin @@ -225,26 +226,18 @@ class N1kvPluginTestCase(test_plugin.NeutronDbPluginV2TestCase): neutron_extensions.append_api_extensions_path(extensions.__path__) - # Save the original RESOURCE_ATTRIBUTE_MAP - self.saved_attr_map = {} - for resource, attrs in attributes.RESOURCE_ATTRIBUTE_MAP.items(): - self.saved_attr_map[resource] = attrs.copy() + self.useFixture(tools.AttributeMapMemento()) # Update the RESOURCE_ATTRIBUTE_MAP with n1kv specific extended attrs. attributes.RESOURCE_ATTRIBUTE_MAP["networks"].update( n1kv.EXTENDED_ATTRIBUTES_2_0["networks"]) attributes.RESOURCE_ATTRIBUTE_MAP["ports"].update( n1kv.EXTENDED_ATTRIBUTES_2_0["ports"]) - self.addCleanup(self.restore_resource_attribute_map) super(N1kvPluginTestCase, self).setUp(self._plugin_name, ext_mgr=ext_mgr) # Create some of the database entries that we require. self._make_test_profile() self._make_test_policy_profile() - def restore_resource_attribute_map(self): - # Restore the original RESOURCE_ATTRIBUTE_MAP - attributes.RESOURCE_ATTRIBUTE_MAP = self.saved_attr_map - class TestN1kvNetworkProfiles(N1kvPluginTestCase): def _prepare_net_profile_data(self, diff --git a/neutron/tests/unit/plugins/ml2/test_security_group.py b/neutron/tests/unit/plugins/ml2/test_security_group.py index 6b1c3d016..75f2a4108 100644 --- a/neutron/tests/unit/plugins/ml2/test_security_group.py +++ b/neutron/tests/unit/plugins/ml2/test_security_group.py @@ -18,10 +18,10 @@ import contextlib import math import mock -from neutron.api.v2 import attributes from neutron.common import constants as const from neutron.extensions import securitygroup as ext_sg from neutron import manager +from neutron.tests import tools from neutron.tests.unit.agent import test_securitygroups_rpc as test_sg_rpc from neutron.tests.unit.api.v2 import test_base from neutron.tests.unit.extensions import test_securitygroup as test_sg @@ -39,16 +39,11 @@ class Ml2SecurityGroupsTestCase(test_sg.SecurityGroupDBTestCase): notifier_cls = notifier_p.start() self.notifier = mock.Mock() notifier_cls.return_value = self.notifier - self._attribute_map_bk_ = {} - for item in attributes.RESOURCE_ATTRIBUTE_MAP: - self._attribute_map_bk_[item] = (attributes. - RESOURCE_ATTRIBUTE_MAP[item]. - copy()) + self.useFixture(tools.AttributeMapMemento()) super(Ml2SecurityGroupsTestCase, self).setUp(PLUGIN_NAME) def tearDown(self): super(Ml2SecurityGroupsTestCase, self).tearDown() - attributes.RESOURCE_ATTRIBUTE_MAP = self._attribute_map_bk_ class TestMl2SecurityGroups(Ml2SecurityGroupsTestCase, diff --git a/neutron/tests/unit/plugins/oneconvergence/test_security_group.py b/neutron/tests/unit/plugins/oneconvergence/test_security_group.py index 9820f9cfd..dcde1915a 100644 --- a/neutron/tests/unit/plugins/oneconvergence/test_security_group.py +++ b/neutron/tests/unit/plugins/oneconvergence/test_security_group.py @@ -16,10 +16,10 @@ import uuid import mock -from neutron.api.v2 import attributes from neutron.extensions import securitygroup as ext_sg from neutron import manager from neutron.plugins.oneconvergence import plugin as nvsd_plugin +from neutron.tests import tools from neutron.tests.unit.agent import test_securitygroups_rpc as test_sg_rpc from neutron.tests.unit.extensions import test_securitygroup as test_sg @@ -49,11 +49,7 @@ class OneConvergenceSecurityGroupsTestCase(test_sg.SecurityGroupDBTestCase): notifier_cls = mock.patch(AGENTNOTIFIER).start() self.notifier = mock.Mock() notifier_cls.return_value = self.notifier - self._attribute_map_bk_ = {} - for item in attributes.RESOURCE_ATTRIBUTE_MAP: - self._attribute_map_bk_[item] = (attributes. - RESOURCE_ATTRIBUTE_MAP[item]. - copy()) + self.useFixture(tools.AttributeMapMemento()) with mock.patch.object(nvsd_plugin.OneConvergencePluginV2, 'oneconvergence_init', new=mocked_oneconvergence_init): @@ -62,7 +58,6 @@ class OneConvergenceSecurityGroupsTestCase(test_sg.SecurityGroupDBTestCase): def tearDown(self): super(OneConvergenceSecurityGroupsTestCase, self).tearDown() - attributes.RESOURCE_ATTRIBUTE_MAP = self._attribute_map_bk_ class TestOneConvergenceSGServerRpcCallBack( diff --git a/neutron/tests/unit/plugins/openvswitch/test_agent_scheduler.py b/neutron/tests/unit/plugins/openvswitch/test_agent_scheduler.py index 6a21e3b2d..20be55287 100644 --- a/neutron/tests/unit/plugins/openvswitch/test_agent_scheduler.py +++ b/neutron/tests/unit/plugins/openvswitch/test_agent_scheduler.py @@ -41,6 +41,7 @@ from neutron import manager from neutron.openstack.common import uuidutils from neutron.plugins.common import constants as service_constants from neutron.tests import fake_notifier +from neutron.tests import tools from neutron.tests.unit.api import test_extensions from neutron.tests.unit.db import test_db_base_plugin_v2 as test_plugin from neutron.tests.unit.extensions import test_agent @@ -245,10 +246,7 @@ class OvsAgentSchedulerTestCaseBase(test_l3.L3NatTestCaseMixin, 'TestL3NatAgentSchedulingServicePlugin') def setUp(self): - # Save the global RESOURCE_ATTRIBUTE_MAP before loading plugin - self.saved_attr_map = {} - for resource, attrs in attributes.RESOURCE_ATTRIBUTE_MAP.iteritems(): - self.saved_attr_map[resource] = attrs.copy() + self.useFixture(tools.AttributeMapMemento()) if self.l3_plugin: service_plugins = {'l3_plugin_name': self.l3_plugin} else: @@ -264,7 +262,6 @@ class OvsAgentSchedulerTestCaseBase(test_l3.L3NatTestCaseMixin, # the global attribute map attributes.RESOURCE_ATTRIBUTE_MAP.update( agent.RESOURCE_ATTRIBUTE_MAP) - self.addCleanup(self.restore_attribute_map) self.l3agentscheduler_dbMinxin = ( manager.NeutronManager.get_service_plugins().get( service_constants.L3_ROUTER_NAT)) @@ -279,10 +276,6 @@ class OvsAgentSchedulerTestCaseBase(test_l3.L3NatTestCaseMixin, 'neutron.extensions.dhcpagentscheduler.notify') self.patched_dhcp_notify = self.dhcp_notify_p.start() - def restore_attribute_map(self): - # Restore the original RESOURCE_ATTRIBUTE_MAP - attributes.RESOURCE_ATTRIBUTE_MAP = self.saved_attr_map - class OvsAgentSchedulerTestCase(OvsAgentSchedulerTestCaseBase): @@ -1307,10 +1300,7 @@ class OvsDhcpAgentNotifierTestCase(test_l3.L3NatTestCaseMixin, plugin_str = 'neutron.plugins.ml2.plugin.Ml2Plugin' def setUp(self): - # Save the global RESOURCE_ATTRIBUTE_MAP before loading plugin - self.saved_attr_map = {} - for resource, attrs in attributes.RESOURCE_ATTRIBUTE_MAP.iteritems(): - self.saved_attr_map[resource] = attrs.copy() + self.useFixture(tools.AttributeMapMemento()) super(OvsDhcpAgentNotifierTestCase, self).setUp(self.plugin_str) self.dhcp_notifier = dhcp_rpc_agent_api.DhcpAgentNotifyAPI() self.dhcp_notifier_cast = mock.patch( @@ -1325,13 +1315,8 @@ class OvsDhcpAgentNotifierTestCase(test_l3.L3NatTestCaseMixin, # the global attribute map attributes.RESOURCE_ATTRIBUTE_MAP.update( agent.RESOURCE_ATTRIBUTE_MAP) - self.addCleanup(self.restore_attribute_map) fake_notifier.reset() - def restore_attribute_map(self): - # Restore the original RESOURCE_ATTRIBUTE_MAP - attributes.RESOURCE_ATTRIBUTE_MAP = self.saved_attr_map - def test_network_add_to_dhcp_agent_notification(self): with self.network() as net1: network_id = net1['network']['id'] @@ -1474,10 +1459,9 @@ class OvsL3AgentNotifierTestCase(test_l3.L3NatTestCaseMixin, self.dhcp_notifier = mock.Mock(name='dhcp_notifier') self.dhcp_notifier_cls = self.dhcp_notifier_cls_p.start() self.dhcp_notifier_cls.return_value = self.dhcp_notifier - # Save the global RESOURCE_ATTRIBUTE_MAP - self.saved_attr_map = {} - for resource, attrs in attributes.RESOURCE_ATTRIBUTE_MAP.iteritems(): - self.saved_attr_map[resource] = attrs.copy() + + self.useFixture(tools.AttributeMapMemento()) + if self.l3_plugin: service_plugins = {'l3_plugin_name': self.l3_plugin} else: @@ -1493,13 +1477,8 @@ class OvsL3AgentNotifierTestCase(test_l3.L3NatTestCaseMixin, # the global attribute map attributes.RESOURCE_ATTRIBUTE_MAP.update( agent.RESOURCE_ATTRIBUTE_MAP) - self.addCleanup(self.restore_attribute_map) fake_notifier.reset() - def restore_attribute_map(self): - # Restore the original RESOURCE_ATTRIBUTE_MAP - attributes.RESOURCE_ATTRIBUTE_MAP = self.saved_attr_map - def test_router_add_to_l3_agent_notification(self): l3_plugin = (manager.NeutronManager.get_service_plugins() [service_constants.L3_ROUTER_NAT])