From d2b553030e29802f01baa0cac9cfb332aab0eb92 Mon Sep 17 00:00:00 2001 From: Andrew Laski Date: Tue, 19 Feb 2013 18:43:23 -0500 Subject: Add an extension to show image size. Adds image size data that is returned from Glance into the API response. This becomes really useful for users when they take a snapshot and want to track the storage used by it. Since this information is already being pulled by Nova we should display it. DocImpact Change-Id: I8a2d4001c21bcc54cac1a2992034dfc9fbe39d7e --- nova/api/openstack/compute/contrib/image_size.py | 88 ++++++++++++++++++++++++ nova/api/openstack/compute/images.py | 2 + 2 files changed, 90 insertions(+) create mode 100644 nova/api/openstack/compute/contrib/image_size.py (limited to 'nova/api') diff --git a/nova/api/openstack/compute/contrib/image_size.py b/nova/api/openstack/compute/contrib/image_size.py new file mode 100644 index 000000000..21998738f --- /dev/null +++ b/nova/api/openstack/compute/contrib/image_size.py @@ -0,0 +1,88 @@ +# Copyright 2013 Rackspace Hosting +# All Rights Reserved. +# +# 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 nova.api.openstack import extensions +from nova.api.openstack import wsgi +from nova.api.openstack import xmlutil + +authorize = extensions.soft_extension_authorizer('compute', 'image_size') + + +def make_image(elem): + elem.set('{%s}size' % Image_size.namespace, '%s:size' % Image_size.alias) + + +class ImagesSizeTemplate(xmlutil.TemplateBuilder): + def construct(self): + root = xmlutil.TemplateElement('images') + elem = xmlutil.SubTemplateElement(root, 'image', selector='images') + make_image(elem) + return xmlutil.SlaveTemplate(root, 1, nsmap={ + Image_size.alias: Image_size.namespace}) + + +class ImageSizeTemplate(xmlutil.TemplateBuilder): + def construct(self): + root = xmlutil.TemplateElement('image', selector='image') + make_image(root) + return xmlutil.SlaveTemplate(root, 1, nsmap={ + Image_size.alias: Image_size.namespace}) + + +class ImageSizeController(wsgi.Controller): + + def _extend_image(self, image, image_cache): + key = "%s:size" % Image_size.alias + image[key] = image_cache['size'] + + @wsgi.extends + def show(self, req, resp_obj, id): + context = req.environ["nova.context"] + if authorize(context): + # Attach our slave template to the response object + resp_obj.attach(xml=ImageSizeTemplate()) + image_resp = resp_obj.obj['image'] + # image guaranteed to be in the cache due to the core API adding + # it in its 'show' method + image_cached = req.get_db_item('images', image_resp['id']) + self._extend_image(image_resp, image_cached) + + @wsgi.extends + def detail(self, req, resp_obj): + context = req.environ['nova.context'] + if authorize(context): + # Attach our slave template to the response object + resp_obj.attach(xml=ImagesSizeTemplate()) + images_resp = list(resp_obj.obj['images']) + # images guaranteed to be in the cache due to the core API adding + # it in its 'detail' method + for image in images_resp: + image_cached = req.get_db_item('images', image['id']) + self._extend_image(image, image_cached) + + +class Image_size(extensions.ExtensionDescriptor): + """Adds image size to image listings.""" + + name = "ImageSize" + alias = "OS-EXT-IMG-SIZE" + namespace = ("http://docs.openstack.org/compute/ext/" + "image_size/api/v1.1") + updated = "2013-02-19T00:00:00+00:00" + + def get_controller_extensions(self): + controller = ImageSizeController() + extension = extensions.ControllerExtension(self, 'images', controller) + return [extension] diff --git a/nova/api/openstack/compute/images.py b/nova/api/openstack/compute/images.py index 7dda64f87..703d2fe2d 100644 --- a/nova/api/openstack/compute/images.py +++ b/nova/api/openstack/compute/images.py @@ -144,6 +144,7 @@ class Controller(wsgi.Controller): explanation = _("Image not found.") raise webob.exc.HTTPNotFound(explanation=explanation) + req.cache_db_items('images', [image], 'id') return self._view_builder.show(req, image) def delete(self, req, id): @@ -200,6 +201,7 @@ class Controller(wsgi.Controller): except exception.Invalid as e: raise webob.exc.HTTPBadRequest(explanation=str(e)) + req.cache_db_items('images', images, 'id') return self._view_builder.detail(req, images) def create(self, *args, **kwargs): -- cgit