Merge "Support group specs search for share group type API"
This commit is contained in:
commit
37c41e57cf
@ -298,6 +298,19 @@ group_snapshot_status_query:
|
||||
in: query
|
||||
required: false
|
||||
type: string
|
||||
group_specs_query:
|
||||
description: |
|
||||
The group specifications as a set of one or more
|
||||
key-value pairs. In each pair, the key is the name of the group
|
||||
specification and the value is the share group type that was used to
|
||||
filter search share group type list. The query must be a “percent-encoded” string,
|
||||
for example, the following query parameters: {'group-specs':
|
||||
{'consistent_snapshot_support': 'true'}} is encoded as
|
||||
'group_specs=%7B%27consistent_snapshot_support%27%3A+%27True%27%7D'
|
||||
in: query
|
||||
required: false
|
||||
type: string
|
||||
min_version: 2.66
|
||||
host_query:
|
||||
description: |
|
||||
The host name of the resource to query with. Querying by hostname is a
|
||||
|
@ -58,6 +58,8 @@ Request
|
||||
.. rest_parameters:: parameters.yaml
|
||||
|
||||
- project_id: project_id_path
|
||||
- is_public: is_public_query
|
||||
- group_specs: group_specs_query
|
||||
|
||||
Response parameters
|
||||
-------------------
|
||||
|
@ -266,6 +266,27 @@ def check_share_network_is_active(share_network):
|
||||
raise webob.exc.HTTPBadRequest(explanation=msg)
|
||||
|
||||
|
||||
def parse_is_public(is_public):
|
||||
"""Parse is_public into something usable.
|
||||
|
||||
:returns:
|
||||
- True: API should list public share group types only
|
||||
- False: API should list private share group types only
|
||||
- None: API should list both public and private share group types
|
||||
"""
|
||||
if is_public is None:
|
||||
# preserve default value of showing only public types
|
||||
return True
|
||||
elif six.text_type(is_public).lower() == "all":
|
||||
return None
|
||||
else:
|
||||
try:
|
||||
return strutils.bool_from_string(is_public, strict=True)
|
||||
except ValueError:
|
||||
msg = _('Invalid is_public filter [%s]') % is_public
|
||||
raise webob.exc.HTTPBadRequest(explanation=msg)
|
||||
|
||||
|
||||
class ViewBuilder(object):
|
||||
"""Model API responses as dictionaries."""
|
||||
|
||||
|
@ -172,13 +172,14 @@ REST_API_VERSION_HISTORY = """
|
||||
'update_security_service', 'update_security_service_check' and
|
||||
'add_security_service_check'.
|
||||
* 2.65 - Added ability to set scheduler hints via the share create API.
|
||||
* 2.66 - Added filter search by group spec for share group type list.
|
||||
"""
|
||||
|
||||
# The minimum and maximum versions of the API supported
|
||||
# The default api version request is defined to be the
|
||||
# minimum version of the API supported.
|
||||
_MIN_API_VERSION = "2.0"
|
||||
_MAX_API_VERSION = "2.65"
|
||||
_MAX_API_VERSION = "2.66"
|
||||
DEFAULT_API_VERSION = _MIN_API_VERSION
|
||||
|
||||
|
||||
|
@ -363,3 +363,7 @@ user documentation.
|
||||
Added ability to specify "scheduler_hints" in the request body of the POST
|
||||
/shares request. These hints will invoke Affinity/Anti-Affinity scheduler
|
||||
filters during share creation and share migration.
|
||||
|
||||
2.66
|
||||
----
|
||||
Added filter search by group spec for share group type list.
|
||||
|
@ -11,14 +11,16 @@
|
||||
# under the License.
|
||||
|
||||
"""The group type API controller module."""
|
||||
import ast
|
||||
|
||||
from oslo_utils import strutils
|
||||
from oslo_utils import uuidutils
|
||||
import six
|
||||
from six.moves import http_client
|
||||
import webob
|
||||
from webob import exc
|
||||
|
||||
from manila.api import common
|
||||
from manila.api.openstack import api_version_request as api_version
|
||||
from manila.api.openstack import wsgi
|
||||
from manila.api.views import share_group_types as views
|
||||
from manila import exception
|
||||
@ -104,35 +106,27 @@ class ShareGroupTypesController(wsgi.Controller):
|
||||
context = req.environ['manila.context']
|
||||
if context.is_admin:
|
||||
# Only admin has query access to all group types
|
||||
filters['is_public'] = self._parse_is_public(
|
||||
filters['is_public'] = common.parse_is_public(
|
||||
req.params.get('is_public'))
|
||||
else:
|
||||
filters['is_public'] = True
|
||||
|
||||
group_specs = req.params.get('group_specs', {})
|
||||
group_specs_disallowed = (req.api_version_request <
|
||||
api_version.APIVersionRequest("2.66"))
|
||||
|
||||
if group_specs and group_specs_disallowed:
|
||||
msg = _("Filter by 'group_specs' is not supported by this "
|
||||
"microversion. Use 2.66 or greater microversion to "
|
||||
"be able to use filter search by 'group_specs.")
|
||||
raise webob.exc.HTTPBadRequest(explanation=msg)
|
||||
elif group_specs:
|
||||
filters['group_specs'] = ast.literal_eval(group_specs)
|
||||
|
||||
limited_types = share_group_types.get_all(
|
||||
context, search_opts=filters).values()
|
||||
return list(limited_types)
|
||||
|
||||
@staticmethod
|
||||
def _parse_is_public(is_public):
|
||||
"""Parse is_public into something usable.
|
||||
|
||||
:returns:
|
||||
- True: API should list public share group types only
|
||||
- False: API should list private share group types only
|
||||
- None: API should list both public and private share group types
|
||||
"""
|
||||
if is_public is None:
|
||||
# preserve default value of showing only public types
|
||||
return True
|
||||
elif six.text_type(is_public).lower() == "all":
|
||||
return None
|
||||
else:
|
||||
try:
|
||||
return strutils.bool_from_string(is_public, strict=True)
|
||||
except ValueError:
|
||||
msg = _('Invalid is_public filter [%s]') % is_public
|
||||
raise exc.HTTPBadRequest(explanation=msg)
|
||||
|
||||
@wsgi.Controller.authorize('create')
|
||||
def _create(self, req, body):
|
||||
"""Creates a new share group type."""
|
||||
|
@ -25,6 +25,7 @@ from six.moves import http_client
|
||||
import webob
|
||||
from webob import exc
|
||||
|
||||
from manila.api import common
|
||||
from manila.api.openstack import api_version_request as api_version
|
||||
from manila.api.openstack import wsgi
|
||||
from manila.api.views import types as views_types
|
||||
@ -125,7 +126,7 @@ class ShareTypesController(wsgi.Controller):
|
||||
context = req.environ['manila.context']
|
||||
if context.is_admin:
|
||||
# Only admin has query access to all share types
|
||||
filters['is_public'] = self._parse_is_public(
|
||||
filters['is_public'] = common.parse_is_public(
|
||||
req.params.get('is_public'))
|
||||
else:
|
||||
filters['is_public'] = True
|
||||
@ -148,26 +149,6 @@ class ShareTypesController(wsgi.Controller):
|
||||
context, search_opts=filters).values()
|
||||
return list(limited_types)
|
||||
|
||||
@staticmethod
|
||||
def _parse_is_public(is_public):
|
||||
"""Parse is_public into something usable.
|
||||
|
||||
* True: API should list public share types only
|
||||
* False: API should list private share types only
|
||||
* None: API should list both public and private share types
|
||||
"""
|
||||
if is_public is None:
|
||||
# preserve default value of showing only public types
|
||||
return True
|
||||
elif six.text_type(is_public).lower() == "all":
|
||||
return None
|
||||
else:
|
||||
try:
|
||||
return strutils.bool_from_string(is_public, strict=True)
|
||||
except ValueError:
|
||||
msg = _('Invalid is_public filter [%s]') % is_public
|
||||
raise exc.HTTPBadRequest(explanation=msg)
|
||||
|
||||
@wsgi.Controller.api_version("1.0", "2.23")
|
||||
@wsgi.action("create")
|
||||
def create(self, req, body):
|
||||
|
@ -344,6 +344,16 @@ class MiscFunctionsTest(test.TestCase):
|
||||
result = common.check_net_id_and_subnet_id(body)
|
||||
self.assertIsNone(result)
|
||||
|
||||
@ddt.data(None, True, 'true', 'false', 'all')
|
||||
def test_parse_is_public_valid(self, value):
|
||||
result = common.parse_is_public(value)
|
||||
self.assertIn(result, (True, False, None))
|
||||
|
||||
def test_parse_is_public_invalid(self):
|
||||
self.assertRaises(webob.exc.HTTPBadRequest,
|
||||
common.parse_is_public,
|
||||
'fakefakefake')
|
||||
|
||||
|
||||
@ddt.ddt
|
||||
class ViewBuilderTest(test.TestCase):
|
||||
|
@ -430,16 +430,6 @@ class ShareTypesAPITest(test.TestCase):
|
||||
self.assertDictEqual(expected_share_type,
|
||||
output['share_types'][i])
|
||||
|
||||
@ddt.data(None, True, 'true', 'false', 'all')
|
||||
def test_parse_is_public_valid(self, value):
|
||||
result = self.controller._parse_is_public(value)
|
||||
self.assertIn(result, (True, False, None))
|
||||
|
||||
def test_parse_is_public_invalid(self):
|
||||
self.assertRaises(webob.exc.HTTPBadRequest,
|
||||
self.controller._parse_is_public,
|
||||
'fakefakefake')
|
||||
|
||||
@ddt.data(
|
||||
("new_name", "new_description", "wrong_bool"),
|
||||
(" ", "new_description", "true"),
|
||||
|
@ -102,7 +102,7 @@ class ShareGroupTypesTestCase(test.TestCase):
|
||||
|
||||
def test_get_all_types_search(self):
|
||||
share_group_type = self.fake_type_w_extra
|
||||
search_filter = {"group_specs": {"gold": "True"}, 'is_public': True}
|
||||
search_filter = {'group_specs': {'gold': 'True'}, 'is_public': True}
|
||||
self.mock_object(
|
||||
db, 'share_group_type_get_all',
|
||||
mock.Mock(return_value=share_group_type))
|
||||
@ -113,11 +113,17 @@ class ShareGroupTypesTestCase(test.TestCase):
|
||||
db.share_group_type_get_all.assert_called_once_with(
|
||||
mock.ANY, 0, filters={'is_public': True})
|
||||
self.assertEqual(sorted(share_group_type), sorted(returned_type))
|
||||
search_filter = {"group_specs": {"gold": "False"}}
|
||||
search_filter = {'group_specs': {'gold': 'False'}}
|
||||
returned_type = share_group_types.get_all(
|
||||
self.context, search_opts=search_filter)
|
||||
self.assertEqual({}, returned_type)
|
||||
|
||||
share_group_type = self.fake_type_w_extra
|
||||
search_filter = {'group_specs': {'gold': 'True'}}
|
||||
returned_type = share_group_types.get_all(
|
||||
self.context, search_opts=search_filter)
|
||||
self.assertItemsEqual(share_group_type, returned_type)
|
||||
|
||||
def test_add_access(self):
|
||||
project_id = '456'
|
||||
share_group_type = share_group_types.create(self.context, 'type2', [])
|
||||
|
@ -0,0 +1,3 @@
|
||||
---
|
||||
features:
|
||||
- Share group types can now be filtered with its group_specs.
|
Loading…
Reference in New Issue
Block a user