3ec364d1fd
The "per_share_gigabytes" quota param was introduced in API version 2.62; when using older API versions, we shouldn't be setting this parameter. Closes-Bug: #2047249 Change-Id: I1eceee52726cef3494648521e4516010ca02f095
389 lines
14 KiB
Python
389 lines
14 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.
|
|
|
|
from osc_lib.command import command
|
|
from osc_lib import exceptions
|
|
from osc_lib import utils
|
|
|
|
from manilaclient import api_versions
|
|
from manilaclient.common._i18n import _
|
|
|
|
|
|
class QuotaSet(command.Command):
|
|
"""Set quotas for a project or project/user or project/share-type.
|
|
|
|
It can be used to set the default class for all projects.
|
|
"""
|
|
|
|
_description = _("Set Quota for a project, or project/user or "
|
|
"project/share-type or a class.")
|
|
|
|
def get_parser(self, prog_name):
|
|
parser = super(QuotaSet, self).get_parser(prog_name)
|
|
quota_type = parser.add_mutually_exclusive_group()
|
|
parser.add_argument(
|
|
'project',
|
|
metavar='<project/class>',
|
|
help=_("A project (name/ID) or a class (e.g.: default).")
|
|
)
|
|
quota_type.add_argument(
|
|
'--class',
|
|
dest='quota_class',
|
|
action='store_true',
|
|
default=False,
|
|
help=_("Update class quota to all projects. "
|
|
"Mutually exclusive with '--user' and '--share-type'.")
|
|
)
|
|
quota_type.add_argument(
|
|
'--user',
|
|
metavar='<user>',
|
|
default=None,
|
|
help=_("Name or ID of a user to set the quotas for. "
|
|
"Mutually exclusive with '--share-type' and '--class'.")
|
|
)
|
|
quota_type.add_argument(
|
|
'--share-type',
|
|
metavar='<share-type>',
|
|
type=str,
|
|
default=None,
|
|
help=_("Name or ID of a share type to set the quotas for. "
|
|
"Mutually exclusive with '--user' and '--class'. "
|
|
"Available only for microversion >= 2.39")
|
|
)
|
|
parser.add_argument(
|
|
'--shares',
|
|
metavar='<shares>',
|
|
type=int,
|
|
default=None,
|
|
help=_('New value for the "shares" quota.')
|
|
)
|
|
parser.add_argument(
|
|
'--snapshots',
|
|
metavar='<snapshots>',
|
|
type=int,
|
|
default=None,
|
|
help=_('New value for the "snapshots" quota.')
|
|
)
|
|
parser.add_argument(
|
|
'--gigabytes',
|
|
metavar='<gigabytes>',
|
|
type=int,
|
|
default=None,
|
|
help=_('New value for the "gigabytes" quota.')
|
|
)
|
|
parser.add_argument(
|
|
'--snapshot-gigabytes',
|
|
metavar='<snapshot-gigabytes>',
|
|
type=int,
|
|
default=None,
|
|
help=_('New value for the "snapshot-gigabytes" quota.')
|
|
)
|
|
parser.add_argument(
|
|
'--share-networks',
|
|
metavar='<share-networks>',
|
|
type=int,
|
|
default=None,
|
|
help=_('New value for the "share-networks" quota.')
|
|
)
|
|
parser.add_argument(
|
|
'--share-groups',
|
|
metavar='<share-groups>',
|
|
type=int,
|
|
default=None,
|
|
help=_('New value for the "share-groups" quota. '
|
|
'Available only for microversion >= 2.40')
|
|
)
|
|
parser.add_argument(
|
|
'--share-group-snapshots',
|
|
metavar='<share-group-snapshots>',
|
|
type=int,
|
|
default=None,
|
|
help=_('New value for the "share-group-snapshots" quota. '
|
|
'Available only for microversion >= 2.40')
|
|
)
|
|
parser.add_argument(
|
|
'--share-replicas',
|
|
metavar='<share-replicas>',
|
|
type=int,
|
|
default=None,
|
|
help=_("Number of share replicas. "
|
|
"Available only for microversion >= 2.53")
|
|
)
|
|
parser.add_argument(
|
|
'--replica-gigabytes',
|
|
metavar='<replica-gigabytes>',
|
|
type=int,
|
|
default=None,
|
|
help=_("Capacity of share replicas in total. "
|
|
"Available only for microversion >= 2.53")
|
|
)
|
|
parser.add_argument(
|
|
'--per-share-gigabytes',
|
|
metavar='<per-share-gigabytes>',
|
|
type=int,
|
|
default=None,
|
|
help=_("New value for the 'per-share-gigabytes' quota."
|
|
"Available only for microversion >= 2.62")
|
|
)
|
|
parser.add_argument(
|
|
'--force',
|
|
dest='force',
|
|
action="store_true",
|
|
default=None,
|
|
help=_('Force update the quota. '
|
|
'Not applicable for class update.')
|
|
)
|
|
return parser
|
|
|
|
def take_action(self, parsed_args):
|
|
share_client = self.app.client_manager.share
|
|
identity_client = self.app.client_manager.identity
|
|
|
|
user_id = None
|
|
if parsed_args.user:
|
|
user_id = utils.find_resource(
|
|
identity_client.users,
|
|
parsed_args.user).id
|
|
|
|
kwargs = {
|
|
"shares": parsed_args.shares,
|
|
"snapshots": parsed_args.snapshots,
|
|
"gigabytes": parsed_args.gigabytes,
|
|
"snapshot_gigabytes": parsed_args.snapshot_gigabytes,
|
|
"share_networks": parsed_args.share_networks,
|
|
}
|
|
|
|
if parsed_args.share_type is not None:
|
|
if share_client.api_version < api_versions.APIVersion('2.39'):
|
|
raise exceptions.CommandError(_(
|
|
"'share type' quotas are available only starting with "
|
|
"'2.39' API microversion."))
|
|
kwargs["share_type"] = parsed_args.share_type
|
|
if parsed_args.share_groups is not None:
|
|
if share_client.api_version < api_versions.APIVersion('2.40'):
|
|
raise exceptions.CommandError(_(
|
|
"'share group' quotas are available only starting with "
|
|
"'2.40' API microversion."))
|
|
kwargs["share_groups"] = parsed_args.share_groups
|
|
if parsed_args.share_group_snapshots is not None:
|
|
if share_client.api_version < api_versions.APIVersion('2.40'):
|
|
raise exceptions.CommandError(_(
|
|
"'share group snapshots' quotas are available only "
|
|
"starting with '2.40' API microversion."))
|
|
kwargs["share_group_snapshots"] = parsed_args.share_group_snapshots
|
|
if parsed_args.share_replicas is not None:
|
|
if share_client.api_version < api_versions.APIVersion('2.53'):
|
|
raise exceptions.CommandError(_(
|
|
"setting the number of 'share replicas' is available only "
|
|
"starting with API microversion '2.53'."))
|
|
kwargs["share_replicas"] = parsed_args.share_replicas
|
|
if parsed_args.replica_gigabytes is not None:
|
|
if share_client.api_version < api_versions.APIVersion('2.53'):
|
|
raise exceptions.CommandError(_(
|
|
"setting the capacity of share replicas in total "
|
|
"is available only starting with API microversion '2.53'.")
|
|
)
|
|
kwargs["replica_gigabytes"] = parsed_args.replica_gigabytes
|
|
if parsed_args.per_share_gigabytes is not None:
|
|
if share_client.api_version < api_versions.APIVersion('2.62'):
|
|
raise exceptions.CommandError(_(
|
|
"'per share gigabytes' quotas are available only "
|
|
"starting with '2.62' API microversion.")
|
|
)
|
|
kwargs["per_share_gigabytes"] = parsed_args.per_share_gigabytes
|
|
|
|
if all(value is None for value in kwargs.values()):
|
|
raise exceptions.CommandError(_(
|
|
"Nothing to set. "
|
|
"New quota must be specified to at least one of the following "
|
|
"resources: 'shares', 'snapshots', 'gigabytes', "
|
|
"'snapshot-gigabytes', 'share-networks', 'share-type', "
|
|
"'share-groups', 'share-group-snapshots', 'share-replicas', "
|
|
"'replica-gigabytes', 'per-share-gigabytes'"))
|
|
|
|
if parsed_args.quota_class:
|
|
kwargs.update({
|
|
"class_name": parsed_args.project,
|
|
})
|
|
try:
|
|
share_client.quota_classes.update(**kwargs)
|
|
except Exception as e:
|
|
raise exceptions.CommandError(_(
|
|
"Failed to set quotas for %s class: '%s'")
|
|
% (parsed_args.project, e))
|
|
else:
|
|
project_id = utils.find_resource(
|
|
identity_client.projects,
|
|
parsed_args.project).id
|
|
|
|
kwargs.update({
|
|
"tenant_id": project_id,
|
|
"force": parsed_args.force,
|
|
"user_id": user_id
|
|
})
|
|
|
|
try:
|
|
share_client.quotas.update(**kwargs)
|
|
except Exception as e:
|
|
raise exceptions.CommandError(_(
|
|
"Failed to set quotas for project '%s' : '%s'")
|
|
% (parsed_args.project, e))
|
|
|
|
|
|
class QuotaShow(command.ShowOne):
|
|
"""List the quotas for a project or project/user or project/share-type."""
|
|
_description = _("Show Quota")
|
|
|
|
def get_parser(self, prog_name):
|
|
parser = super(QuotaShow, self).get_parser(prog_name)
|
|
quota_type = parser.add_mutually_exclusive_group()
|
|
parser.add_argument(
|
|
'project',
|
|
metavar='<project>',
|
|
help=_('Name or ID of the project to list quotas for.')
|
|
)
|
|
quota_type.add_argument(
|
|
'--user',
|
|
metavar='<user>',
|
|
default=None,
|
|
help=_("Name or ID of user to list the quotas for. Optional. "
|
|
"Mutually exclusive with '--share-type'.")
|
|
)
|
|
quota_type.add_argument(
|
|
'--share-type',
|
|
metavar='<share-type>',
|
|
type=str,
|
|
default=None,
|
|
help=_("Name or ID of a share type to list the quotas for. "
|
|
"Optional. "
|
|
"Mutually exclusive with '--user'. "
|
|
"Available only for microversion >= 2.39")
|
|
)
|
|
parser.add_argument(
|
|
'--detail',
|
|
action='store_true',
|
|
default=False,
|
|
help=_('Optional flag to indicate whether to show quota in detail.'
|
|
' Default false, available only for microversion >= 2.25.')
|
|
)
|
|
parser.add_argument(
|
|
'--defaults',
|
|
action='store_true',
|
|
default=False,
|
|
help=_('Show the default quotas for the project.')
|
|
)
|
|
return parser
|
|
|
|
def take_action(self, parsed_args):
|
|
share_client = self.app.client_manager.share
|
|
identity_client = self.app.client_manager.identity
|
|
|
|
user_id = None
|
|
if parsed_args.user:
|
|
user_id = utils.find_resource(
|
|
identity_client.users,
|
|
parsed_args.user).id
|
|
|
|
project_id = utils.find_resource(
|
|
identity_client.projects,
|
|
parsed_args.project).id
|
|
|
|
quotas = {}
|
|
if parsed_args.defaults:
|
|
quotas = share_client.quotas.defaults(project_id)
|
|
else:
|
|
kwargs = {
|
|
"tenant_id": project_id,
|
|
"user_id": user_id,
|
|
"detail": parsed_args.detail,
|
|
}
|
|
if parsed_args.share_type is not None:
|
|
if share_client.api_version < api_versions.APIVersion("2.39"):
|
|
raise exceptions.CommandError(_(
|
|
"'share type' quotas are available only starting with "
|
|
"'2.39' API microversion."))
|
|
kwargs["share_type"] = parsed_args.share_type
|
|
|
|
quotas = share_client.quotas.get(**kwargs)
|
|
|
|
printable_quotas = {}
|
|
for quota_k, quota_v in sorted(quotas.to_dict().items()):
|
|
if isinstance(quota_v, dict):
|
|
quota_v = '\n'.join(
|
|
['%s = %s' % (k, v) for k, v in sorted(quota_v.items())])
|
|
printable_quotas[quota_k] = quota_v
|
|
|
|
return self.dict2columns(printable_quotas)
|
|
|
|
|
|
class QuotaDelete(command.Command):
|
|
"""Delete quota for project/user or project/share-type.
|
|
|
|
The quota will revert back to default.
|
|
"""
|
|
|
|
_description = _("Delete Quota")
|
|
|
|
def get_parser(self, prog_name):
|
|
parser = super(QuotaDelete, self).get_parser(prog_name)
|
|
quota_type = parser.add_mutually_exclusive_group()
|
|
parser.add_argument(
|
|
'project',
|
|
metavar='<project>',
|
|
help=_('Name or ID of the project to delete quotas for.')
|
|
)
|
|
quota_type.add_argument(
|
|
'--user',
|
|
metavar='<user>',
|
|
default=None,
|
|
help=_("Name or ID of user to delete the quotas for. Optional. "
|
|
"Mutually exclusive with '--share-type'.")
|
|
)
|
|
quota_type.add_argument(
|
|
'--share-type',
|
|
metavar='<share-type>',
|
|
type=str,
|
|
default=None,
|
|
help=_("Name or ID of a share type to delete the quotas for. "
|
|
"Optional. "
|
|
"Mutually exclusive with '--user'. "
|
|
"Available only for microversion >= 2.39")
|
|
)
|
|
return parser
|
|
|
|
def take_action(self, parsed_args):
|
|
share_client = self.app.client_manager.share
|
|
identity_client = self.app.client_manager.identity
|
|
|
|
user_id = None
|
|
if parsed_args.user:
|
|
user_id = utils.find_resource(
|
|
identity_client.users,
|
|
parsed_args.user).id
|
|
|
|
project_id = utils.find_resource(
|
|
identity_client.projects,
|
|
parsed_args.project).id
|
|
|
|
kwargs = {
|
|
"tenant_id": project_id,
|
|
"user_id": user_id
|
|
}
|
|
if parsed_args.share_type:
|
|
if share_client.api_version < api_versions.APIVersion("2.39"):
|
|
raise exceptions.CommandError(_(
|
|
"'share type' quotas are available only starting with "
|
|
"API microversion '2.39'."))
|
|
kwargs["share_type"] = parsed_args.share_type
|
|
|
|
share_client.quotas.delete(**kwargs)
|