From 4d90e8949c77a399be53f23fbddfab4c06de4fd9 Mon Sep 17 00:00:00 2001 From: linb Date: Wed, 24 Feb 2016 10:54:39 +0800 Subject: [PATCH] Fix router intf port deleted when are in use When trying to delete router interface which is in use such as FIP case, the request should be rejected and we should not delete the port the backend. Fixes-Bug: #1548624 Change-Id: I3a77f7dd47faca84e15950f40cc43a74d24ffab9 --- vmware_nsx/plugins/nsx_v3/plugin.py | 4 +++ vmware_nsx/tests/unit/nsx_v3/test_plugin.py | 34 +++++++++++++++++++++ 2 files changed, 38 insertions(+) diff --git a/vmware_nsx/plugins/nsx_v3/plugin.py b/vmware_nsx/plugins/nsx_v3/plugin.py index 2f74481ef8..8bd4443a8a 100644 --- a/vmware_nsx/plugins/nsx_v3/plugin.py +++ b/vmware_nsx/plugins/nsx_v3/plugin.py @@ -1458,12 +1458,16 @@ class NsxV3Plugin(addr_pair_db.AllowedAddressPairsMixin, port = self._get_port(context, port_id) if port.get('fixed_ips'): subnet_id = port['fixed_ips'][0]['subnet_id'] + self._confirm_router_interface_not_in_use( + context, router_id, subnet_id) if not (port['device_owner'] in const.ROUTER_INTERFACE_OWNERS and port['device_id'] == router_id): raise l3.RouterInterfaceNotFound(router_id=router_id, port_id=port_id) elif 'subnet_id' in interface_info: subnet_id = interface_info['subnet_id'] + self._confirm_router_interface_not_in_use( + context, router_id, subnet_id) subnet = self._get_subnet(context, subnet_id) rport_qry = context.session.query(models_v2.Port) ports = rport_qry.filter_by( diff --git a/vmware_nsx/tests/unit/nsx_v3/test_plugin.py b/vmware_nsx/tests/unit/nsx_v3/test_plugin.py index b54c881060..e81ec235e4 100644 --- a/vmware_nsx/tests/unit/nsx_v3/test_plugin.py +++ b/vmware_nsx/tests/unit/nsx_v3/test_plugin.py @@ -14,6 +14,7 @@ # limitations under the License. import mock import six +from webob import exc from neutron.api.v2 import attributes from neutron.common import constants @@ -378,6 +379,39 @@ class TestL3NatTestCase(L3NatTest, self._router_interface_action('remove', r1['router']['id'], s1['subnet']['id'], None) + def test_router_remove_interface_inuse_return_409(self): + with self.router() as r1,\ + self.subnet() as ext_subnet,\ + self.subnet(cidr='11.0.0.0/24') as s1: + self._set_net_external(ext_subnet['subnet']['network_id']) + self._router_interface_action( + 'add', r1['router']['id'], + s1['subnet']['id'], None) + self._add_external_gateway_to_router( + r1['router']['id'], + ext_subnet['subnet']['network_id']) + with self.port(subnet=s1,) as p: + fip_res = self._create_floatingip( + self.fmt, + ext_subnet['subnet']['network_id'], + subnet_id=ext_subnet['subnet']['id'], + port_id=p['port']['id']) + fip = self.deserialize(self.fmt, fip_res) + self._router_interface_action( + 'remove', + r1['router']['id'], + s1['subnet']['id'], + None, + expected_code=exc.HTTPConflict.code) + self._delete('floatingips', fip['floatingip']['id']) + self._remove_external_gateway_from_router( + r1['router']['id'], + ext_subnet['subnet']['network_id']) + self._router_interface_action('remove', + r1['router']['id'], + s1['subnet']['id'], + None) + def test_router_update_on_external_port(self): with self.router() as r: with self.subnet(cidr='10.0.1.0/24') as s: