Object-ify APIv2 flavorextraspecs extension
This makes the flavorextraspecs extension use the Flavor object. Related to blueprint compute-manager-objects-juno Change-Id: I28bcc24382f1e993b98b3f7342fed53c9ae85cbf
This commit is contained in:
parent
4115b522b3
commit
0c1484ec03
|
@ -21,8 +21,8 @@ from nova.api.openstack import extensions
|
|||
from nova.api.openstack import wsgi
|
||||
from nova.api.openstack import xmlutil
|
||||
from nova.compute import flavors
|
||||
from nova import db
|
||||
from nova import exception
|
||||
from nova import objects
|
||||
from nova.openstack.common.gettextutils import _
|
||||
from nova import utils
|
||||
|
||||
|
@ -48,8 +48,8 @@ class FlavorExtraSpecsController(object):
|
|||
"""The flavor extra specs API controller for the OpenStack API."""
|
||||
|
||||
def _get_extra_specs(self, context, flavor_id):
|
||||
extra_specs = db.flavor_extra_specs_get(context, flavor_id)
|
||||
return dict(extra_specs=extra_specs)
|
||||
flavor = objects.Flavor.get_by_flavor_id(context, flavor_id)
|
||||
return dict(extra_specs=flavor.extra_specs)
|
||||
|
||||
def _check_body(self, body):
|
||||
if body is None or body == "":
|
||||
|
@ -90,11 +90,13 @@ class FlavorExtraSpecsController(object):
|
|||
specs = body.get('extra_specs')
|
||||
self._check_extra_specs(specs)
|
||||
try:
|
||||
db.flavor_extra_specs_update_or_create(context,
|
||||
flavor_id,
|
||||
specs)
|
||||
flavor = objects.Flavor.get_by_flavor_id(context, flavor_id)
|
||||
flavor.extra_specs = dict(flavor.extra_specs, **specs)
|
||||
flavor.save()
|
||||
except exception.MetadataLimitExceeded as error:
|
||||
raise exc.HTTPBadRequest(explanation=error.format_message())
|
||||
except exception.FlavorNotFound as error:
|
||||
raise exc.HTTPNotFound(explanation=error.format_message())
|
||||
return body
|
||||
|
||||
@wsgi.serializers(xml=ExtraSpecTemplate)
|
||||
|
@ -109,11 +111,13 @@ class FlavorExtraSpecsController(object):
|
|||
expl = _('Request body contains too many items')
|
||||
raise exc.HTTPBadRequest(explanation=expl)
|
||||
try:
|
||||
db.flavor_extra_specs_update_or_create(context,
|
||||
flavor_id,
|
||||
body)
|
||||
flavor = objects.Flavor.get_by_flavor_id(context, flavor_id)
|
||||
flavor.extra_specs = dict(flavor.extra_specs, **body)
|
||||
flavor.save()
|
||||
except exception.MetadataLimitExceeded as error:
|
||||
raise exc.HTTPBadRequest(explanation=error.format_message())
|
||||
except exception.FlavorNotFound as error:
|
||||
raise exc.HTTPNotFound(explanation=error.format_message())
|
||||
return body
|
||||
|
||||
@wsgi.serializers(xml=ExtraSpecTemplate)
|
||||
|
@ -122,20 +126,31 @@ class FlavorExtraSpecsController(object):
|
|||
context = req.environ['nova.context']
|
||||
authorize(context, action='show')
|
||||
try:
|
||||
extra_spec = db.flavor_extra_specs_get_item(context,
|
||||
flavor_id, id)
|
||||
return extra_spec
|
||||
except exception.FlavorExtraSpecsNotFound:
|
||||
raise exc.HTTPNotFound()
|
||||
flavor = objects.Flavor.get_by_flavor_id(context, flavor_id)
|
||||
return {id: flavor.extra_specs[id]}
|
||||
except exception.FlavorNotFound as error:
|
||||
raise exc.HTTPNotFound(explanation=error.format_message())
|
||||
except KeyError:
|
||||
msg = _("Flavor %(flavor_id)s has no extra specs with "
|
||||
"key %(key)s.") % dict(flavor_id=flavor_id,
|
||||
key=id)
|
||||
raise exc.HTTPNotFound(explanation=msg)
|
||||
|
||||
def delete(self, req, flavor_id, id):
|
||||
"""Deletes an existing extra spec."""
|
||||
context = req.environ['nova.context']
|
||||
authorize(context, action='delete')
|
||||
try:
|
||||
db.flavor_extra_specs_delete(context, flavor_id, id)
|
||||
except exception.FlavorExtraSpecsNotFound as e:
|
||||
flavor = objects.Flavor.get_by_flavor_id(context, flavor_id)
|
||||
del flavor.extra_specs[id]
|
||||
flavor.save()
|
||||
except exception.FlavorNotFound as e:
|
||||
raise exc.HTTPNotFound(explanation=e.format_message())
|
||||
except KeyError:
|
||||
msg = _("Flavor %(flavor_id)s has no extra specs with "
|
||||
"key %(key)s.") % dict(flavor_id=flavor_id,
|
||||
key=id)
|
||||
raise exc.HTTPNotFound(explanation=msg)
|
||||
|
||||
|
||||
class Flavorextraspecs(extensions.ExtensionDescriptor):
|
||||
|
|
|
@ -21,6 +21,7 @@ import nova.db
|
|||
from nova import exception
|
||||
from nova import test
|
||||
from nova.tests.api.openstack import fakes
|
||||
from nova.tests.objects import test_flavor
|
||||
|
||||
|
||||
def return_create_flavor_extra_specs(context, flavor_id, extra_specs):
|
||||
|
@ -61,11 +62,13 @@ class FlavorsExtraSpecsTest(test.TestCase):
|
|||
self.controller = flavorextraspecs.FlavorExtraSpecsController()
|
||||
|
||||
def test_index(self):
|
||||
self.stubs.Set(nova.db, 'flavor_extra_specs_get',
|
||||
return_flavor_extra_specs)
|
||||
flavor = dict(test_flavor.fake_flavor,
|
||||
extra_specs={'key1': 'value1'})
|
||||
|
||||
req = fakes.HTTPRequest.blank('/v2/fake/flavors/1/os-extra_specs')
|
||||
res_dict = self.controller.index(req, 1)
|
||||
with mock.patch('nova.db.flavor_get_by_flavor_id') as mock_get:
|
||||
mock_get.return_value = flavor
|
||||
res_dict = self.controller.index(req, 1)
|
||||
|
||||
self.assertEqual('value1', res_dict['extra_specs']['key1'])
|
||||
|
||||
|
@ -79,12 +82,13 @@ class FlavorsExtraSpecsTest(test.TestCase):
|
|||
self.assertEqual(0, len(res_dict['extra_specs']))
|
||||
|
||||
def test_show(self):
|
||||
self.stubs.Set(nova.db, 'flavor_extra_specs_get_item',
|
||||
return_flavor_extra_specs_item)
|
||||
|
||||
flavor = dict(test_flavor.fake_flavor,
|
||||
extra_specs={'key5': 'value5'})
|
||||
req = fakes.HTTPRequest.blank('/v2/fake/flavors/1/os-extra_specs' +
|
||||
'/key5')
|
||||
res_dict = self.controller.show(req, 1, 'key5')
|
||||
with mock.patch('nova.db.flavor_get_by_flavor_id') as mock_get:
|
||||
mock_get.return_value = flavor
|
||||
res_dict = self.controller.show(req, 1, 'key5')
|
||||
|
||||
self.assertEqual('value5', res_dict['key5'])
|
||||
|
||||
|
@ -97,13 +101,36 @@ class FlavorsExtraSpecsTest(test.TestCase):
|
|||
self.assertRaises(webob.exc.HTTPNotFound, self.controller.show,
|
||||
req, 1, 'key6')
|
||||
|
||||
def test_not_found_because_flavor(self):
|
||||
req = fakes.HTTPRequestV3.blank('/flavors/1/extra-specs/key5',
|
||||
use_admin_context=True)
|
||||
with mock.patch('nova.db.flavor_get_by_flavor_id') as mock_get:
|
||||
mock_get.side_effect = exception.FlavorNotFound(flavor_id='1')
|
||||
self.assertRaises(webob.exc.HTTPNotFound, self.controller.show,
|
||||
req, 1, 'key5')
|
||||
self.assertRaises(webob.exc.HTTPNotFound, self.controller.update,
|
||||
req, 1, 'key5', {'key5': 'value5'})
|
||||
self.assertRaises(webob.exc.HTTPNotFound, self.controller.delete,
|
||||
req, 1, 'key5')
|
||||
|
||||
req = fakes.HTTPRequestV3.blank('/flavors/1/extra-specs',
|
||||
use_admin_context=True)
|
||||
with mock.patch('nova.db.flavor_get_by_flavor_id') as mock_get:
|
||||
mock_get.side_effect = exception.FlavorNotFound(flavor_id='1')
|
||||
self.assertRaises(webob.exc.HTTPNotFound, self.controller.create,
|
||||
req, 1, {'extra_specs': {'key5': 'value5'}})
|
||||
|
||||
def test_delete(self):
|
||||
flavor = dict(test_flavor.fake_flavor,
|
||||
extra_specs={'key5': 'value5'})
|
||||
self.stubs.Set(nova.db, 'flavor_extra_specs_delete',
|
||||
delete_flavor_extra_specs)
|
||||
|
||||
req = fakes.HTTPRequest.blank('/v2/fake/flavors/1/os-extra_specs' +
|
||||
'/key5', use_admin_context=True)
|
||||
self.controller.delete(req, 1, 'key5')
|
||||
with mock.patch('nova.db.flavor_get_by_flavor_id') as mock_get:
|
||||
mock_get.return_value = flavor
|
||||
self.controller.delete(req, 1, 'key5')
|
||||
|
||||
def test_delete_no_admin(self):
|
||||
self.stubs.Set(nova.db, 'flavor_extra_specs_delete',
|
||||
|
|
Loading…
Reference in New Issue