Merge "Merged flavor_disabled extension into V3 core api"
This commit is contained in:
@@ -1,91 +0,0 @@
|
||||
# Copyright 2012 Nebula, Inc.
|
||||
#
|
||||
# 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.
|
||||
|
||||
"""The Flavor Disabled API extension."""
|
||||
|
||||
from nova.api.openstack import extensions
|
||||
from nova.api.openstack import wsgi
|
||||
from nova.api.openstack import xmlutil
|
||||
|
||||
ALIAS = 'os-flavor-disabled'
|
||||
authorize = extensions.soft_extension_authorizer('compute', 'v3:' + ALIAS)
|
||||
|
||||
|
||||
class FlavorDisabledController(wsgi.Controller):
|
||||
def _extend_flavors(self, req, flavors):
|
||||
for flavor in flavors:
|
||||
db_flavor = req.get_db_flavor(flavor['id'])
|
||||
key = "%s:disabled" % FlavorDisabled.alias
|
||||
flavor[key] = db_flavor['disabled']
|
||||
|
||||
def _show(self, req, resp_obj):
|
||||
if not authorize(req.environ['nova.context']):
|
||||
return
|
||||
if 'flavor' in resp_obj.obj:
|
||||
resp_obj.attach(xml=FlavorDisabledTemplate())
|
||||
self._extend_flavors(req, [resp_obj.obj['flavor']])
|
||||
|
||||
@wsgi.extends
|
||||
def show(self, req, resp_obj, id):
|
||||
return self._show(req, resp_obj)
|
||||
|
||||
@wsgi.extends(action='create')
|
||||
def create(self, req, resp_obj, body):
|
||||
return self._show(req, resp_obj)
|
||||
|
||||
@wsgi.extends
|
||||
def detail(self, req, resp_obj):
|
||||
if not authorize(req.environ['nova.context']):
|
||||
return
|
||||
resp_obj.attach(xml=FlavorsDisabledTemplate())
|
||||
self._extend_flavors(req, list(resp_obj.obj['flavors']))
|
||||
|
||||
|
||||
class FlavorDisabled(extensions.V3APIExtensionBase):
|
||||
"""Support to show the disabled status of a flavor."""
|
||||
|
||||
name = "FlavorDisabled"
|
||||
alias = ALIAS
|
||||
namespace = "http://docs.openstack.org/compute/ext/%s/api/v3" % ALIAS
|
||||
version = 1
|
||||
|
||||
def get_controller_extensions(self):
|
||||
controller = FlavorDisabledController()
|
||||
extension = extensions.ControllerExtension(self, 'flavors', controller)
|
||||
return [extension]
|
||||
|
||||
def get_resources(self):
|
||||
return []
|
||||
|
||||
|
||||
def make_flavor(elem):
|
||||
elem.set('{%s}disabled' % FlavorDisabled.namespace,
|
||||
'%s:disabled' % FlavorDisabled.alias)
|
||||
|
||||
|
||||
class FlavorDisabledTemplate(xmlutil.TemplateBuilder):
|
||||
def construct(self):
|
||||
root = xmlutil.TemplateElement('flavor', selector='flavor')
|
||||
make_flavor(root)
|
||||
return xmlutil.SlaveTemplate(root, 1, nsmap={
|
||||
FlavorDisabled.alias: FlavorDisabled.namespace})
|
||||
|
||||
|
||||
class FlavorsDisabledTemplate(xmlutil.TemplateBuilder):
|
||||
def construct(self):
|
||||
root = xmlutil.TemplateElement('flavors')
|
||||
elem = xmlutil.SubTemplateElement(root, 'flavor', selector='flavors')
|
||||
make_flavor(elem)
|
||||
return xmlutil.SlaveTemplate(root, 1, nsmap={
|
||||
FlavorDisabled.alias: FlavorDisabled.namespace})
|
||||
@@ -38,6 +38,7 @@ def make_flavor(elem, detailed=False):
|
||||
# NOTE(vish): this was originally added without a namespace
|
||||
elem.set('swap', xmlutil.EmptyStringSelector('swap'))
|
||||
elem.set('ephemeral', xmlutil.EmptyStringSelector('ephemeral'))
|
||||
elem.set('disabled')
|
||||
|
||||
xmlutil.make_links(elem, 'links')
|
||||
|
||||
|
||||
@@ -7,6 +7,7 @@
|
||||
<attribute name="vcpus"> <text/> </attribute>
|
||||
<attribute name="swap"> <text/> </attribute>
|
||||
<attribute name="ephemeral"> <text/> </attribute>
|
||||
<attribute name="disabled"> <text/> </attribute>
|
||||
<zeroOrMore>
|
||||
<externalRef href="../atom-link.rng"/>
|
||||
</zeroOrMore>
|
||||
|
||||
@@ -78,5 +78,6 @@ class V3ViewBuilder(ViewBuilder):
|
||||
flavor_dict['flavor'].update({
|
||||
"swap": flavor.get("swap") or "",
|
||||
"ephemeral": flavor.get("ephemeral_gb") or "",
|
||||
"disabled": flavor.get("disabled", False)
|
||||
})
|
||||
return flavor_dict
|
||||
|
||||
@@ -1,101 +0,0 @@
|
||||
# Copyright 2012 Nebula, Inc.
|
||||
#
|
||||
# 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 lxml import etree
|
||||
import webob
|
||||
|
||||
from nova.api.openstack.compute.plugins.v3 import flavor_disabled
|
||||
from nova.compute import flavors
|
||||
from nova.openstack.common import jsonutils
|
||||
from nova import test
|
||||
from nova.tests.api.openstack import fakes
|
||||
|
||||
FAKE_FLAVORS = {
|
||||
'flavor 1': {
|
||||
"flavorid": '1',
|
||||
"name": 'flavor 1',
|
||||
"memory_mb": '256',
|
||||
"root_gb": '10',
|
||||
"disabled": False,
|
||||
},
|
||||
'flavor 2': {
|
||||
"flavorid": '2',
|
||||
"name": 'flavor 2',
|
||||
"memory_mb": '512',
|
||||
"root_gb": '20',
|
||||
"disabled": True,
|
||||
},
|
||||
}
|
||||
|
||||
|
||||
def fake_flavor_get_by_flavor_id(flavorid):
|
||||
return FAKE_FLAVORS['flavor %s' % flavorid]
|
||||
|
||||
|
||||
def fake_flavor_get_all(*args, **kwargs):
|
||||
return FAKE_FLAVORS
|
||||
|
||||
|
||||
class FlavorDisabledTest(test.TestCase):
|
||||
content_type = 'application/json'
|
||||
prefix = '%s:' % flavor_disabled.FlavorDisabled.alias
|
||||
|
||||
def setUp(self):
|
||||
super(FlavorDisabledTest, self).setUp()
|
||||
fakes.stub_out_nw_api(self.stubs)
|
||||
self.stubs.Set(flavors, "get_all_flavors",
|
||||
fake_flavor_get_all)
|
||||
self.stubs.Set(flavors,
|
||||
"get_flavor_by_flavor_id",
|
||||
fake_flavor_get_by_flavor_id)
|
||||
|
||||
def _make_request(self, url):
|
||||
req = webob.Request.blank(url)
|
||||
req.headers['Accept'] = self.content_type
|
||||
app = fakes.wsgi_app_v3(init_only=('servers', 'flavors',
|
||||
'os-flavor-disabled'))
|
||||
return req.get_response(app)
|
||||
|
||||
def _get_flavor(self, body):
|
||||
return jsonutils.loads(body).get('flavor')
|
||||
|
||||
def _get_flavors(self, body):
|
||||
return jsonutils.loads(body).get('flavors')
|
||||
|
||||
def assertFlavorDisabled(self, flavor, disabled):
|
||||
self.assertEqual(str(flavor.get('%sdisabled' % self.prefix)), disabled)
|
||||
|
||||
def test_show(self):
|
||||
res = self._make_request('/v3/flavors/1')
|
||||
self.assertEqual(res.status_int, 200, res.body)
|
||||
self.assertFlavorDisabled(self._get_flavor(res.body), 'False')
|
||||
|
||||
def test_detail(self):
|
||||
res = self._make_request('/v3/flavors/detail')
|
||||
|
||||
self.assertEqual(res.status_int, 200, res.body)
|
||||
flavors = self._get_flavors(res.body)
|
||||
self.assertFlavorDisabled(flavors[0], 'False')
|
||||
self.assertFlavorDisabled(flavors[1], 'True')
|
||||
|
||||
|
||||
class FlavorDisabledXmlTest(FlavorDisabledTest):
|
||||
content_type = 'application/xml'
|
||||
prefix = '{%s}' % flavor_disabled.FlavorDisabled.namespace
|
||||
|
||||
def _get_flavor(self, body):
|
||||
return etree.XML(body)
|
||||
|
||||
def _get_flavors(self, body):
|
||||
return etree.XML(body).getchildren()
|
||||
@@ -22,6 +22,8 @@ import urlparse
|
||||
|
||||
from nova.api.openstack.compute.plugins.v3 import flavors
|
||||
from nova.api.openstack import xmlutil
|
||||
from nova.openstack.common import jsonutils
|
||||
|
||||
import nova.compute.flavors
|
||||
from nova import context
|
||||
from nova import db
|
||||
@@ -42,6 +44,7 @@ FAKE_FLAVORS = {
|
||||
"root_gb": '10',
|
||||
"swap": '512',
|
||||
"ephemeral_gb": '1',
|
||||
"disabled": False,
|
||||
},
|
||||
'flavor 2': {
|
||||
"flavorid": '2',
|
||||
@@ -50,6 +53,7 @@ FAKE_FLAVORS = {
|
||||
"root_gb": '20',
|
||||
"swap": '1024',
|
||||
"ephemeral_gb": '10',
|
||||
"disabled": True,
|
||||
},
|
||||
}
|
||||
|
||||
@@ -118,6 +122,7 @@ class FlavorsTest(test.TestCase):
|
||||
"vcpus": "",
|
||||
"swap": '512',
|
||||
"ephemeral": "1",
|
||||
"disabled": False,
|
||||
"links": [
|
||||
{
|
||||
"rel": "self",
|
||||
@@ -146,6 +151,7 @@ class FlavorsTest(test.TestCase):
|
||||
"vcpus": "",
|
||||
"swap": '512',
|
||||
"ephemeral": "1",
|
||||
"disabled": False,
|
||||
"links": [
|
||||
{
|
||||
"rel": "self",
|
||||
@@ -314,6 +320,7 @@ class FlavorsTest(test.TestCase):
|
||||
"vcpus": "",
|
||||
"swap": '512',
|
||||
"ephemeral": "1",
|
||||
"disabled": False,
|
||||
"links": [
|
||||
{
|
||||
"rel": "self",
|
||||
@@ -333,6 +340,7 @@ class FlavorsTest(test.TestCase):
|
||||
"vcpus": "",
|
||||
"swap": '1024',
|
||||
"ephemeral": "10",
|
||||
"disabled": True,
|
||||
"links": [
|
||||
{
|
||||
"rel": "self",
|
||||
@@ -434,6 +442,7 @@ class FlavorsTest(test.TestCase):
|
||||
"vcpus": "",
|
||||
"swap": '1024',
|
||||
"ephemeral": "10",
|
||||
"disabled": True,
|
||||
"links": [
|
||||
{
|
||||
"rel": "self",
|
||||
@@ -450,6 +459,62 @@ class FlavorsTest(test.TestCase):
|
||||
self.assertEqual(flavor, expected)
|
||||
|
||||
|
||||
class FlavorDisabledTest(test.TestCase):
|
||||
content_type = 'application/json'
|
||||
|
||||
def setUp(self):
|
||||
super(FlavorDisabledTest, self).setUp()
|
||||
fakes.stub_out_nw_api(self.stubs)
|
||||
|
||||
#def fake_flavor_get_all(*args, **kwargs):
|
||||
# return FAKE_FLAVORS
|
||||
#
|
||||
self.stubs.Set(nova.compute.flavors, "get_all_flavors",
|
||||
fake_flavor_get_all)
|
||||
self.stubs.Set(nova.compute.flavors,
|
||||
"get_flavor_by_flavor_id",
|
||||
fake_flavor_get_by_flavor_id)
|
||||
|
||||
def _make_request(self, url):
|
||||
req = webob.Request.blank(url)
|
||||
req.headers['Accept'] = self.content_type
|
||||
app = fakes.wsgi_app_v3(init_only=('servers', 'flavors',
|
||||
'os-flavor-disabled'))
|
||||
return req.get_response(app)
|
||||
|
||||
def _get_flavor(self, body):
|
||||
return jsonutils.loads(body).get('flavor')
|
||||
|
||||
def _get_flavors(self, body):
|
||||
return jsonutils.loads(body).get('flavors')
|
||||
|
||||
def assertFlavorDisabled(self, flavor, disabled):
|
||||
self.assertEqual(str(flavor.get('disabled')), disabled)
|
||||
|
||||
def test_show(self):
|
||||
res = self._make_request('/v3/flavors/1')
|
||||
self.assertEqual(res.status_int, 200, res.body)
|
||||
self.assertFlavorDisabled(self._get_flavor(res.body), 'False')
|
||||
|
||||
def test_detail(self):
|
||||
res = self._make_request('/v3/flavors/detail')
|
||||
|
||||
self.assertEqual(res.status_int, 200, res.body)
|
||||
flavors = self._get_flavors(res.body)
|
||||
self.assertFlavorDisabled(flavors[0], 'False')
|
||||
self.assertFlavorDisabled(flavors[1], 'True')
|
||||
|
||||
|
||||
class FlavorDisabledXmlTest(FlavorDisabledTest):
|
||||
content_type = 'application/xml'
|
||||
|
||||
def _get_flavor(self, body):
|
||||
return etree.XML(body)
|
||||
|
||||
def _get_flavors(self, body):
|
||||
return etree.XML(body).getchildren()
|
||||
|
||||
|
||||
class FlavorsXMLSerializationTest(test.TestCase):
|
||||
def _create_flavor(self):
|
||||
id = 0
|
||||
@@ -463,6 +528,7 @@ class FlavorsXMLSerializationTest(test.TestCase):
|
||||
"vcpus": "",
|
||||
"swap": "512",
|
||||
"ephemeral": "512",
|
||||
"disabled": False,
|
||||
"links": [
|
||||
{
|
||||
"rel": "self",
|
||||
|
||||
@@ -80,7 +80,6 @@ nova.api.v3.extensions =
|
||||
flavors = nova.api.openstack.compute.plugins.v3.flavors:Flavors
|
||||
flavors_extraspecs = nova.api.openstack.compute.plugins.v3.flavors_extraspecs:FlavorsExtraSpecs
|
||||
flavor_access = nova.api.openstack.compute.plugins.v3.flavor_access:FlavorAccess
|
||||
flavor_disabled = nova.api.openstack.compute.plugins.v3.flavor_disabled:FlavorDisabled
|
||||
flavor_rxtx = nova.api.openstack.compute.plugins.v3.flavor_rxtx:FlavorRxtx
|
||||
hide_server_addresses = nova.api.openstack.compute.plugins.v3.hide_server_addresses:HideServerAddresses
|
||||
hosts = nova.api.openstack.compute.plugins.v3.hosts:Hosts
|
||||
|
||||
Reference in New Issue
Block a user