
Referecne to level values added to DB model and level marshalling. Fuel2 commands lvl show, lvl list added. Change-Id: I11fb465c00c411464d75229fc2f8bffdbb8dcc53 Closes-Bug: #1642326
166 lines
5.2 KiB
Python
166 lines
5.2 KiB
Python
# 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 abc
|
|
import json
|
|
import yaml
|
|
|
|
from cliff import command
|
|
from cliff import lister
|
|
from cliff import show
|
|
from fuelclient.cli import error as fc_error
|
|
from fuelclient.common import data_utils
|
|
import six
|
|
|
|
|
|
def level_converter(value):
|
|
levels = []
|
|
for part in value.split(','):
|
|
spl = part.split("=", 1)
|
|
if len(spl) != 2:
|
|
raise TypeError("Levels list should be in format "
|
|
"level1=value1,level2=value2")
|
|
levels.append(tuple(spl))
|
|
return levels
|
|
|
|
try:
|
|
text_type = unicode
|
|
except NameError:
|
|
text_type = str
|
|
|
|
|
|
def format_output(output, format_):
|
|
if format_ == 'plain':
|
|
if output is None:
|
|
return ''
|
|
if isinstance(output, text_type):
|
|
if text_type is str:
|
|
return output
|
|
else:
|
|
return output.encode('utf-8')
|
|
format_ = 'json'
|
|
# numbers, booleans, lists and dicts will be represented as JSON
|
|
if format_ == 'json':
|
|
return json.dumps(output)
|
|
if format_ == 'yaml':
|
|
# Usage of safe_dump here is crucial since PyYAML emits
|
|
# "!!python/unicode" objects from unicode strings by defaul
|
|
return yaml.safe_dump(output, default_flow_style=False)
|
|
raise RuntimeError("Unknown format '{}'".format(format_))
|
|
|
|
|
|
class BaseCommand(command.Command):
|
|
|
|
def get_client(self):
|
|
return self.app.client
|
|
|
|
def _parse_comma_separated(self, parsed_args, param_name, cast_to):
|
|
param = getattr(parsed_args, param_name)
|
|
if param is None or param == '[]':
|
|
return []
|
|
result = six.moves.map(six.text_type.strip,
|
|
six.text_type(param).split(','))
|
|
return list(six.moves.map(cast_to, result))
|
|
|
|
def read_json(self):
|
|
return json.load(self.app.stdin)
|
|
|
|
def read_yaml(self):
|
|
docs_gen = yaml.safe_load_all(self.app.stdin)
|
|
doc = next(docs_gen)
|
|
guard = object()
|
|
if next(docs_gen, guard) is not guard:
|
|
self.app.stderr.write("Warning: will use only first "
|
|
"document from YAML stream")
|
|
return doc
|
|
|
|
|
|
class BaseOneCommand(BaseCommand):
|
|
|
|
@abc.abstractproperty
|
|
def base_url(self):
|
|
"""Base url for request operations"""
|
|
|
|
@abc.abstractproperty
|
|
def entity_name(self):
|
|
"""Name of the TuningBox entity"""
|
|
|
|
def get_parser(self, *args, **kwargs):
|
|
parser = super(BaseOneCommand, self).get_parser(*args, **kwargs)
|
|
parser.add_argument(
|
|
'id',
|
|
type=int,
|
|
help='Id of the {0}'.format(self.entity_name))
|
|
return parser
|
|
|
|
def get_url(self, parsed_args):
|
|
return '{0}/{1}'.format(self.base_url, parsed_args.id)
|
|
|
|
def get_deletion_message(self, parsed_args):
|
|
return '{0} with id {1} was deleted\n'.format(
|
|
self.entity_name.capitalize(), parsed_args.id)
|
|
|
|
def get_update_message(self, parsed_args):
|
|
return '{0} with id {1} was updated\n'.format(
|
|
self.entity_name.capitalize(), parsed_args.id)
|
|
|
|
|
|
class BaseDeleteCommand(BaseOneCommand):
|
|
"""Deletes entity with the specified id."""
|
|
|
|
def take_action(self, parsed_args):
|
|
result = self.get_client().delete(self.get_url(parsed_args))
|
|
if result is None:
|
|
result = self.get_deletion_message(parsed_args)
|
|
self.app.stdout.write(six.text_type(result))
|
|
|
|
|
|
class BaseListCommand(BaseCommand, lister.Lister):
|
|
|
|
def take_action(self, parsed_args):
|
|
result = self.get_client().get(self.base_url)
|
|
try:
|
|
data = data_utils.get_display_data_multi(self.columns, result)
|
|
return self.columns, data
|
|
except fc_error.BadDataException:
|
|
return zip(*result.items())
|
|
|
|
|
|
class BaseShowCommand(BaseOneCommand, show.ShowOne):
|
|
|
|
def take_action(self, parsed_args):
|
|
result = self.get_client().get(self.get_url(parsed_args))
|
|
try:
|
|
data = data_utils.get_display_data_single(self.columns, result)
|
|
return self.columns, data
|
|
except fc_error.BadDataException:
|
|
return zip(*result.items())
|
|
|
|
|
|
class FormattedCommand(BaseCommand):
|
|
format_choices = ('json', 'yaml', 'plain')
|
|
|
|
def get_parser(self, *args, **kwargs):
|
|
parser = super(FormattedCommand, self).get_parser(*args, **kwargs)
|
|
parser.add_argument(
|
|
'-f', '--format',
|
|
choices=self.format_choices,
|
|
default='json',
|
|
help="Desired format for return value",
|
|
)
|
|
return parser
|
|
|
|
def run(self, parsed_args):
|
|
res = self.take_action(parsed_args)
|
|
self.app.stdout.write(format_output(res, parsed_args.format))
|
|
return 0
|