diff options
author | vladimir.p <vladimir@zadarastorage.com> | 2011-08-24 16:48:04 -0700 |
---|---|---|
committer | vladimir.p <vladimir@zadarastorage.com> | 2011-08-24 16:48:04 -0700 |
commit | 08af6ab6325e27b60d3d036d6e780f8e594234cc (patch) | |
tree | 08cf95e9b1a5fd8e2486357a24bab8b07781ac55 /nova/volume/api.py | |
parent | 48cd9689de31e408c792052747f714a9dbe1f8f7 (diff) | |
parent | 96f85f94f23c9eeac3f43e122d2992b6d0938827 (diff) | |
download | nova-08af6ab6325e27b60d3d036d6e780f8e594234cc.tar.gz nova-08af6ab6325e27b60d3d036d6e780f8e594234cc.tar.xz nova-08af6ab6325e27b60d3d036d6e780f8e594234cc.zip |
merged with volume_types. no code refactoring yet
Diffstat (limited to 'nova/volume/api.py')
-rw-r--r-- | nova/volume/api.py | 89 |
1 files changed, 78 insertions, 11 deletions
diff --git a/nova/volume/api.py b/nova/volume/api.py index 6b220cc54..e66792373 100644 --- a/nova/volume/api.py +++ b/nova/volume/api.py @@ -42,8 +42,9 @@ class API(base.Base): """API for interacting with the volume manager.""" def create(self, context, size, snapshot_id, name, description, - to_vsa_id=None, from_vsa_id=None, drive_type_id=None, - availability_zone=None): + volume_type=None, metadata=None, + to_vsa_id=None, from_vsa_id=None, drive_type_id=None, + availability_zone=None): if snapshot_id != None: snapshot = self.get_snapshot(context, snapshot_id) if snapshot['status'] != "available": @@ -52,11 +53,7 @@ class API(base.Base): if not size: size = snapshot['volume_size'] - if availability_zone is None: - availability_zone = FLAGS.storage_availability_zone - if to_vsa_id is None: - # Check quotas for non-VSA volumes only if quota.allowed_volumes(context, 1, size) < 1: pid = context.project_id LOG.warn(_("Quota exceeded for %(pid)s, tried to create" @@ -64,6 +61,14 @@ class API(base.Base): raise quota.QuotaError(_("Volume quota exceeded. You cannot " "create a volume of size %sG") % size) + if availability_zone is None: + availability_zone = FLAGS.storage_availability_zone + + if volume_type is None: + volume_type_id = None + else: + volume_type_id = volume_type.get('id', None) + options = { 'size': size, 'user_id': context.user_id, @@ -74,9 +79,12 @@ class API(base.Base): 'attach_status': "detached", 'display_name': name, 'display_description': description, + 'volume_type_id': volume_type_id, + 'metadata': metadata, 'to_vsa_id': to_vsa_id, 'from_vsa_id': from_vsa_id, - 'drive_type_id': drive_type_id} + 'drive_type_id': drive_type_id, + } volume = self.db.volume_create(context, options) if from_vsa_id is not None: # for FE VSA volumes do nothing @@ -115,7 +123,6 @@ class API(base.Base): if volume['status'] != "available": raise exception.ApiError(_("Volume status must be available")) - now = utils.utcnow() self.db.volume_update(context, volume_id, {'status': 'deleting', 'terminated_at': now}) @@ -132,10 +139,44 @@ class API(base.Base): rv = self.db.volume_get(context, volume_id) return dict(rv.iteritems()) - def get_all(self, context): + def get_all(self, context, search_opts={}): if context.is_admin: - return self.db.volume_get_all(context) - return self.db.volume_get_all_by_project(context, context.project_id) + volumes = self.db.volume_get_all(context) + else: + volumes = self.db.volume_get_all_by_project(context, + context.project_id) + + if search_opts: + LOG.debug(_("Searching by: %s") % str(search_opts)) + + def _check_metadata_match(volume, searchdict): + volume_metadata = {} + for i in volume.get('volume_metadata'): + volume_metadata[i['key']] = i['value'] + + for k, v in searchdict: + if k not in volume_metadata.keys()\ + or volume_metadata[k] != v: + return False + return True + + # search_option to filter_name mapping. + filter_mapping = {'metadata': _check_metadata_match} + + for volume in volumes: + # go over all filters in the list + for opt, values in search_opts.iteritems(): + try: + filter_func = filter_mapping[opt] + except KeyError: + # no such filter - ignore it, go to next filter + continue + else: + if filter_func(volume, values) == False: + # if one of conditions didn't match - remove + volumes.remove(volume) + break + return volumes def get_all_by_vsa(self, context, vsa_id, direction): if direction == "to": @@ -219,3 +260,29 @@ class API(base.Base): {"method": "delete_snapshot", "args": {"topic": FLAGS.volume_topic, "snapshot_id": snapshot_id}}) + + def get_volume_metadata(self, context, volume_id): + """Get all metadata associated with a volume.""" + rv = self.db.volume_metadata_get(context, volume_id) + return dict(rv.iteritems()) + + def delete_volume_metadata(self, context, volume_id, key): + """Delete the given metadata item from an volume.""" + self.db.volume_metadata_delete(context, volume_id, key) + + def update_volume_metadata(self, context, volume_id, + metadata, delete=False): + """Updates or creates volume metadata. + + If delete is True, metadata items that are not specified in the + `metadata` argument will be deleted. + + """ + if delete: + _metadata = metadata + else: + _metadata = self.get_volume_metadata(context, volume_id) + _metadata.update(metadata) + + self.db.volume_metadata_update(context, volume_id, _metadata, True) + return _metadata |