M V P Nitesh 0de0c4f2c8 Replace six.iteritems() with .items()
1.As mentioned in [1], we should avoid using six.iteritems to achieve
iterators. We can use dict.items instead, as it will return iterators
in PY3 as well. And dict.items/keys will more readable.
2.In py2, the performance about list should be negligible, see the
link [2].
[1] https://wiki.openstack.org/wiki/Python3
[2] http://lists.openstack.org/pipermail/openstack-dev/2015-June/066391.html

Change-Id: Ifac571e10ee48b119bc4bbb6a5d92200d0c7e482
2017-03-30 15:58:56 +05:30

312 lines
10 KiB
Python

# Copyright 2016 Huawei, Inc. All rights reserved.
#
# 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.
#
"""Mogan v1 Baremetal flavor action implementations"""
import copy
import logging
from osc_lib.cli import parseractions
from osc_lib.command import command
from osc_lib import exceptions
from osc_lib import utils
from moganclient.common import base
from moganclient.common.i18n import _
LOG = logging.getLogger(__name__)
class CreateFlavor(command.ShowOne):
"""Create a new baremetal flavor"""
def get_parser(self, prog_name):
parser = super(CreateFlavor, self).get_parser(prog_name)
parser.add_argument(
"name",
metavar="<name>",
help=_("New baremetal flavor name")
)
public_group = parser.add_mutually_exclusive_group()
public_group.add_argument(
"--public",
action="store_true",
help=_("Flavor is available to other projects (default)")
)
public_group.add_argument(
"--private",
action="store_true",
help=_("Flavor is not available to other projects")
)
parser.add_argument(
"--description",
metavar="<description>",
help=_("Flavor description"),
)
parser.add_argument(
"--property",
metavar="<key=value>",
action=parseractions.KeyValueAction,
help=_("Property to add to this flavor "
"(repeat option to set multiple properties)")
)
return parser
def take_action(self, parsed_args):
bc_client = self.app.client_manager.baremetal_compute
info = {}
is_public = True
if parsed_args.public:
is_public = True
if parsed_args.private:
is_public = False
data = bc_client.flavor.create(
name=parsed_args.name,
is_public=is_public,
description=parsed_args.description,
)
info.update(data._info)
if parsed_args.property:
bc_client.flavor.update_extra_specs(data,
parsed_args.property)
extra_specs = bc_client.flavor.get_extra_specs(data)
info.update(extra_specs)
return zip(*sorted(info.items()))
class DeleteFlavor(command.Command):
"""Delete existing baremetal flavor(s)"""
def get_parser(self, prog_name):
parser = super(DeleteFlavor, self).get_parser(prog_name)
parser.add_argument(
'flavor',
metavar='<flavor>',
nargs='+',
help=_("Flavor(s) to delete (name or UUID)")
)
return parser
def take_action(self, parsed_args):
bc_client = self.app.client_manager.baremetal_compute
result = 0
for one_flavor in parsed_args.flavor:
try:
data = utils.find_resource(
bc_client.flavor, one_flavor)
bc_client.flavor.delete(data.uuid)
except Exception as e:
result += 1
LOG.error(_("Failed to delete flavor with name or UUID "
"'%(flavor)s': %(e)s") %
{'flavor': one_flavor, 'e': e})
if result > 0:
total = len(parsed_args.flavor)
msg = (_("%(result)s of %(total)s flavors failed "
"to delete.") % {'result': result, 'total': total})
raise exceptions.CommandError(msg)
class ListFlavor(command.Lister):
"""List all baremetal flavors"""
def take_action(self, parsed_args):
bc_client = self.app.client_manager.baremetal_compute
data = bc_client.flavor.list()
column_headers = (
"UUID",
"Name",
"Is Public",
"Description",
"Properties",
)
columns = (
"UUID",
"Name",
"Is Public",
"Description",
"Extra Specs",
)
return (column_headers,
(utils.get_item_properties(
s, columns,
) for s in data))
class SetFlavor(command.Command):
"""Set baremetal flavor properties"""
def get_parser(self, prog_name):
parser = super(SetFlavor, self).get_parser(prog_name)
parser.add_argument(
'flavor',
metavar='<flavor>',
help=_("Flavor to modify (name or UUID)")
)
parser.add_argument(
"--property",
metavar="<key=value>",
action=parseractions.KeyValueAction,
help=_("Property to set on <flavor> "
"(repeat option to set multiple properties)")
)
parser.add_argument(
"--no-property",
dest="no_property",
action="store_true",
help=_("Remove all properties from <flavor> "
"(specify both --property and --no-property to "
"overwrite the current properties)"),
)
return parser
def take_action(self, parsed_args):
bc_client = self.app.client_manager.baremetal_compute
data = utils.find_resource(
bc_client.flavor,
parsed_args.flavor,
)
set_property = None
del_property_key = None
# NOTE(RuiChen): extra specs update API is append mode, so if the
# options is overwrite mode, the update and delete
# properties need to be handled in client side.
if parsed_args.no_property and parsed_args.property:
# override
del_property_key = data.extra_specs.keys()
set_property = copy.deepcopy(parsed_args.property)
elif parsed_args.property:
# append
set_property = copy.deepcopy(parsed_args.property)
elif parsed_args.no_property:
# clean
del_property_key = data.extra_specs.keys()
result = 0
if del_property_key is not None:
for each_key in del_property_key:
try:
# If the key is in the set_property, it will be updated
# in the follow logic.
if (set_property is None or
each_key not in set_property):
bc_client.flavor.delete_extra_specs(
data,
each_key
)
except Exception as e:
result += 1
LOG.error(_("Failed to remove flavor property with key "
"'%(key)s': %(e)s") % {'key': each_key,
'e': e})
if set_property is not None:
try:
bc_client.flavor.update_extra_specs(
data,
set_property
)
except Exception as e:
result += 1
LOG.error(_("Failed to update flavor property with key/value "
"'%(key)s': %(e)s") % {'key': set_property,
'e': e})
if result > 0:
msg = (_("Set flavor %(flavor)s property failed.") % {
'flavor': base.getid(data)})
raise exceptions.CommandError(msg)
class ShowFlavor(command.ShowOne):
"""Display baremetal flavor details"""
def get_parser(self, prog_name):
parser = super(ShowFlavor, self).get_parser(prog_name)
parser.add_argument(
'flavor',
metavar='<flavor>',
help=_("Flavor to display (name or UUID)")
)
return parser
def take_action(self, parsed_args):
bc_client = self.app.client_manager.baremetal_compute
data = utils.find_resource(
bc_client.flavor,
parsed_args.flavor,
)
info = {}
info.update(data._info)
return zip(*sorted(info.items()))
class UnsetFlavor(command.Command):
"""Unset baremetal flavor properties"""
def get_parser(self, prog_name):
parser = super(UnsetFlavor, self).get_parser(prog_name)
parser.add_argument(
'flavor',
metavar='<flavor>',
help=_("Flavor to modify (name or UUID)")
)
parser.add_argument(
"--property",
metavar="<key>",
action='append',
help=_("Property to remove from <flavor> "
"(repeat option to remove multiple properties)")
)
return parser
def take_action(self, parsed_args):
bc_client = self.app.client_manager.baremetal_compute
data = utils.find_resource(
bc_client.flavor,
parsed_args.flavor,
)
unset_property_key = []
if parsed_args.property:
unset_property_key = list(
set(data.extra_specs.keys()).intersection(
set(parsed_args.property)))
result = 0
for each_key in unset_property_key:
try:
bc_client.flavor.delete_extra_specs(data, each_key)
except Exception as e:
result += 1
LOG.error(_("Failed to remove flavor property with key "
"'%(key)s': %(e)s") % {'key': each_key, 'e': e})
if result > 0:
total = len(unset_property_key)
msg = (_("%(result)s of %(total)s flavor property failed "
"to remove.") % {'result': result, 'total': total})
raise exceptions.CommandError(msg)