Merge "Add network extension list"

This commit is contained in:
Jenkins 2014-09-18 09:41:51 +00:00 committed by Gerrit Code Review
commit df69d3264f
3 changed files with 126 additions and 15 deletions

View File

@ -15,6 +15,7 @@
"""Extension action implementations"""
import itertools
import logging
from cliff import lister
@ -25,28 +26,30 @@ from openstackclient.common import utils
class ListExtension(lister.Lister):
"""List extension command"""
# TODO(mfisch): add support for volume and network
# when the underlying APIs support it.
log = logging.getLogger(__name__ + '.ListExtension')
def get_parser(self, prog_name):
parser = super(ListExtension, self).get_parser(prog_name)
parser.add_argument(
'--long',
'--compute',
action='store_true',
default=False,
help='List additional fields in output')
help='List extensions for the Compute API')
parser.add_argument(
'--identity',
action='store_true',
default=False,
help='List extensions for the Identity API')
parser.add_argument(
'--compute',
'--long',
action='store_true',
default=False,
help='List extensions for the Compute API')
help='List additional fields in output')
parser.add_argument(
'--network',
action='store_true',
default=False,
help='List extensions for the Network API')
parser.add_argument(
'--volume',
action='store_true',
@ -69,7 +72,7 @@ class ListExtension(lister.Lister):
# user specifies one or more of the APIs to show
# for now, only identity and compute are supported.
show_all = (not parsed_args.identity and not parsed_args.compute
and not parsed_args.volume)
and not parsed_args.volume and not parsed_args.network)
if parsed_args.identity or show_all:
identity_client = self.app.client_manager.identity
@ -95,8 +98,33 @@ class ListExtension(lister.Lister):
message = "Extensions list not supported by Volume API"
self.log.warning(message)
return (columns,
(utils.get_item_properties(
s, columns,
formatters={},
) for s in data))
# Resource classes for the above
extension_tuples = (
utils.get_item_properties(
s,
columns,
formatters={},
) for s in data
)
# Dictionaries for the below
if parsed_args.network or show_all:
network_client = self.app.client_manager.network
try:
data = network_client.list_extensions()['extensions']
dict_tuples = (
utils.get_dict_properties(
s,
columns,
formatters={},
) for s in data
)
extension_tuples = itertools.chain(
extension_tuples,
dict_tuples
)
except Exception:
message = "Extensions list not supported by Network API"
self.log.warning(message)
return (columns, extension_tuples)

View File

@ -18,6 +18,7 @@ from openstackclient.tests import fakes
from openstackclient.tests import utils
from openstackclient.tests.identity.v2_0 import fakes as identity_fakes
from openstackclient.tests.network.v2 import fakes as network_fakes
class TestExtension(utils.TestCommand):
@ -29,12 +30,15 @@ class TestExtension(utils.TestCommand):
endpoint=fakes.AUTH_URL,
token=fakes.AUTH_TOKEN,
)
# Get shortcuts to the ExtensionManager Mocks
self.identity_extensions_mock = (
self.app.client_manager.identity.extensions)
self.identity_extensions_mock.reset_mock()
network = network_fakes.FakeNetworkV2Client()
self.app.client_manager.network = network
self.network_extensions_mock = network.list_extensions
self.network_extensions_mock.reset_mock()
class TestExtensionList(TestExtension):
@ -48,6 +52,13 @@ class TestExtensionList(TestExtension):
loaded=True,
),
]
self.network_extensions_mock.list.return_value = [
fakes.FakeResource(
None,
copy.deepcopy(identity_fakes.EXTENSION),
loaded=True,
),
]
# Get the command object to test
self.cmd = extension.ListExtension(self.app, None)
@ -71,6 +82,11 @@ class TestExtensionList(TestExtension):
identity_fakes.extension_alias,
identity_fakes.extension_description,
),
(
network_fakes.extension_name,
network_fakes.extension_alias,
network_fakes.extension_description,
),
)
self.assertEqual(tuple(data), datalist)
@ -101,6 +117,14 @@ class TestExtensionList(TestExtension):
identity_fakes.extension_updated,
identity_fakes.extension_links,
),
(
network_fakes.extension_name,
network_fakes.extension_namespace,
network_fakes.extension_description,
network_fakes.extension_alias,
network_fakes.extension_updated,
network_fakes.extension_links,
),
)
self.assertEqual(tuple(data), datalist)
@ -126,3 +150,27 @@ class TestExtensionList(TestExtension):
identity_fakes.extension_description,
), )
self.assertEqual(tuple(data), datalist)
def test_extension_list_network(self):
arglist = [
'--network',
]
verifylist = [
('network', True),
]
parsed_args = self.check_parser(self.cmd, arglist, verifylist)
columns, data = self.cmd.take_action(parsed_args)
self.network_extensions_mock.assert_called_with()
collist = ('Name', 'Alias', 'Description')
self.assertEqual(columns, collist)
datalist = (
(
network_fakes.extension_name,
network_fakes.extension_alias,
network_fakes.extension_description,
),
)
self.assertEqual(tuple(data), datalist)

View File

@ -0,0 +1,35 @@
# Licensed under the Apache License, Version 2.0 (the "License"); you may
# not use this file except in compliance with the License. You may obtain
# a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
# License for the specific language governing permissions and limitations
# under the License.
#
import mock
extension_name = 'Matrix'
extension_namespace = 'http://docs.openstack.org/network/'
extension_description = 'Simulated reality'
extension_updated = '2013-07-09T12:00:0-00:00'
extension_alias = 'Dystopian'
extension_links = '[{"href":''"https://github.com/os/network", "type"}]'
NETEXT = {
'name': extension_name,
'namespace': extension_namespace,
'description': extension_description,
'updated': extension_updated,
'alias': extension_alias,
'links': extension_links,
}
class FakeNetworkV2Client(object):
def __init__(self, **kwargs):
self.list_extensions = mock.Mock(return_value={'extensions': [NETEXT]})