From 18c532377a2f6d87adef80465fea7ed50d5a17d1 Mon Sep 17 00:00:00 2001 From: Ankur Gupta Date: Wed, 12 Oct 2016 22:39:35 -0500 Subject: [PATCH] Network L3 Router Commands for OSC Implements: blueprint network-l3-commands Co-Authored-By: Akihiro Motoki Change-Id: Ia24d76227e164062e89a74c1621b8acb830b26cf --- .../cli/command-objects/network-agent.rst | 121 +++++++++--- doc/source/cli/command-objects/router.rst | 5 + openstackclient/network/v2/network_agent.py | 121 +++++++++--- openstackclient/network/v2/router.py | 32 +++- .../network/v2/test_network_agent.py | 36 ++++ .../functional/network/v2/test_router.py | 34 ++++ .../unit/network/v2/test_network_agent.py | 173 +++++++++++++++--- .../tests/unit/network/v2/test_router.py | 50 +++++ ...work-l3-adv-commands-cc1df715a184f1b2.yaml | 8 + setup.cfg | 2 + 10 files changed, 504 insertions(+), 78 deletions(-) create mode 100644 releasenotes/notes/bp-network-l3-adv-commands-cc1df715a184f1b2.yaml diff --git a/doc/source/cli/command-objects/network-agent.rst b/doc/source/cli/command-objects/network-agent.rst index f69d0ece69..2ceb263f1b 100644 --- a/doc/source/cli/command-objects/network-agent.rst +++ b/doc/source/cli/command-objects/network-agent.rst @@ -33,7 +33,34 @@ Add network to an agent .. describe:: - Network to be added to an agent (ID or name) + Network to be added to an agent (name or ID) + +network agent add router +------------------------ + +Add router to an agent + +.. program:: network agent add router +.. code:: bash + + openstack network agent add router + [--l3] + + + +.. option:: --l3 + + Add router to L3 agent + +.. _network_agent_add_router-agent-id: +.. describe:: + + Agent to which a router is added (ID only) + +.. _network_agent_add_router-router: +.. describe:: + + Router to be added to an agent (name or ID) network agent delete -------------------- @@ -62,7 +89,8 @@ List network agents openstack network agent list [--agent-type ] [--host ] - [--network ] + [--network | --router ] + [--long] .. option:: --agent-type @@ -77,7 +105,69 @@ List network agents .. option:: --network - List agents hosting a network (ID or name) + List agents hosting a network (name or ID) + +.. option:: --router + + List agents hosting this router (name or ID) + +.. option:: --long + + List additional fields in output + +network agent remove network +---------------------------- + +Remove network from an agent + +.. program:: network agent remove network +.. code:: bash + + openstack network agent remove network + [--dhcp] + + + +.. option:: --dhcp + + Remove network from DHCP agent + +.. _network_agent_remove_network-agent-id: +.. describe:: + + Agent to which a network is removed (ID only) + +.. _network_agent_remove_network-network: +.. describe:: + + Network to be removed from an agent (name or ID) + +network agent remove router +--------------------------- + +Remove router from an agent + +.. program:: network agent remove router +.. code:: bash + + openstack agent remove router + [--l3] + + + +.. option:: --l3 + + Remove router from L3 agent + +.. _network_agent_remove_router-agent-id: +.. describe:: + + Agent from which router will be removed (ID only) + +.. _network_agent_remove_router-router: +.. describe:: + + Router to be removed from an agent (name or ID) network agent set ----------------- @@ -124,28 +214,3 @@ Display network agent details .. describe:: Network agent to display (ID only) - -network agent remove network ----------------------------- - -Remove network from an agent - -.. program:: network agent remove network -.. code:: bash - - openstack network agent remove network - [--dhcp] - - - -.. describe:: --dhcp - - Remove network from DHCP agent. - -.. describe:: - - Agent to which a network is removed (ID only) - -.. describe:: - - Network to be removed from an agent (ID or name) diff --git a/doc/source/cli/command-objects/router.rst b/doc/source/cli/command-objects/router.rst index 50e791ea7d..8bdf81dbf7 100644 --- a/doc/source/cli/command-objects/router.rst +++ b/doc/source/cli/command-objects/router.rst @@ -155,6 +155,11 @@ List routers [--enable | --disable] [--long] [--project [--project-domain ]] + [--agent ] + +.. option:: --agent + + List routers hosted by an agent (ID only) .. option:: --long diff --git a/openstackclient/network/v2/network_agent.py b/openstackclient/network/v2/network_agent.py index 1334f77e17..ed4970a488 100644 --- a/openstackclient/network/v2/network_agent.py +++ b/openstackclient/network/v2/network_agent.py @@ -26,10 +26,16 @@ from openstackclient.network import sdk_utils LOG = logging.getLogger(__name__) +def _format_alive(alive): + return ":-)" if alive else "XXX" + + def _format_admin_state(state): return 'UP' if state else 'DOWN' _formatters = { + 'is_alive': _format_alive, + 'alive': _format_alive, 'admin_state_up': _format_admin_state, 'is_admin_state_up': _format_admin_state, 'configurations': utils.format_dict, @@ -60,7 +66,7 @@ class AddNetworkToAgent(command.Command): parser.add_argument( 'network', metavar='', - help=_('Network to be added to an agent (ID or name)')) + help=_('Network to be added to an agent (name or ID)')) return parser @@ -78,6 +84,37 @@ class AddNetworkToAgent(command.Command): exceptions.CommandError(msg) +class AddRouterToAgent(command.Command): + _description = _("Add router to an agent") + + def get_parser(self, prog_name): + parser = super(AddRouterToAgent, self).get_parser(prog_name) + parser.add_argument( + '--l3', + action='store_true', + help=_('Add router to an L3 agent') + ) + parser.add_argument( + 'agent_id', + metavar='', + help=_("Agent to which a router is added (ID only)") + ) + parser.add_argument( + 'router', + metavar='', + help=_("Router to be added to an agent (name or ID)") + ) + + return parser + + def take_action(self, parsed_args): + client = self.app.client_manager.network + agent = client.get_agent(parsed_args.agent_id) + router = client.find_router(parsed_args.router, ignore_missing=False) + if parsed_args.l3: + client.add_router_to_agent(agent, router) + + class DeleteNetworkAgent(command.Command): _description = _("Delete network agent(s)") @@ -135,11 +172,24 @@ class ListNetworkAgent(command.Lister): metavar='', help=_("List only agents running on the specified host") ) - parser.add_argument( + agent_type_group = parser.add_mutually_exclusive_group() + agent_type_group.add_argument( '--network', metavar='', help=_('List agents hosting a network (name or ID)') ) + agent_type_group.add_argument( + '--router', + metavar='', + help=_('List agents hosting this router (name or ID)') + ) + parser.add_argument( + '--long', + action='store_true', + default=False, + help=_("List additional fields in output") + ) + return parser def take_action(self, parsed_args): @@ -178,28 +228,18 @@ class ListNetworkAgent(command.Lister): } filters = {} + if parsed_args.network is not None: - columns = ( - 'id', - 'host', - 'is_admin_state_up', - 'is_alive', - ) - column_headers = ( - 'ID', - 'Host', - 'Admin State Up', - 'Alive', - ) network = client.find_network( parsed_args.network, ignore_missing=False) data = client.network_hosting_dhcp_agents(network) - - return (column_headers, - (utils.get_item_properties( - s, columns, - formatters=_formatters, - ) for s in data)) + elif parsed_args.router is not None: + if parsed_args.long: + columns += ('ha_state',) + column_headers += ('HA State',) + router = client.find_router(parsed_args.router, + ignore_missing=False) + data = client.routers_hosting_l3_agents(router) else: if parsed_args.agent_type is not None: filters['agent_type'] = key_value[parsed_args.agent_type] @@ -207,10 +247,10 @@ class ListNetworkAgent(command.Lister): filters['host'] = parsed_args.host data = client.agents(**filters) - return (column_headers, - (utils.get_item_properties( - s, columns, formatters=_formatters, - ) for s in data)) + return (column_headers, + (utils.get_item_properties( + s, columns, formatters=_formatters, + ) for s in data)) class RemoveNetworkFromAgent(command.Command): @@ -229,7 +269,7 @@ class RemoveNetworkFromAgent(command.Command): parser.add_argument( 'network', metavar='', - help=_('Network to be removed from an agent (ID or name)')) + help=_('Network to be removed from an agent (name or ID)')) return parser def take_action(self, parsed_args): @@ -246,6 +286,37 @@ class RemoveNetworkFromAgent(command.Command): exceptions.CommandError(msg) +class RemoveRouterFromAgent(command.Command): + _description = _("Remove router from an agent") + + def get_parser(self, prog_name): + parser = super(RemoveRouterFromAgent, self).get_parser(prog_name) + parser.add_argument( + '--l3', + action='store_true', + help=_('Remove router from an L3 agent') + ) + parser.add_argument( + 'agent_id', + metavar='', + help=_("Agent from which router will be removed (ID only)") + ) + parser.add_argument( + 'router', + metavar='', + help=_("Router to be removed from an agent (name or ID)") + ) + + return parser + + def take_action(self, parsed_args): + client = self.app.client_manager.network + agent = client.get_agent(parsed_args.agent_id) + router = client.find_router(parsed_args.router, ignore_missing=False) + if parsed_args.l3: + client.remove_router_from_agent(agent, router) + + # TODO(huanxuan): Use the SDK resource mapped attribute names once the # OSC minimum requirements include SDK 1.0. class SetNetworkAgent(command.Command): diff --git a/openstackclient/network/v2/router.py b/openstackclient/network/v2/router.py index 0da91baa44..8db0c4393b 100644 --- a/openstackclient/network/v2/router.py +++ b/openstackclient/network/v2/router.py @@ -305,11 +305,18 @@ class ListRouter(command.Lister): help=_("List routers according to their project (name or ID)") ) identity_common.add_project_domain_option_to_parser(parser) + parser.add_argument( + '--agent', + metavar='', + help=_("List routers hosted by an agent (ID only)") + ) + return parser def take_action(self, parsed_args): identity_client = self.app.client_manager.identity client = self.app.client_manager.network + columns = ( 'id', 'name', @@ -349,6 +356,16 @@ class ListRouter(command.Lister): ).id args['tenant_id'] = project_id args['project_id'] = project_id + + if parsed_args.agent is not None: + agent = client.get_agent(parsed_args.agent) + data = client.agent_hosted_routers(agent) + # NOTE: Networking API does not support filtering by parameters, + # so we need filtering in the client side. + data = [d for d in data if self._filter_match(d, args)] + else: + data = client.routers(**args) + if parsed_args.long: columns = columns + ( 'routes', @@ -368,13 +385,26 @@ class ListRouter(command.Lister): 'Availability zones', ) - data = client.routers(**args) return (column_headers, (utils.get_item_properties( s, columns, formatters=_formatters, ) for s in data)) + @staticmethod + def _filter_match(data, conditions): + for key, value in conditions.items(): + try: + if getattr(data, key) != value: + return False + except AttributeError: + # Some filter attributes like tenant_id or admin_state_up + # are backward compatibility in older OpenStack SDK support. + # They does not exist in the latest release. + # In this case we just skip checking such filter condition. + continue + return True + class RemovePortFromRouter(command.Command): _description = _("Remove a port from a router") diff --git a/openstackclient/tests/functional/network/v2/test_network_agent.py b/openstackclient/tests/functional/network/v2/test_network_agent.py index 1648795513..0c74ea1d05 100644 --- a/openstackclient/tests/functional/network/v2/test_network_agent.py +++ b/openstackclient/tests/functional/network/v2/test_network_agent.py @@ -137,3 +137,39 @@ class NetworkAgentListTests(common.NetworkTests): self.assertIn( agent_id, col_name ) + + def test_network_agent_list_routers(self): + """Add agent to router, list agents on router, delete.""" + name = uuid.uuid4().hex + cmd_output = json.loads(self.openstack( + 'router create -f json ' + name)) + + self.addCleanup(self.openstack, 'router delete ' + name) + # Get router ID + router_id = cmd_output['id'] + # Get l3 agent id + cmd_output = json.loads(self.openstack( + 'network agent list -f json --agent-type l3')) + + # Check at least one L3 agent is included in the response. + self.assertTrue(cmd_output) + agent_id = cmd_output[0]['ID'] + + # Add router to agent + self.openstack( + 'network agent add router --l3 ' + agent_id + ' ' + router_id) + + # Test router list --agent + cmd_output = json.loads(self.openstack( + 'network agent list -f json --router ' + router_id)) + + agent_ids = [x['ID'] for x in cmd_output] + self.assertIn(agent_id, agent_ids) + + # Remove router from agent + self.openstack( + 'network agent remove router --l3 ' + agent_id + ' ' + router_id) + cmd_output = json.loads(self.openstack( + 'network agent list -f json --router ' + router_id)) + agent_ids = [x['ID'] for x in cmd_output] + self.assertNotIn(agent_id, agent_ids) diff --git a/openstackclient/tests/functional/network/v2/test_router.py b/openstackclient/tests/functional/network/v2/test_router.py index 313feefc01..2e5cb5ef55 100644 --- a/openstackclient/tests/functional/network/v2/test_router.py +++ b/openstackclient/tests/functional/network/v2/test_router.py @@ -151,6 +151,40 @@ class RouterTests(common.NetworkTests): self.assertIn(name1, names) self.assertIn(name2, names) + def test_router_list_l3_agent(self): + """Tests create router, add l3 agent, list, delete""" + name = uuid.uuid4().hex + cmd_output = json.loads(self.openstack( + 'router create -f json ' + name)) + + self.addCleanup(self.openstack, 'router delete ' + name) + # Get router ID + router_id = cmd_output['id'] + # Get l3 agent id + cmd_output = json.loads(self.openstack( + 'network agent list -f json --agent-type l3')) + + # Check at least one L3 agent is included in the response. + self.assertTrue(cmd_output) + agent_id = cmd_output[0]['ID'] + + # Add router to agent + self.openstack( + 'network agent add router --l3 ' + agent_id + ' ' + router_id) + + cmd_output = json.loads(self.openstack( + 'router list -f json --agent ' + agent_id)) + router_ids = [x['ID'] for x in cmd_output] + self.assertIn(router_id, router_ids) + + # Remove router from agent + self.openstack( + 'network agent remove router --l3 ' + agent_id + ' ' + router_id) + cmd_output = json.loads(self.openstack( + 'router list -f json --agent ' + agent_id)) + router_ids = [x['ID'] for x in cmd_output] + self.assertNotIn(router_id, router_ids) + def test_router_set_show_unset(self): """Tests create router, set, unset, show""" diff --git a/openstackclient/tests/unit/network/v2/test_network_agent.py b/openstackclient/tests/unit/network/v2/test_network_agent.py index 9bb3f090f3..12e40cdbc8 100644 --- a/openstackclient/tests/unit/network/v2/test_network_agent.py +++ b/openstackclient/tests/unit/network/v2/test_network_agent.py @@ -73,6 +73,46 @@ class TestAddNetworkToAgent(TestNetworkAgent): self.agent, self.net) +class TestAddRouterAgent(TestNetworkAgent): + + _router = network_fakes.FakeRouter.create_one_router() + _agent = network_fakes.FakeNetworkAgent.create_one_network_agent() + + def setUp(self): + super(TestAddRouterAgent, self).setUp() + self.network.add_router_to_agent = mock.Mock() + self.cmd = network_agent.AddRouterToAgent(self.app, self.namespace) + self.network.get_agent = mock.Mock(return_value=self._agent) + self.network.find_router = mock.Mock(return_value=self._router) + + def test_add_no_options(self): + arglist = [] + verifylist = [] + + # Missing agent ID will cause command to bail + self.assertRaises(tests_utils.ParserException, self.check_parser, + self.cmd, arglist, verifylist) + + def test_add_router_required_options(self): + arglist = [ + self._agent.id, + self._router.id, + '--l3', + ] + verifylist = [ + ('l3', True), + ('agent_id', self._agent.id), + ('router', self._router.id), + ] + + parsed_args = self.check_parser(self.cmd, arglist, verifylist) + result = self.cmd.take_action(parsed_args) + + self.network.add_router_to_agent.assert_called_with( + self._agent, self._router) + self.assertIsNone(result) + + class TestDeleteNetworkAgent(TestNetworkAgent): network_agents = ( @@ -171,34 +211,16 @@ class TestListNetworkAgent(TestNetworkAgent): ) data = [] for agent in network_agents: - agent.agent_type = 'DHCP agent' data.append(( agent.id, agent.agent_type, agent.host, agent.availability_zone, - agent.alive, + network_agent._format_alive(agent.alive), network_agent._format_admin_state(agent.admin_state_up), agent.binary, )) - network_agent_columns = ( - 'ID', - 'Host', - 'Admin State Up', - 'Alive', - ) - - network_agent_data = [] - - for agent in network_agents: - network_agent_data.append(( - agent.id, - agent.host, - network_agent._format_admin_state(agent.admin_state_up), - agent.alive, - )) - def setUp(self): super(TestListNetworkAgent, self).setUp() self.network.agents = mock.Mock( @@ -213,6 +235,14 @@ class TestListNetworkAgent(TestNetworkAgent): self.network.network_hosting_dhcp_agents = mock.Mock( return_value=self.network_agents) + self.network.get_agent = mock.Mock(return_value=_testagent) + + self._testrouter = \ + network_fakes.FakeRouter.create_one_router() + self.network.find_router = mock.Mock(return_value=self._testrouter) + self.network.routers_hosting_l3_agents = mock.Mock( + return_value=self.network_agents) + # Get the command object to test self.cmd = network_agent.ListNetworkAgent(self.app, self.namespace) @@ -239,7 +269,7 @@ class TestListNetworkAgent(TestNetworkAgent): columns, data = self.cmd.take_action(parsed_args) self.network.agents.assert_called_once_with(**{ - 'agent_type': self.network_agents[0].agent_type, + 'agent_type': 'DHCP agent', }) self.assertEqual(self.columns, columns) self.assertEqual(self.data, list(data)) @@ -276,8 +306,53 @@ class TestListNetworkAgent(TestNetworkAgent): self.network.network_hosting_dhcp_agents.assert_called_once_with( *attrs) - self.assertEqual(self.network_agent_columns, columns) - self.assertEqual(list(self.network_agent_data), list(data)) + self.assertEqual(self.columns, columns) + self.assertEqual(self.data, list(data)) + + def test_network_agents_list_routers(self): + arglist = [ + '--router', self._testrouter.id, + ] + verifylist = [ + ('router', self._testrouter.id), + ('long', False) + ] + + attrs = {self._testrouter, } + + parsed_args = self.check_parser(self.cmd, arglist, verifylist) + columns, data = self.cmd.take_action(parsed_args) + + self.network.routers_hosting_l3_agents.assert_called_once_with( + *attrs) + + self.assertEqual(self.columns, columns) + self.assertEqual(self.data, list(data)) + + def test_network_agents_list_routers_with_long_option(self): + arglist = [ + '--router', self._testrouter.id, + '--long', + ] + verifylist = [ + ('router', self._testrouter.id), + ('long', True) + ] + + attrs = {self._testrouter, } + + parsed_args = self.check_parser(self.cmd, arglist, verifylist) + columns, data = self.cmd.take_action(parsed_args) + + self.network.routers_hosting_l3_agents.assert_called_once_with( + *attrs) + + # Add a column 'HA State' and corresponding data. + router_agent_columns = self.columns + ('HA State',) + router_agent_data = [d + ('',) for d in self.data] + + self.assertEqual(router_agent_columns, columns) + self.assertEqual(router_agent_data, list(data)) class TestRemoveNetworkFromAgent(TestNetworkAgent): @@ -303,6 +378,16 @@ class TestRemoveNetworkFromAgent(TestNetworkAgent): self.assertRaises(tests_utils.ParserException, self.check_parser, self.cmd, arglist, verifylist) + def test_network_agents_list_routers_no_arg(self): + arglist = [ + '--routers', + ] + verifylist = [] + + # Missing required args should bail here + self.assertRaises(tests_utils.ParserException, self.check_parser, + self.cmd, arglist, verifylist) + def test_network_from_dhcp_agent(self): arglist = [ '--dhcp', @@ -322,6 +407,46 @@ class TestRemoveNetworkFromAgent(TestNetworkAgent): self.agent, self.net) +class TestRemoveRouterAgent(TestNetworkAgent): + _router = network_fakes.FakeRouter.create_one_router() + _agent = network_fakes.FakeNetworkAgent.create_one_network_agent() + + def setUp(self): + super(TestRemoveRouterAgent, self).setUp() + self.network.remove_router_from_agent = mock.Mock() + self.cmd = network_agent.RemoveRouterFromAgent(self.app, + self.namespace) + self.network.get_agent = mock.Mock(return_value=self._agent) + self.network.find_router = mock.Mock(return_value=self._router) + + def test_remove_no_options(self): + arglist = [] + verifylist = [] + + # Missing agent ID will cause command to bail + self.assertRaises(tests_utils.ParserException, self.check_parser, + self.cmd, arglist, verifylist) + + def test_remove_router_required_options(self): + arglist = [ + '--l3', + self._agent.id, + self._router.id, + ] + verifylist = [ + ('l3', True), + ('agent_id', self._agent.id), + ('router', self._router.id), + ] + + parsed_args = self.check_parser(self.cmd, arglist, verifylist) + result = self.cmd.take_action(parsed_args) + + self.network.remove_router_from_agent.assert_called_with( + self._agent, self._router) + self.assertIsNone(result) + + class TestSetNetworkAgent(TestNetworkAgent): _network_agent = ( @@ -415,9 +540,9 @@ class TestShowNetworkAgent(TestNetworkAgent): 'id', ) data = ( - network_agent._format_admin_state(_network_agent.admin_state_up), + network_agent._format_admin_state(_network_agent.is_admin_state_up), _network_agent.agent_type, - _network_agent.alive, + network_agent._format_alive(_network_agent.is_alive), _network_agent.availability_zone, _network_agent.binary, utils.format_dict(_network_agent.configurations), diff --git a/openstackclient/tests/unit/network/v2/test_router.py b/openstackclient/tests/unit/network/v2/test_router.py index 02e0be9459..c153fe4a08 100644 --- a/openstackclient/tests/unit/network/v2/test_router.py +++ b/openstackclient/tests/unit/network/v2/test_router.py @@ -381,6 +381,21 @@ class TestListRouter(TestRouter): r.ha, r.tenant_id, )) + + router_agent_data = [] + for r in routers: + router_agent_data.append(( + r.id, + r.name, + r.external_gateway_info, + )) + + agents_columns = ( + 'ID', + 'Name', + 'External Gateway Info', + ) + data_long = [] for i in range(0, len(routers)): r = routers[i] @@ -407,8 +422,15 @@ class TestListRouter(TestRouter): # Get the command object to test self.cmd = router.ListRouter(self.app, self.namespace) + self.network.agent_hosted_routers = mock.Mock( + return_value=self.routers) self.network.routers = mock.Mock(return_value=self.routers) self.network.find_extension = mock.Mock(return_value=self._extensions) + self.network.find_router = mock.Mock(return_value=self.routers[0]) + self._testagent = \ + network_fakes.FakeNetworkAgent.create_one_network_agent() + self.network.get_agent = mock.Mock(return_value=self._testagent) + self.network.get_router = mock.Mock(return_value=self.routers[0]) def test_router_list_no_options(self): arglist = [] @@ -556,6 +578,34 @@ class TestListRouter(TestRouter): self.assertEqual(self.columns, columns) self.assertEqual(self.data, list(data)) + def test_router_list_agents_no_args(self): + arglist = [ + '--agents', + ] + verifylist = [] + + # Missing required router ID should bail here + self.assertRaises(tests_utils.ParserException, self.check_parser, + self.cmd, arglist, verifylist) + + def test_router_list_agents(self): + arglist = [ + '--agent', self._testagent.id, + ] + verifylist = [ + ('agent', self._testagent.id), + ] + + attrs = {self._testagent.id, } + + parsed_args = self.check_parser(self.cmd, arglist, verifylist) + columns, data = self.cmd.take_action(parsed_args) + + self.network.agent_hosted_routers( + *attrs) + self.assertEqual(self.columns, columns) + self.assertEqual(self.data, list(data)) + class TestRemovePortFromRouter(TestRouter): '''Remove port from a Router ''' diff --git a/releasenotes/notes/bp-network-l3-adv-commands-cc1df715a184f1b2.yaml b/releasenotes/notes/bp-network-l3-adv-commands-cc1df715a184f1b2.yaml new file mode 100644 index 0000000000..f978f4d650 --- /dev/null +++ b/releasenotes/notes/bp-network-l3-adv-commands-cc1df715a184f1b2.yaml @@ -0,0 +1,8 @@ +--- +features: + - | + Add network l3-agent related commands ``network agent add router``, + ``network agent remove router`` for adding/removing routers to l3 agents. + Add ``network agent list --router``, and ``router list --agent`` for + listing agents on routers and routers on specific agents. + [Blueprint :oscbp:`network-l3-commands`] diff --git a/setup.cfg b/setup.cfg index 73a9c42cfb..16917e5099 100644 --- a/setup.cfg +++ b/setup.cfg @@ -365,9 +365,11 @@ openstack.network.v2 = ip_floating_pool_list = openstackclient.network.v2.floating_ip_pool:ListIPFloatingPool network_agent_add_network = openstackclient.network.v2.network_agent:AddNetworkToAgent + network_agent_add_router = openstackclient.network.v2.network_agent:AddRouterToAgent network_agent_delete = openstackclient.network.v2.network_agent:DeleteNetworkAgent network_agent_list = openstackclient.network.v2.network_agent:ListNetworkAgent network_agent_remove_network = openstackclient.network.v2.network_agent:RemoveNetworkFromAgent + network_agent_remove_router = openstackclient.network.v2.network_agent:RemoveRouterFromAgent network_agent_set = openstackclient.network.v2.network_agent:SetNetworkAgent network_agent_show = openstackclient.network.v2.network_agent:ShowNetworkAgent