From e85ff2264e681308760f1c46e350f138582d2957 Mon Sep 17 00:00:00 2001 From: Ilya Shakhat Date: Thu, 24 Jul 2014 15:14:26 +0400 Subject: [PATCH] Avoid RequestURITooLong exception in metadata agent Length of API port query is proportional to number of networks and may exceed URI limit. The solution is to query ports by given ip address only and then filter them by network_id. Closes bug 1348097 Change-Id: I2a87d6b215df380b24dd5ebb24947e8729f3f6fb --- neutron/agent/metadata/agent.py | 7 ++--- neutron/tests/unit/test_metadata_agent.py | 31 +++++++++++++---------- 2 files changed, 21 insertions(+), 17 deletions(-) diff --git a/neutron/agent/metadata/agent.py b/neutron/agent/metadata/agent.py index c56c78d7a..9365c4f02 100644 --- a/neutron/agent/metadata/agent.py +++ b/neutron/agent/metadata/agent.py @@ -157,11 +157,12 @@ class MetadataProxyHandler(object): """ qclient = self._get_neutron_client() - - return qclient.list_ports( - network_id=networks, + all_ports = qclient.list_ports( fixed_ips=['ip_address=%s' % remote_address])['ports'] + networks = set(networks) + return [p for p in all_ports if p['network_id'] in networks] + def _get_ports(self, remote_address, network_id=None, router_id=None): """Search for all ports that contain passed ip address and belongs to given network. diff --git a/neutron/tests/unit/test_metadata_agent.py b/neutron/tests/unit/test_metadata_agent.py index 6a5c671d8..5c7cb59c1 100644 --- a/neutron/tests/unit/test_metadata_agent.py +++ b/neutron/tests/unit/test_metadata_agent.py @@ -130,27 +130,29 @@ class TestMetadataProxyHandlerCache(base.BaseTestCase): def test_get_ports_for_remote_address(self): remote_address = 'remote_address' - networks = 'networks' + networks = ('network_id1', 'network_id3') fixed_ips = ["ip_address=%s" % remote_address] + expected_ports = [{'network_id': 'network_id1', 'something': 42}] + mock_list_ports = self.qclient.return_value.list_ports + mock_list_ports.return_value = {'ports': [{'network_id': 'network_id1', + 'something': 42}, + {'network_id': 'network_id2', + 'something_else': 64}]} ports = self.handler._get_ports_for_remote_address(remote_address, networks) - mock_list_ports = self.qclient.return_value.list_ports - mock_list_ports.assert_called_once_with( - network_id=networks, fixed_ips=fixed_ips) - self.assertEqual(mock_list_ports.return_value.__getitem__('ports'), - ports) + mock_list_ports.assert_called_once_with(fixed_ips=fixed_ips) + self.assertEqual(expected_ports, ports) def _get_ports_for_remote_address_cache_hit_helper(self): remote_address = 'remote_address' networks = ('net1', 'net2') fixed_ips = ["ip_address=%s" % remote_address] - ports = self.handler._get_ports_for_remote_address(remote_address, - networks) mock_list_ports = self.qclient.return_value.list_ports + mock_list_ports.return_value = {'ports': [{'network_id': 'net1', + 'something': 42}]} + self.handler._get_ports_for_remote_address(remote_address, networks) mock_list_ports.assert_called_once_with( - network_id=networks, fixed_ips=fixed_ips) - self.assertEqual( - mock_list_ports.return_value.__getitem__('ports'), ports) + fixed_ips=fixed_ips) self.assertEqual(1, mock_list_ports.call_count) self.handler._get_ports_for_remote_address(remote_address, networks) @@ -237,7 +239,6 @@ class TestMetadataProxyHandlerCache(base.BaseTestCase): expected.extend([ new_qclient_call, mock.call().list_ports( - network_id=networks or tuple(), fixed_ips=['ip_address=192.168.1.1']) ]) @@ -254,7 +255,8 @@ class TestMetadataProxyHandlerCache(base.BaseTestCase): networks = ('net1', 'net2') ports = [ [{'network_id': 'net1'}, {'network_id': 'net2'}], - [{'device_id': 'device_id', 'tenant_id': 'tenant_id'}] + [{'device_id': 'device_id', 'tenant_id': 'tenant_id', + 'network_id': 'net1'}] ] self.assertEqual( @@ -290,7 +292,8 @@ class TestMetadataProxyHandlerCache(base.BaseTestCase): ports = [ [{'device_id': 'device_id', - 'tenant_id': 'tenant_id'}] + 'tenant_id': 'tenant_id', + 'network_id': 'the_id'}] ] self.assertEqual( -- 2.45.2