Merge "Check volume and minimum disk sizes to create volume"
diff --git a/tempest/api/compute/admin/test_floating_ips_bulk.py b/tempest/api/compute/admin/test_floating_ips_bulk.py
index e207aed..a4695b0 100644
--- a/tempest/api/compute/admin/test_floating_ips_bulk.py
+++ b/tempest/api/compute/admin/test_floating_ips_bulk.py
@@ -17,6 +17,7 @@
from tempest.api.compute import base
from tempest import config
+from tempest.lib.common.utils import test_utils
from tempest.lib import exceptions
from tempest import test
@@ -54,12 +55,6 @@
raise exceptions.InvalidConfiguration(msg)
return
- def _delete_floating_ips_bulk(self, ip_range):
- try:
- self.client.delete_floating_ips_bulk(ip_range)
- except Exception:
- pass
-
@test.idempotent_id('2c8f145f-8012-4cb8-ac7e-95a587f0e4ab')
@test.services('network')
def test_create_list_delete_floating_ips_bulk(self):
@@ -73,7 +68,8 @@
pool,
interface)
['floating_ips_bulk_create'])
- self.addCleanup(self._delete_floating_ips_bulk, self.ip_range)
+ self.addCleanup(test_utils.call_and_ignore_notfound_exc,
+ self.client.delete_floating_ips_bulk, self.ip_range)
self.assertEqual(self.ip_range, body['ip_range'])
ips_list = self.client.list_floating_ips_bulk()['floating_ip_info']
self.assertNotEqual(0, len(ips_list))
diff --git a/tempest/api/compute/admin/test_hosts_negative.py b/tempest/api/compute/admin/test_hosts_negative.py
index c270829..3821b22 100644
--- a/tempest/api/compute/admin/test_hosts_negative.py
+++ b/tempest/api/compute/admin/test_hosts_negative.py
@@ -13,7 +13,6 @@
# under the License.
from tempest.api.compute import base
-from tempest.common.utils import data_utils
from tempest.lib import exceptions as lib_exc
from tempest import test
@@ -27,11 +26,13 @@
cls.client = cls.os_adm.hosts_client
cls.non_admin_client = cls.os.hosts_client
- def _get_host_name(self):
- hosts = self.client.list_hosts()['hosts']
- self.assertGreaterEqual(len(hosts), 1)
- hostname = hosts[0]['host_name']
- return hostname
+ @classmethod
+ def resource_setup(cls):
+ super(HostsAdminNegativeTestJSON, cls).resource_setup()
+ hosts = cls.client.list_hosts()['hosts']
+ if not hosts:
+ raise lib_exc.NotFound("no host found")
+ cls.hostname = hosts[0]['host_name']
@test.attr(type=['negative'])
@test.idempotent_id('dd032027-0210-4d9c-860e-69b1b8deed5f')
@@ -42,27 +43,22 @@
@test.attr(type=['negative'])
@test.idempotent_id('e75b0a1a-041f-47a1-8b4a-b72a6ff36d3f')
def test_show_host_detail_with_nonexistent_hostname(self):
- nonexitent_hostname = data_utils.rand_name('rand_hostname')
self.assertRaises(lib_exc.NotFound,
- self.client.show_host, nonexitent_hostname)
+ self.client.show_host, 'nonexistent_hostname')
@test.attr(type=['negative'])
@test.idempotent_id('19ebe09c-bfd4-4b7c-81a2-e2e0710f59cc')
def test_show_host_detail_with_non_admin_user(self):
- hostname = self._get_host_name()
-
self.assertRaises(lib_exc.Forbidden,
self.non_admin_client.show_host,
- hostname)
+ self.hostname)
@test.attr(type=['negative'])
@test.idempotent_id('e40c72b1-0239-4ed6-ba21-81a184df1f7c')
def test_update_host_with_non_admin_user(self):
- hostname = self._get_host_name()
-
self.assertRaises(lib_exc.Forbidden,
self.non_admin_client.update_host,
- hostname,
+ self.hostname,
status='enable',
maintenance_mode='enable')
@@ -70,11 +66,9 @@
@test.idempotent_id('fbe2bf3e-3246-4a95-a59f-94e4e298ec77')
def test_update_host_with_invalid_status(self):
# 'status' can only be 'enable' or 'disable'
- hostname = self._get_host_name()
-
self.assertRaises(lib_exc.BadRequest,
self.client.update_host,
- hostname,
+ self.hostname,
status='invalid',
maintenance_mode='enable')
@@ -82,11 +76,9 @@
@test.idempotent_id('ab1e230e-5e22-41a9-8699-82b9947915d4')
def test_update_host_with_invalid_maintenance_mode(self):
# 'maintenance_mode' can only be 'enable' or 'disable'
- hostname = self._get_host_name()
-
self.assertRaises(lib_exc.BadRequest,
self.client.update_host,
- hostname,
+ self.hostname,
status='enable',
maintenance_mode='invalid')
@@ -94,73 +86,57 @@
@test.idempotent_id('0cd85f75-6992-4a4a-b1bd-d11e37fd0eee')
def test_update_host_without_param(self):
# 'status' or 'maintenance_mode' needed for host update
- hostname = self._get_host_name()
-
self.assertRaises(lib_exc.BadRequest,
self.client.update_host,
- hostname)
+ self.hostname)
@test.attr(type=['negative'])
@test.idempotent_id('23c92146-2100-4d68-b2d6-c7ade970c9c1')
def test_update_nonexistent_host(self):
- nonexitent_hostname = data_utils.rand_name('rand_hostname')
-
self.assertRaises(lib_exc.NotFound,
self.client.update_host,
- nonexitent_hostname,
+ 'nonexistent_hostname',
status='enable',
maintenance_mode='enable')
@test.attr(type=['negative'])
@test.idempotent_id('0d981ac3-4320-4898-b674-82b61fbb60e4')
def test_startup_nonexistent_host(self):
- nonexitent_hostname = data_utils.rand_name('rand_hostname')
-
self.assertRaises(lib_exc.NotFound,
self.client.startup_host,
- nonexitent_hostname)
+ 'nonexistent_hostname')
@test.attr(type=['negative'])
@test.idempotent_id('9f4ebb7e-b2ae-4e5b-a38f-0fd1bb0ddfca')
def test_startup_host_with_non_admin_user(self):
- hostname = self._get_host_name()
-
self.assertRaises(lib_exc.Forbidden,
self.non_admin_client.startup_host,
- hostname)
+ self.hostname)
@test.attr(type=['negative'])
@test.idempotent_id('9e637444-29cf-4244-88c8-831ae82c31b6')
def test_shutdown_nonexistent_host(self):
- nonexitent_hostname = data_utils.rand_name('rand_hostname')
-
self.assertRaises(lib_exc.NotFound,
self.client.shutdown_host,
- nonexitent_hostname)
+ 'nonexistent_hostname')
@test.attr(type=['negative'])
@test.idempotent_id('a803529c-7e3f-4d3c-a7d6-8e1c203d27f6')
def test_shutdown_host_with_non_admin_user(self):
- hostname = self._get_host_name()
-
self.assertRaises(lib_exc.Forbidden,
self.non_admin_client.shutdown_host,
- hostname)
+ self.hostname)
@test.attr(type=['negative'])
@test.idempotent_id('f86bfd7b-0b13-4849-ae29-0322e83ee58b')
def test_reboot_nonexistent_host(self):
- nonexitent_hostname = data_utils.rand_name('rand_hostname')
-
self.assertRaises(lib_exc.NotFound,
self.client.reboot_host,
- nonexitent_hostname)
+ 'nonexistent_hostname')
@test.attr(type=['negative'])
@test.idempotent_id('02d79bb9-eb57-4612-abf6-2cb38897d2f8')
def test_reboot_host_with_non_admin_user(self):
- hostname = self._get_host_name()
-
self.assertRaises(lib_exc.Forbidden,
self.non_admin_client.reboot_host,
- hostname)
+ self.hostname)
diff --git a/tempest/api/compute/admin/test_quotas.py b/tempest/api/compute/admin/test_quotas.py
index 7d97ce2..ce0adb4 100644
--- a/tempest/api/compute/admin/test_quotas.py
+++ b/tempest/api/compute/admin/test_quotas.py
@@ -74,7 +74,8 @@
'ram': 10240, 'floating_ips': 20, 'fixed_ips': 10,
'key_pairs': 200, 'injected_file_path_bytes': 512,
'instances': 20, 'security_group_rules': 20,
- 'cores': 2, 'security_groups': 20}
+ 'cores': 2, 'security_groups': 20,
+ 'server_groups': 20, 'server_group_members': 20}
# Update limits for all quota resources
quota_set = self.adm_client.update_quota_set(
self.demo_tenant_id,
@@ -82,13 +83,6 @@
**new_quota_set)['quota_set']
default_quota_set.pop('id')
- # NOTE(PhilDay) The following is safe as we're not updating these
- # two quota values yet. Once the Nova change to add these is merged
- # and the client updated to support them this can be removed
- if 'server_groups' in default_quota_set:
- default_quota_set.pop('server_groups')
- if 'server_group_members' in default_quota_set:
- default_quota_set.pop('server_group_members')
self.addCleanup(self.adm_client.update_quota_set,
self.demo_tenant_id, **default_quota_set)
for quota in new_quota_set:
diff --git a/tempest/api/compute/admin/test_quotas_negative.py b/tempest/api/compute/admin/test_quotas_negative.py
index d6aba5b..015e14d 100644
--- a/tempest/api/compute/admin/test_quotas_negative.py
+++ b/tempest/api/compute/admin/test_quotas_negative.py
@@ -40,6 +40,17 @@
# tenant most of them should be skipped if we can't do that
cls.demo_tenant_id = cls.client.tenant_id
+ def _update_quota(self, quota_item, quota_value):
+ quota_set = (self.adm_client.show_quota_set(self.demo_tenant_id)
+ ['quota_set'])
+ default_quota_value = quota_set[quota_item]
+
+ self.adm_client.update_quota_set(self.demo_tenant_id,
+ force=True,
+ **{quota_item: quota_value})
+ self.addCleanup(self.adm_client.update_quota_set, self.demo_tenant_id,
+ **{quota_item: default_quota_value})
+
@test.attr(type=['negative'])
@test.idempotent_id('733abfe8-166e-47bb-8363-23dbd7ff3476')
def test_update_quota_normal_user(self):
@@ -54,17 +65,7 @@
@test.idempotent_id('91058876-9947-4807-9f22-f6eb17140d9b')
def test_create_server_when_cpu_quota_is_full(self):
# Disallow server creation when tenant's vcpu quota is full
- quota_set = (self.adm_client.show_quota_set(self.demo_tenant_id)
- ['quota_set'])
- default_vcpu_quota = quota_set['cores']
- vcpu_quota = 0 # Set the quota to zero to conserve resources
-
- self.adm_client.update_quota_set(self.demo_tenant_id,
- force=True,
- cores=vcpu_quota)
-
- self.addCleanup(self.adm_client.update_quota_set, self.demo_tenant_id,
- cores=default_vcpu_quota)
+ self._update_quota('cores', 0)
self.assertRaises((lib_exc.Forbidden, lib_exc.OverLimit),
self.create_test_server)
@@ -72,17 +73,7 @@
@test.idempotent_id('6fdd7012-584d-4327-a61c-49122e0d5864')
def test_create_server_when_memory_quota_is_full(self):
# Disallow server creation when tenant's memory quota is full
- quota_set = (self.adm_client.show_quota_set(self.demo_tenant_id)
- ['quota_set'])
- default_mem_quota = quota_set['ram']
- mem_quota = 0 # Set the quota to zero to conserve resources
-
- self.adm_client.update_quota_set(self.demo_tenant_id,
- force=True,
- ram=mem_quota)
-
- self.addCleanup(self.adm_client.update_quota_set, self.demo_tenant_id,
- ram=default_mem_quota)
+ self._update_quota('ram', 0)
self.assertRaises((lib_exc.Forbidden, lib_exc.OverLimit),
self.create_test_server)
@@ -90,16 +81,7 @@
@test.idempotent_id('7c6be468-0274-449a-81c3-ac1c32ee0161')
def test_create_server_when_instances_quota_is_full(self):
# Once instances quota limit is reached, disallow server creation
- quota_set = (self.adm_client.show_quota_set(self.demo_tenant_id)
- ['quota_set'])
- default_instances_quota = quota_set['instances']
- instances_quota = 0 # Set quota to zero to disallow server creation
-
- self.adm_client.update_quota_set(self.demo_tenant_id,
- force=True,
- instances=instances_quota)
- self.addCleanup(self.adm_client.update_quota_set, self.demo_tenant_id,
- instances=default_instances_quota)
+ self._update_quota('instances', 0)
self.assertRaises((lib_exc.Forbidden, lib_exc.OverLimit),
self.create_test_server)
@@ -109,22 +91,10 @@
@test.services('network')
def test_security_groups_exceed_limit(self):
# Negative test: Creation Security Groups over limit should FAIL
-
- quota_set = (self.adm_client.show_quota_set(self.demo_tenant_id)
- ['quota_set'])
- default_sg_quota = quota_set['security_groups']
-
# Set the quota to number of used security groups
sg_quota = self.limits_client.show_limits()['limits']['absolute'][
'totalSecurityGroupsUsed']
-
- self.adm_client.update_quota_set(self.demo_tenant_id,
- force=True,
- security_groups=sg_quota)
-
- self.addCleanup(self.adm_client.update_quota_set,
- self.demo_tenant_id,
- security_groups=default_sg_quota)
+ self._update_quota('security_groups', sg_quota)
# Check we cannot create anymore
# A 403 Forbidden or 413 Overlimit (old behaviour) exception
@@ -141,19 +111,7 @@
def test_security_groups_rules_exceed_limit(self):
# Negative test: Creation of Security Group Rules should FAIL
# when we reach limit maxSecurityGroupRules
-
- quota_set = (self.adm_client.show_quota_set(self.demo_tenant_id)
- ['quota_set'])
- default_sg_rules_quota = quota_set['security_group_rules']
- sg_rules_quota = 0 # Set the quota to zero to conserve resources
-
- self.adm_client.update_quota_set(self.demo_tenant_id,
- force=True,
- security_group_rules=sg_rules_quota)
-
- self.addCleanup(self.adm_client.update_quota_set,
- self.demo_tenant_id,
- security_group_rules=default_sg_rules_quota)
+ self._update_quota('security_group_rules', 0)
s_name = data_utils.rand_name('securitygroup')
s_description = data_utils.rand_name('description')
diff --git a/tempest/api/compute/servers/test_server_metadata.py b/tempest/api/compute/servers/test_server_metadata.py
index cb66e81..847b7a1 100644
--- a/tempest/api/compute/servers/test_server_metadata.py
+++ b/tempest/api/compute/servers/test_server_metadata.py
@@ -23,7 +23,6 @@
def setup_clients(cls):
super(ServerMetadataTestJSON, cls).setup_clients()
cls.client = cls.servers_client
- cls.quotas = cls.quotas_client
@classmethod
def resource_setup(cls):
diff --git a/tempest/api/compute/servers/test_server_metadata_negative.py b/tempest/api/compute/servers/test_server_metadata_negative.py
index aae9101..62b8962 100644
--- a/tempest/api/compute/servers/test_server_metadata_negative.py
+++ b/tempest/api/compute/servers/test_server_metadata_negative.py
@@ -25,7 +25,6 @@
def setup_clients(cls):
super(ServerMetadataNegativeTestJSON, cls).setup_clients()
cls.client = cls.servers_client
- cls.quotas = cls.quotas_client
@classmethod
def resource_setup(cls):
@@ -134,7 +133,8 @@
# A 403 Forbidden or 413 Overlimit (old behaviour) exception
# will be raised while exceeding metadata items limit for
# tenant.
- quota_set = self.quotas.show_quota_set(self.tenant_id)['quota_set']
+ quota_set = self.quotas_client.show_quota_set(
+ self.tenant_id)['quota_set']
quota_metadata = quota_set['metadata_items']
if quota_metadata == -1:
raise self.skipException("No limit for metadata_items")
diff --git a/tempest/api/compute/volumes/test_volume_snapshots.py b/tempest/api/compute/volumes/test_volume_snapshots.py
index 460c882..01718cc 100644
--- a/tempest/api/compute/volumes/test_volume_snapshots.py
+++ b/tempest/api/compute/volumes/test_volume_snapshots.py
@@ -13,6 +13,8 @@
# License for the specific language governing permissions and limitations
# under the License.
+import testtools
+
from tempest.api.compute import base
from tempest.common.utils import data_utils
from tempest.common import waiters
@@ -39,6 +41,8 @@
cls.snapshots_client = cls.snapshots_extensions_client
@test.idempotent_id('cd4ec87d-7825-450d-8040-6e2068f2da8f')
+ @testtools.skipUnless(CONF.volume_feature_enabled.snapshot,
+ 'Cinder volume snapshots are disabled')
def test_volume_snapshot_create_get_list_delete(self):
volume = self.create_volume()
self.addCleanup(self.delete_volume, volume['id'])
diff --git a/tempest/api/image/v2/test_images.py b/tempest/api/image/v2/test_images.py
index 5cf8084..42912f0 100644
--- a/tempest/api/image/v2/test_images.py
+++ b/tempest/api/image/v2/test_images.py
@@ -129,7 +129,6 @@
class ListImagesTest(base.BaseV2ImageTest):
- """Here we test the listing of image information"""
@classmethod
def resource_setup(cls):
@@ -157,23 +156,49 @@
"""
size = random.randint(1024, 4096)
image_file = six.BytesIO(data_utils.random_bytes(size))
+ tags = [data_utils.rand_name('tag'), data_utils.rand_name('tag')]
image = cls.create_image(container_format=container_format,
disk_format=disk_format,
- visibility='private')
+ visibility='private',
+ tags=tags)
cls.client.store_image_file(image['id'], data=image_file)
+ # Keep the data of one test image so it can be used to filter lists
+ cls.test_data = image
+ cls.test_data['size'] = size
return image['id']
+
+class ListUserImagesTest(ListImagesTest):
+ """Here we test the listing of image information"""
+
def _list_by_param_value_and_assert(self, params):
"""Perform list action with given params and validates result."""
-
+ # Retrieve the list of images that meet the filter
images_list = self.client.list_images(params=params)['images']
# Validating params of fetched images
+ msg = 'No images were found that met the filter criteria.'
+ self.assertNotEmpty(images_list, msg)
for image in images_list:
for key in params:
msg = "Failed to list images by %s" % key
self.assertEqual(params[key], image[key], msg)
+ def _list_sorted_by_image_size_and_assert(self, params, desc=False):
+ """Validate an image list that has been sorted by size
+
+ Perform list action with given params and validates the results are
+ sorted by image size in either ascending or descending order.
+ """
+ # Retrieve the list of images that meet the filter
+ images_list = self.client.list_images(params=params)['images']
+ # Validate that the list was fetched sorted accordingly
+ msg = 'No images were found that met the filter criteria.'
+ self.assertNotEmpty(images_list, msg)
+ sorted_list = [image['size'] for image in images_list]
+ msg = 'The list of images was not sorted correctly.'
+ self.assertEqual(sorted(sorted_list, reverse=desc), sorted_list, msg)
+
@test.idempotent_id('1e341d7a-90a9-494c-b143-2cdf2aeb6aee')
def test_list_no_params(self):
# Simple test to see all fixture images returned
@@ -185,8 +210,8 @@
@test.idempotent_id('9959ca1d-1aa7-4b7a-a1ea-0fff0499b37e')
def test_list_images_param_container_format(self):
- # Test to get all images with container_format='bare'
- params = {"container_format": "bare"}
+ # Test to get all images with a specific container_format
+ params = {"container_format": self.test_data['container_format']}
self._list_by_param_value_and_assert(params)
@test.idempotent_id('4a4735a7-f22f-49b6-b0d9-66e1ef7453eb')
@@ -254,6 +279,37 @@
params = {"owner": image['owner']}
self._list_by_param_value_and_assert(params)
+ @test.idempotent_id('55c8f5f5-bfed-409d-a6d5-4caeda985d7b')
+ def test_list_images_param_name(self):
+ # Test to get images by name
+ params = {'name': self.test_data['name']}
+ self._list_by_param_value_and_assert(params)
+
+ @test.idempotent_id('aa8ac4df-cff9-418b-8d0f-dd9c67b072c9')
+ def test_list_images_param_tag(self):
+ # Test to get images matching a tag
+ params = {'tag': self.test_data['tags'][0]}
+ images_list = self.client.list_images(params=params)['images']
+ # Validating properties of fetched images
+ self.assertNotEmpty(images_list)
+ for image in images_list:
+ msg = ("The image {image_name} does not have the expected tag "
+ "{expected_tag} among its tags: {observerd_tags}."
+ .format(image_name=image['name'],
+ expected_tag=self.test_data['tags'][0],
+ observerd_tags=image['tags']))
+ self.assertIn(self.test_data['tags'][0], image['tags'], msg)
+
+ @test.idempotent_id('eeadce49-04e0-43b7-aec7-52535d903e7a')
+ def test_list_images_param_sort(self):
+ params = {'sort': 'size:desc'}
+ self._list_sorted_by_image_size_and_assert(params, desc=True)
+
+ @test.idempotent_id('9faaa0c2-c3a5-43e1-8f61-61c54b409a49')
+ def test_list_images_param_sort_key_dir(self):
+ params = {'sort_key': 'size', 'sort_dir': 'desc'}
+ self._list_sorted_by_image_size_and_assert(params, desc=True)
+
@test.idempotent_id('622b925c-479f-4736-860d-adeaf13bc371')
def test_get_image_schema(self):
# Test to get image schema
@@ -267,3 +323,32 @@
schema = "images"
body = self.schemas_client.show_schema(schema)
self.assertEqual("images", body['name'])
+
+
+class ListSharedImagesTest(ListImagesTest):
+ """Here we test the listing of a shared image information"""
+
+ credentials = ['primary', 'alt']
+
+ @classmethod
+ def setup_clients(cls):
+ super(ListSharedImagesTest, cls).setup_clients()
+ cls.image_member_client = cls.os.image_member_client_v2
+ cls.alt_img_client = cls.os_alt.image_client_v2
+
+ @test.idempotent_id('3fa50be4-8e38-4c02-a8db-7811bb780122')
+ def test_list_images_param_member_status(self):
+ # Share one of the images created with the alt user
+ self.image_member_client.create_image_member(
+ image_id=self.test_data['id'],
+ member=self.alt_img_client.tenant_id)
+ # Update the info on the test data so it remains accurate
+ self.test_data['updated_at'] = self.client.show_image(
+ self.test_data['id'])['updated_at']
+ # As an image consumer you need to provide the member_status parameter
+ # along with the visibility=shared parameter in order for it to show
+ # results
+ params = {'member_status': 'pending', 'visibility': 'shared'}
+ fetched_images = self.alt_img_client.list_images(params)['images']
+ self.assertEqual(1, len(fetched_images))
+ self.assertEqual(self.test_data['id'], fetched_images[0]['id'])
diff --git a/tempest/api/volume/admin/test_volume_types.py b/tempest/api/volume/admin/test_volume_types.py
index eb6500c..3098cab 100644
--- a/tempest/api/volume/admin/test_volume_types.py
+++ b/tempest/api/volume/admin/test_volume_types.py
@@ -51,8 +51,7 @@
'size': CONF.volume.volume_size}
# Create volume
- volume = self.volumes_client.create_volume(**params)['volume']
- self.addCleanup(self.delete_volume, self.volumes_client, volume['id'])
+ volume = self.create_volume(**params)
self.assertEqual(volume_types[0]['name'], volume["volume_type"])
self.assertEqual(volume[self.name_field], vol_name,
"The created volume name is not equal "
diff --git a/tempest/api/volume/admin/v2/test_volume_type_access.py b/tempest/api/volume/admin/v2/test_volume_type_access.py
index 91ff5af..80dbf12 100644
--- a/tempest/api/volume/admin/v2/test_volume_type_access.py
+++ b/tempest/api/volume/admin/v2/test_volume_type_access.py
@@ -16,7 +16,6 @@
import operator
from tempest.api.volume import base
-from tempest.common import waiters
from tempest import config
from tempest.lib import exceptions as lib_exc
from tempest import test
@@ -52,13 +51,7 @@
project=self.volumes_client.tenant_id)
# Creating a volume from primary tenant
- volume = self.volumes_client.create_volume(
- volume_type=volume_type['id'],
- size=CONF.volume.volume_size)['volume']
- self.addCleanup(self.delete_volume, self.volumes_client, volume['id'])
- waiters.wait_for_volume_status(self.volumes_client, volume['id'],
- 'available')
-
+ volume = self.create_volume(volume_type=volume_type['id'])
# Validating the created volume is based on the volume type
self.assertEqual(volume_type['name'], volume['volume_type'])
diff --git a/tempest/api/volume/admin/v3/test_user_messages.py b/tempest/api/volume/admin/v3/test_user_messages.py
index 39a5dfa..257a434 100755
--- a/tempest/api/volume/admin/v3/test_user_messages.py
+++ b/tempest/api/volume/admin/v3/test_user_messages.py
@@ -15,9 +15,7 @@
from tempest.api.volume.v3 import base
from tempest.common.utils import data_utils
-from tempest.common import waiters
from tempest import config
-from tempest import exceptions
from tempest import test
CONF = config.CONF
@@ -47,21 +45,11 @@
'vendor_name': bad_vendor}
vol_type_name = data_utils.rand_name(
self.__class__.__name__ + '-volume-type')
- bogus_type = self.admin_volume_types_client.create_volume_type(
- name=vol_type_name,
- extra_specs=extra_specs)['volume_type']
- self.addCleanup(self.admin_volume_types_client.delete_volume_type,
- bogus_type['id'])
+ bogus_type = self.create_volume_type(
+ name=vol_type_name, extra_specs=extra_specs)
params = {'volume_type': bogus_type['id'],
'size': CONF.volume.volume_size}
- volume = self.volumes_client.create_volume(**params)['volume']
- self.addCleanup(self.delete_volume, self.volumes_client, volume['id'])
- try:
- waiters.wait_for_volume_status(self.volumes_client, volume['id'],
- 'error')
- except exceptions.VolumeBuildErrorException:
- # Error state is expected and desired
- pass
+ volume = self.create_volume(wait_until="error", **params)
messages = self.messages_client.list_messages()['messages']
message_id = None
for message in messages:
diff --git a/tempest/api/volume/base.py b/tempest/api/volume/base.py
index ba982ed..f32c84a 100644
--- a/tempest/api/volume/base.py
+++ b/tempest/api/volume/base.py
@@ -108,8 +108,11 @@
super(BaseVolumeTest, cls).resource_cleanup()
@classmethod
- def create_volume(cls, **kwargs):
- """Wrapper utility that returns a test volume."""
+ def create_volume(cls, wait_until='available', **kwargs):
+ """Wrapper utility that returns a test volume.
+
+ :param wait_until: wait till volume status.
+ """
if 'size' not in kwargs:
kwargs['size'] = CONF.volume.volume_size
@@ -126,8 +129,8 @@
volume = cls.volumes_client.create_volume(**kwargs)['volume']
cls.volumes.append(volume)
- waiters.wait_for_volume_status(cls.volumes_client,
- volume['id'], 'available')
+ waiters.wait_for_volume_status(cls.volumes_client, volume['id'],
+ wait_until)
return volume
@classmethod
@@ -154,6 +157,18 @@
client.delete_volume(volume_id)
client.wait_for_resource_deletion(volume_id)
+ def attach_volume(self, server_id, volume_id):
+ """Attachs a volume to a server"""
+ self.servers_client.attach_volume(
+ server_id, volumeId=volume_id,
+ device='/dev/%s' % CONF.compute.volume_device_name)
+ waiters.wait_for_volume_status(self.volumes_client,
+ volume_id, 'in-use')
+ self.addCleanup(waiters.wait_for_volume_status, self.volumes_client,
+ volume_id, 'available')
+ self.addCleanup(self.servers_client.detach_volume, server_id,
+ self.volume_origin['id'])
+
@classmethod
def clear_volumes(cls):
for volume in cls.volumes:
diff --git a/tempest/api/volume/test_volumes_snapshots.py b/tempest/api/volume/test_volumes_snapshots.py
index 3c05d3e..3c7a2c8 100644
--- a/tempest/api/volume/test_volumes_snapshots.py
+++ b/tempest/api/volume/test_volumes_snapshots.py
@@ -12,7 +12,6 @@
from tempest.api.volume import base
from tempest.common.utils import data_utils
-from tempest.common import waiters
from tempest import config
from tempest import test
@@ -46,21 +45,53 @@
# Create a snapshot when volume status is in-use
# Create a test instance
server = self.create_server(wait_until='ACTIVE')
- self.servers_client.attach_volume(
- server['id'], volumeId=self.volume_origin['id'],
- device='/dev/%s' % CONF.compute.volume_device_name)
- waiters.wait_for_volume_status(self.volumes_client,
- self.volume_origin['id'], 'in-use')
- self.addCleanup(waiters.wait_for_volume_status, self.volumes_client,
- self.volume_origin['id'], 'available')
- self.addCleanup(self.servers_client.detach_volume, server['id'],
- self.volume_origin['id'])
+ self.attach_volume(server['id'], self.volume_origin['id'])
+
# Snapshot a volume even if it's attached to an instance
snapshot = self.create_snapshot(self.volume_origin['id'],
force=True)
# Delete the snapshot
self.cleanup_snapshot(snapshot)
+ @test.idempotent_id('8567b54c-4455-446d-a1cf-651ddeaa3ff2')
+ @test.services('compute')
+ def test_snapshot_delete_with_volume_in_use(self):
+ # Create a test instance
+ server = self.create_server(wait_until='ACTIVE')
+ self.attach_volume(server['id'], self.volume_origin['id'])
+
+ # Snapshot a volume attached to an instance
+ snapshot1 = self.create_snapshot(self.volume_origin['id'], force=True)
+ snapshot2 = self.create_snapshot(self.volume_origin['id'], force=True)
+ snapshot3 = self.create_snapshot(self.volume_origin['id'], force=True)
+
+ # Delete the snapshots. Some snapshot implementations can take
+ # different paths according to order they are deleted.
+ self.cleanup_snapshot(snapshot1)
+ self.cleanup_snapshot(snapshot3)
+ self.cleanup_snapshot(snapshot2)
+
+ @test.idempotent_id('5210a1de-85a0-11e6-bb21-641c676a5d61')
+ @test.services('compute')
+ def test_snapshot_create_offline_delete_online(self):
+
+ # Create a snapshot while it is not attached
+ snapshot1 = self.create_snapshot(self.volume_origin['id'])
+
+ # Create a server and attach it
+ server = self.create_server(wait_until='ACTIVE')
+ self.attach_volume(server['id'], self.volume_origin['id'])
+
+ # Now that the volume is attached, create another snapshots
+ snapshot2 = self.create_snapshot(self.volume_origin['id'], force=True)
+ snapshot3 = self.create_snapshot(self.volume_origin['id'], force=True)
+
+ # Delete the snapshots. Some snapshot implementations can take
+ # different paths according to order they are deleted.
+ self.cleanup_snapshot(snapshot3)
+ self.cleanup_snapshot(snapshot1)
+ self.cleanup_snapshot(snapshot2)
+
@test.idempotent_id('2a8abbe4-d871-46db-b049-c41f5af8216e')
def test_snapshot_create_get_list_update_delete(self):
# Create a snapshot
diff --git a/tempest/api/volume/v3/base.py b/tempest/api/volume/v3/base.py
index e38f947..31fc1eb 100644
--- a/tempest/api/volume/v3/base.py
+++ b/tempest/api/volume/v3/base.py
@@ -52,7 +52,8 @@
self.request_microversion))
-class VolumesV3AdminTest(VolumesV3Test):
+class VolumesV3AdminTest(VolumesV3Test,
+ base.BaseVolumeAdminTest):
"""Base test case class for all v3 Volume Admin API tests."""
credentials = ['primary', 'admin']
diff --git a/tempest/common/waiters.py b/tempest/common/waiters.py
index 92bce5f..0cf8154 100644
--- a/tempest/common/waiters.py
+++ b/tempest/common/waiters.py
@@ -176,7 +176,7 @@
time.sleep(client.build_interval)
body = client.show_volume(volume_id)['volume']
volume_status = body['status']
- if volume_status == 'error':
+ if volume_status == 'error' and status != 'error':
raise exceptions.VolumeBuildErrorException(volume_id=volume_id)
if volume_status == 'error_restoring':
raise exceptions.VolumeRestoreErrorException(volume_id=volume_id)
diff --git a/tempest/lib/services/volume/v1/backups_client.py b/tempest/lib/services/volume/v1/backups_client.py
index 2728c67..8677913 100644
--- a/tempest/lib/services/volume/v1/backups_client.py
+++ b/tempest/lib/services/volume/v1/backups_client.py
@@ -26,8 +26,9 @@
def create_backup(self, **kwargs):
"""Creates a backup of volume.
- Available params: see http://developer.openstack.org/
- api-ref-blockstorage-v2.html#createBackup
+ For a full list of available parameters, please refer to the official
+ API reference:
+ http://developer.openstack.org/api-ref/block-storage/v2/#create-backup
"""
post_body = json.dumps({'backup': kwargs})
resp, body = self.post('backups', post_body)
@@ -38,8 +39,9 @@
def restore_backup(self, backup_id, **kwargs):
"""Restore volume from backup.
- Available params: see http://developer.openstack.org/
- api-ref-blockstorage-v2.html#restoreBackup
+ For a full list of available parameters, please refer to the official
+ API reference:
+ http://developer.openstack.org/api-ref/block-storage/v2/#restore-backup
"""
post_body = json.dumps({'restore': kwargs})
resp, body = self.post('backups/%s/restore' % (backup_id), post_body)
diff --git a/tempest/lib/services/volume/v1/qos_client.py b/tempest/lib/services/volume/v1/qos_client.py
index 65ae274..e247b7b 100644
--- a/tempest/lib/services/volume/v1/qos_client.py
+++ b/tempest/lib/services/volume/v1/qos_client.py
@@ -41,8 +41,9 @@
def create_qos(self, **kwargs):
"""Create a QoS Specification.
- Available params: see http://developer.openstack.org/
- api-ref-blockstorage-v2.html#createQoSSpec
+ For a full list of available parameters, please refer to the official
+ API reference:
+ http://developer.openstack.org/api-ref/block-storage/v2/#create-qos-specification
"""
post_body = json.dumps({'qos_specs': kwargs})
resp, body = self.post('qos-specs', post_body)
@@ -76,8 +77,9 @@
def set_qos_key(self, qos_id, **kwargs):
"""Set the specified keys/values of QoS specification.
- Available params: see http://developer.openstack.org/
- api-ref-blockstorage-v2.html#setQoSKey
+ For a full list of available parameters, please refer to the official
+ API reference:
+ http://developer.openstack.org/api-ref/block-storage/v2/#set-keys-in-qos-specification
"""
put_body = json.dumps({"qos_specs": kwargs})
resp, body = self.put('qos-specs/%s' % qos_id, put_body)
diff --git a/tempest/lib/services/volume/v1/snapshots_client.py b/tempest/lib/services/volume/v1/snapshots_client.py
index 1881078..2cf1555 100644
--- a/tempest/lib/services/volume/v1/snapshots_client.py
+++ b/tempest/lib/services/volume/v1/snapshots_client.py
@@ -25,8 +25,9 @@
def list_snapshots(self, detail=False, **params):
"""List all the snapshot.
- Available params: see http://developer.openstack.org/
- api-ref-blockstorage-v1.html#listSnapshots
+ For a full list of available parameters, please refer to the official
+ API reference:
+ http://developer.openstack.org/api-ref-blockstorage-v1.html#listSnapshots
"""
url = 'snapshots'
if detail:
@@ -42,8 +43,9 @@
def show_snapshot(self, snapshot_id):
"""Returns the details of a single snapshot.
- Available params: see http://developer.openstack.org/
- api-ref-blockstorage-v1.html#showSnapshot
+ For a full list of available parameters, please refer to the official
+ API reference:
+ http://developer.openstack.org/api-ref-blockstorage-v1.html#showSnapshot
"""
url = "snapshots/%s" % snapshot_id
resp, body = self.get(url)
@@ -54,8 +56,9 @@
def create_snapshot(self, **kwargs):
"""Creates a new snapshot.
- Available params: see http://developer.openstack.org/
- api-ref-blockstorage-v1.html#createSnapshot
+ For a full list of available parameters, please refer to the official
+ API reference:
+ http://developer.openstack.org/api-ref-blockstorage-v1.html#createSnapshot
"""
post_body = json.dumps({'snapshot': kwargs})
resp, body = self.post('snapshots', post_body)
@@ -66,8 +69,9 @@
def delete_snapshot(self, snapshot_id):
"""Delete Snapshot.
- Available params: see http://developer.openstack.org/
- api-ref-blockstorage-v1.html#deleteSnapshot
+ For a full list of available parameters, please refer to the official
+ API reference:
+ http://developer.openstack.org/api-ref-blockstorage-v1.html#deleteSnapshot
"""
resp, body = self.delete("snapshots/%s" % snapshot_id)
self.expected_success(202, resp.status)
@@ -117,9 +121,9 @@
def update_snapshot(self, snapshot_id, **kwargs):
"""Updates a snapshot.
- Available params: see http://developer.openstack.org/
- api-ref-blockstorage-v1.html#
- updateSnapshotMetadata
+ For a full list of available parameters, please refer to the official
+ API reference:
+ http://developer.openstack.org/api-ref-blockstorage-v1.html#updateSnapshotMetadata
"""
put_body = json.dumps({'snapshot': kwargs})
resp, body = self.put('snapshots/%s' % snapshot_id, put_body)
@@ -130,9 +134,9 @@
def show_snapshot_metadata(self, snapshot_id):
"""Get metadata of the snapshot.
- Available params: see http://developer.openstack.org/
- api-ref-blockstorage-v1.html#
- showSnapshotMetadata
+ For a full list of available parameters, please refer to the official
+ API reference:
+ http://developer.openstack.org/api-ref-blockstorage-v1.html#showSnapshotMetadata
"""
url = "snapshots/%s/metadata" % snapshot_id
resp, body = self.get(url)
@@ -143,9 +147,9 @@
def update_snapshot_metadata(self, snapshot_id, **kwargs):
"""Update metadata for the snapshot.
- Available params: see http://developer.openstack.org/
- api-ref-blockstorage-v1.html#
- updateSnapshotMetadata
+ For a full list of available parameters, please refer to the official
+ API reference:
+ http://developer.openstack.org/api-ref-blockstorage-v1.html#updateSnapshotMetadata
"""
put_body = json.dumps(kwargs)
url = "snapshots/%s/metadata" % snapshot_id
diff --git a/tempest/lib/services/volume/v1/types_client.py b/tempest/lib/services/volume/v1/types_client.py
index dce728d..2b696e5 100644
--- a/tempest/lib/services/volume/v1/types_client.py
+++ b/tempest/lib/services/volume/v1/types_client.py
@@ -38,8 +38,9 @@
def list_volume_types(self, **params):
"""List all the volume_types created.
- Available params: see http://developer.openstack.org/
- api-ref-blockstorage-v1.html#listVolumeTypes
+ For a full list of available parameters, please refer to the official
+ API reference:
+ http://developer.openstack.org/api-ref-blockstorage-v1.html#listVolumeTypes
"""
url = 'types'
if params:
@@ -53,8 +54,9 @@
def show_volume_type(self, volume_type_id):
"""Returns the details of a single volume_type.
- Available params: see http://developer.openstack.org/
- api-ref-blockstorage-v1.html#showVolumeType
+ For a full list of available parameters, please refer to the official
+ API reference:
+ http://developer.openstack.org/api-ref-blockstorage-v1.html#showVolumeType
"""
url = "types/%s" % volume_type_id
resp, body = self.get(url)
@@ -65,8 +67,9 @@
def create_volume_type(self, **kwargs):
"""Create volume type.
- Available params: see http://developer.openstack.org/
- api-ref-blockstorage-v1.html#createVolumeType
+ For a full list of available parameters, please refer to the official
+ API reference:
+ http://developer.openstack.org/api-ref-blockstorage-v1.html#createVolumeType
"""
post_body = json.dumps({'volume_type': kwargs})
resp, body = self.post('types', post_body)
@@ -77,8 +80,9 @@
def delete_volume_type(self, volume_type_id):
"""Deletes the Specified Volume_type.
- Available params: see http://developer.openstack.org/
- api-ref-blockstorage-v1.html#deleteVolumeType
+ For a full list of available parameters, please refer to the official
+ API reference:
+ http://developer.openstack.org/api-ref-blockstorage-v1.html#deleteVolumeType
"""
resp, body = self.delete("types/%s" % volume_type_id)
self.expected_success(202, resp.status)
@@ -131,8 +135,9 @@
def update_volume_type(self, volume_type_id, **kwargs):
"""Updates volume type name, description, and/or is_public.
- Available params: see http://developer.openstack.org/
- api-ref-blockstorage-v2.html#updateVolumeType
+ For a full list of available parameters, please refer to the official
+ API reference:
+ http://developer.openstack.org/api-ref-blockstorage-v2.html#updateVolumeType
"""
put_body = json.dumps({'volume_type': kwargs})
resp, body = self.put('types/%s' % volume_type_id, put_body)
@@ -148,9 +153,9 @@
extra_spec_name: Name of the extra spec to be updated.
extra_spec: A dictionary of with key as extra_spec_name and the
updated value.
- Available params: see http://developer.openstack.org/
- api-ref-blockstorage-v2.html#
- updateVolumeTypeExtraSpecs
+ For a full list of available parameters, please refer to the official
+ API reference:
+ http://developer.openstack.org/api-ref-blockstorage-v2.html#updateVolumeTypeExtraSpecs
"""
url = "types/%s/extra_specs/%s" % (volume_type_id, extra_spec_name)
put_body = json.dumps(extra_specs)
diff --git a/tempest/lib/services/volume/v1/volumes_client.py b/tempest/lib/services/volume/v1/volumes_client.py
index cc98c91..242befc 100644
--- a/tempest/lib/services/volume/v1/volumes_client.py
+++ b/tempest/lib/services/volume/v1/volumes_client.py
@@ -61,8 +61,9 @@
def create_volume(self, **kwargs):
"""Creates a new Volume.
- Available params: see http://developer.openstack.org/
- api-ref-blockstorage-v2.html#createVolume
+ For a full list of available parameters, please refer to the official
+ API reference:
+ http://developer.openstack.org/api-ref-blockstorage-v2.html#createVolume
"""
post_body = json.dumps({'volume': kwargs})
resp, body = self.post('volumes', post_body)
@@ -73,8 +74,9 @@
def update_volume(self, volume_id, **kwargs):
"""Updates the Specified Volume.
- Available params: see http://developer.openstack.org/
- api-ref-blockstorage-v2.html#updateVolume
+ For a full list of available parameters, please refer to the official
+ API reference:
+ http://developer.openstack.org/api-ref-blockstorage-v2.html#updateVolume
"""
put_body = json.dumps({'volume': kwargs})
resp, body = self.put('volumes/%s' % volume_id, put_body)
@@ -100,8 +102,9 @@
def attach_volume(self, volume_id, **kwargs):
"""Attaches a volume to a given instance on a given mountpoint.
- Available params: see http://developer.openstack.org/
- api-ref-blockstorage-v2.html#attachVolume
+ For a full list of available parameters, please refer to the official
+ API reference:
+ http://developer.openstack.org/api-ref-blockstorage-v2.html#attachVolume
"""
post_body = json.dumps({'os-attach': kwargs})
url = 'volumes/%s/action' % (volume_id)
@@ -156,8 +159,9 @@
def extend_volume(self, volume_id, **kwargs):
"""Extend a volume.
- Available params: see http://developer.openstack.org/
- api-ref-blockstorage-v2.html#extendVolume
+ For a full list of available parameters, please refer to the official
+ API reference:
+ http://developer.openstack.org/api-ref-blockstorage-v2.html#extendVolume
"""
post_body = json.dumps({'os-extend': kwargs})
url = 'volumes/%s/action' % (volume_id)
@@ -168,8 +172,9 @@
def reset_volume_status(self, volume_id, **kwargs):
"""Reset the Specified Volume's Status.
- Available params: see http://developer.openstack.org/
- api-ref-blockstorage-v2.html#resetVolume
+ For a full list of available parameters, please refer to the official
+ API reference:
+ http://developer.openstack.org/api-ref-blockstorage-v2.html#resetVolume
"""
post_body = json.dumps({'os-reset_status': kwargs})
resp, body = self.post('volumes/%s/action' % volume_id, post_body)
@@ -179,8 +184,9 @@
def create_volume_transfer(self, **kwargs):
"""Create a volume transfer.
- Available params: see http://developer.openstack.org/
- api-ref-blockstorage-v2.html#createVolumeTransfer
+ For a full list of available parameters, please refer to the official
+ API reference:
+ http://developer.openstack.org/api-ref-blockstorage-v2.html#createVolumeTransfer
"""
post_body = json.dumps({'transfer': kwargs})
resp, body = self.post('os-volume-transfer', post_body)
@@ -199,8 +205,9 @@
def list_volume_transfers(self, **params):
"""List all the volume transfers created.
- Available params: see http://developer.openstack.org/
- api-ref-blockstorage-v2.html#listVolumeTransfer
+ For a full list of available parameters, please refer to the official
+ API reference:
+ http://developer.openstack.org/api-ref-blockstorage-v2.html#listVolumeTransfer
"""
url = 'os-volume-transfer'
if params:
@@ -219,8 +226,9 @@
def accept_volume_transfer(self, transfer_id, **kwargs):
"""Accept a volume transfer.
- Available params: see http://developer.openstack.org/
- api-ref-blockstorage-v2.html#acceptVolumeTransfer
+ For a full list of available parameters, please refer to the official
+ API reference:
+ http://developer.openstack.org/api-ref-blockstorage-v2.html#acceptVolumeTransfer
"""
url = 'os-volume-transfer/%s/accept' % transfer_id
post_body = json.dumps({'accept': kwargs})
diff --git a/tempest/lib/services/volume/v2/backups_client.py b/tempest/lib/services/volume/v2/backups_client.py
index 61f865d..ab5eefd 100644
--- a/tempest/lib/services/volume/v2/backups_client.py
+++ b/tempest/lib/services/volume/v2/backups_client.py
@@ -26,8 +26,9 @@
def create_backup(self, **kwargs):
"""Creates a backup of volume.
- Available params: see http://developer.openstack.org/
- api-ref-blockstorage-v2.html#createBackup
+ For a full list of available parameters, please refer to the official
+ API reference:
+ http://developer.openstack.org/api-ref-blockstorage-v2.html#createBackup
"""
post_body = json.dumps({'backup': kwargs})
resp, body = self.post('backups', post_body)
@@ -38,8 +39,9 @@
def restore_backup(self, backup_id, **kwargs):
"""Restore volume from backup.
- Available params: see http://developer.openstack.org/
- api-ref-blockstorage-v2.html#restoreBackup
+ For a full list of available parameters, please refer to the official
+ API reference:
+ http://developer.openstack.org/api-ref-blockstorage-v2.html#restoreBackup
"""
post_body = json.dumps({'restore': kwargs})
resp, body = self.post('backups/%s/restore' % (backup_id), post_body)
diff --git a/tempest/lib/services/volume/v2/snapshots_client.py b/tempest/lib/services/volume/v2/snapshots_client.py
index c84e557..dd0f407 100644
--- a/tempest/lib/services/volume/v2/snapshots_client.py
+++ b/tempest/lib/services/volume/v2/snapshots_client.py
@@ -25,8 +25,9 @@
def list_snapshots(self, detail=False, **params):
"""List all the snapshot.
- Available params: see http://developer.openstack.org/
- api-ref-blockstorage-v2.html#listSnapshots
+ For a full list of available parameters, please refer to the official
+ API reference:
+ http://developer.openstack.org/api-ref-blockstorage-v2.html#listSnapshots
"""
url = 'snapshots'
if detail:
@@ -42,8 +43,9 @@
def show_snapshot(self, snapshot_id):
"""Returns the details of a single snapshot.
- Available params: see http://developer.openstack.org/
- api-ref-blockstorage-v2.html#showSnapshot
+ For a full list of available parameters, please refer to the official
+ API reference:
+ http://developer.openstack.org/api-ref-blockstorage-v2.html#showSnapshot
"""
url = "snapshots/%s" % snapshot_id
resp, body = self.get(url)
@@ -54,8 +56,9 @@
def create_snapshot(self, **kwargs):
"""Creates a new snapshot.
- Available params: see http://developer.openstack.org/
- api-ref-blockstorage-v2.html#createSnapshot
+ For a full list of available parameters, please refer to the official
+ API reference:
+ http://developer.openstack.org/api-ref-blockstorage-v2.html#createSnapshot
"""
post_body = json.dumps({'snapshot': kwargs})
resp, body = self.post('snapshots', post_body)
@@ -66,8 +69,9 @@
def update_snapshot(self, snapshot_id, **kwargs):
"""Updates a snapshot.
- Available params: see http://developer.openstack.org/
- api-ref-blockstorage-v2.html#updateSnapshot
+ For a full list of available parameters, please refer to the official
+ API reference:
+ http://developer.openstack.org/api-ref-blockstorage-v2.html#updateSnapshot
"""
put_body = json.dumps({'snapshot': kwargs})
resp, body = self.put('snapshots/%s' % snapshot_id, put_body)
@@ -78,8 +82,9 @@
def delete_snapshot(self, snapshot_id):
"""Delete Snapshot.
- Available params: see http://developer.openstack.org/
- api-ref-blockstorage-v2.html#deleteSnapshot
+ For a full list of available parameters, please refer to the official
+ API reference:
+ http://developer.openstack.org/api-ref-blockstorage-v2.html#deleteSnapshot
"""
resp, body = self.delete("snapshots/%s" % snapshot_id)
self.expected_success(202, resp.status)
@@ -129,9 +134,9 @@
def show_snapshot_metadata(self, snapshot_id):
"""Get metadata of the snapshot.
- Available params: see http://developer.openstack.org/
- api-ref-blockstorage-v2.html#
- showSnapshotMetadata
+ For a full list of available parameters, please refer to the official
+ API reference:
+ http://developer.openstack.org/api-ref-blockstorage-v2.html#showSnapshotMetadata
"""
url = "snapshots/%s/metadata" % snapshot_id
resp, body = self.get(url)
@@ -142,9 +147,9 @@
def update_snapshot_metadata(self, snapshot_id, **kwargs):
"""Update metadata for the snapshot.
- Available params: see http://developer.openstack.org/
- api-ref-blockstorage-v2.html#
- updateSnapshotMetadata
+ For a full list of available parameters, please refer to the official
+ API reference:
+ http://developer.openstack.org/api-ref-blockstorage-v2.html#updateSnapshotMetadata
"""
put_body = json.dumps(kwargs)
url = "snapshots/%s/metadata" % snapshot_id
diff --git a/tempest/lib/services/volume/v2/types_client.py b/tempest/lib/services/volume/v2/types_client.py
index d399e99..7a0d6d0 100644
--- a/tempest/lib/services/volume/v2/types_client.py
+++ b/tempest/lib/services/volume/v2/types_client.py
@@ -39,8 +39,9 @@
def list_volume_types(self, **params):
"""List all the volume_types created.
- Available params: see http://developer.openstack.org/
- api-ref-blockstorage-v2.html#showVolumeTypes
+ For a full list of available parameters, please refer to the official
+ API reference:
+ http://developer.openstack.org/api-ref-blockstorage-v2.html#showVolumeTypes
"""
url = 'types'
if params:
@@ -54,8 +55,9 @@
def show_volume_type(self, volume_type_id):
"""Returns the details of a single volume_type.
- Available params: see http://developer.openstack.org/
- api-ref-blockstorage-v2.html#showVolumeType
+ For a full list of available parameters, please refer to the official
+ API reference:
+ http://developer.openstack.org/api-ref-blockstorage-v2.html#showVolumeType
"""
url = "types/%s" % volume_type_id
resp, body = self.get(url)
@@ -66,8 +68,9 @@
def create_volume_type(self, **kwargs):
"""Create volume type.
- Available params: see http://developer.openstack.org/
- api-ref-blockstorage-v2.html#createVolumeType
+ For a full list of available parameters, please refer to the official
+ API reference:
+ http://developer.openstack.org/api-ref-blockstorage-v2.html#createVolumeType
"""
post_body = json.dumps({'volume_type': kwargs})
resp, body = self.post('types', post_body)
@@ -78,8 +81,9 @@
def delete_volume_type(self, volume_type_id):
"""Deletes the Specified Volume_type.
- Available params: see http://developer.openstack.org/
- api-ref-blockstorage-v2.html#deleteVolumeType
+ For a full list of available parameters, please refer to the official
+ API reference:
+ http://developer.openstack.org/api-ref-blockstorage-v2.html#deleteVolumeType
"""
resp, body = self.delete("types/%s" % volume_type_id)
self.expected_success(202, resp.status)
@@ -132,8 +136,9 @@
def update_volume_type(self, volume_type_id, **kwargs):
"""Updates volume type name, description, and/or is_public.
- Available params: see http://developer.openstack.org/
- api-ref-blockstorage-v2.html#updateVolumeType
+ For a full list of available parameters, please refer to the official
+ API reference:
+ http://developer.openstack.org/api-ref-blockstorage-v2.html#updateVolumeType
"""
put_body = json.dumps({'volume_type': kwargs})
resp, body = self.put('types/%s' % volume_type_id, put_body)
@@ -149,9 +154,9 @@
extra_spec_name: Name of the extra spec to be updated.
extra_spec: A dictionary of with key as extra_spec_name and the
updated value.
- Available params: see http://developer.openstack.org/
- api-ref-blockstorage-v2.html#
- updateVolumeTypeExtraSpecs
+ For a full list of available parameters, please refer to the official
+ API reference:
+ http://developer.openstack.org/api-ref-blockstorage-v2.html#updateVolumeTypeExtraSpecs
"""
url = "types/%s/extra_specs/%s" % (volume_type_id, extra_spec_name)
put_body = json.dumps(extra_specs)
@@ -163,9 +168,9 @@
def add_type_access(self, volume_type_id, **kwargs):
"""Adds volume type access for the given project.
- Available params: see http://developer.openstack.org/
- api-ref-blockstorage-v2.html
- #createVolumeTypeAccessExt
+ For a full list of available parameters, please refer to the official
+ API reference:
+ http://developer.openstack.org/api-ref-blockstorage-v2.html#createVolumeTypeAccessExt
"""
post_body = json.dumps({'addProjectAccess': kwargs})
url = 'types/%s/action' % volume_type_id
@@ -176,9 +181,9 @@
def remove_type_access(self, volume_type_id, **kwargs):
"""Removes volume type access for the given project.
- Available params: see http://developer.openstack.org/
- api-ref-blockstorage-v2.html
- #removeVolumeTypeAccessExt
+ For a full list of available parameters, please refer to the official
+ API reference:
+ http://developer.openstack.org/api-ref-blockstorage-v2.html#removeVolumeTypeAccessExt
"""
post_body = json.dumps({'removeProjectAccess': kwargs})
url = 'types/%s/action' % volume_type_id
@@ -189,9 +194,9 @@
def list_type_access(self, volume_type_id):
"""Print access information about the given volume type.
- Available params: see http://developer.openstack.org/
- api-ref-blockstorage-v2.html#
- listVolumeTypeAccessExt
+ For a full list of available parameters, please refer to the official
+ API reference:
+ http://developer.openstack.org/api-ref-blockstorage-v2.html#listVolumeTypeAccessExt
"""
url = 'types/%s/os-volume-type-access' % volume_type_id
resp, body = self.get(url)
diff --git a/tempest/lib/services/volume/v2/volumes_client.py b/tempest/lib/services/volume/v2/volumes_client.py
index b1930e1..1fb5727 100644
--- a/tempest/lib/services/volume/v2/volumes_client.py
+++ b/tempest/lib/services/volume/v2/volumes_client.py
@@ -62,8 +62,9 @@
def create_volume(self, **kwargs):
"""Creates a new Volume.
- Available params: see http://developer.openstack.org/
- api-ref-blockstorage-v2.html#createVolume
+ For a full list of available parameters, please refer to the official
+ API reference:
+ http://developer.openstack.org/api-ref-blockstorage-v2.html#createVolume
"""
post_body = json.dumps({'volume': kwargs})
resp, body = self.post('volumes', post_body)
@@ -74,8 +75,9 @@
def update_volume(self, volume_id, **kwargs):
"""Updates the Specified Volume.
- Available params: see http://developer.openstack.org/
- api-ref-blockstorage-v2.html#updateVolume
+ For a full list of available parameters, please refer to the official
+ API reference:
+ http://developer.openstack.org/api-ref-blockstorage-v2.html#updateVolume
"""
put_body = json.dumps({'volume': kwargs})
resp, body = self.put('volumes/%s' % volume_id, put_body)
@@ -101,8 +103,9 @@
def attach_volume(self, volume_id, **kwargs):
"""Attaches a volume to a given instance on a given mountpoint.
- Available params: see http://developer.openstack.org/
- api-ref-blockstorage-v2.html#attachVolume
+ For a full list of available parameters, please refer to the official
+ API reference:
+ http://developer.openstack.org/api-ref-blockstorage-v2.html#attachVolume
"""
post_body = json.dumps({'os-attach': kwargs})
url = 'volumes/%s/action' % (volume_id)
@@ -157,8 +160,9 @@
def extend_volume(self, volume_id, **kwargs):
"""Extend a volume.
- Available params: see http://developer.openstack.org/
- api-ref-blockstorage-v2.html#extendVolume
+ For a full list of available parameters, please refer to the official
+ API reference:
+ http://developer.openstack.org/api-ref-blockstorage-v2.html#extendVolume
"""
post_body = json.dumps({'os-extend': kwargs})
url = 'volumes/%s/action' % (volume_id)
@@ -169,8 +173,9 @@
def reset_volume_status(self, volume_id, **kwargs):
"""Reset the Specified Volume's Status.
- Available params: see http://developer.openstack.org/
- api-ref-blockstorage-v2.html#resetVolume
+ For a full list of available parameters, please refer to the official
+ API reference:
+ http://developer.openstack.org/api-ref-blockstorage-v2.html#resetVolume
"""
post_body = json.dumps({'os-reset_status': kwargs})
resp, body = self.post('volumes/%s/action' % volume_id, post_body)
@@ -180,8 +185,9 @@
def create_volume_transfer(self, **kwargs):
"""Create a volume transfer.
- Available params: see http://developer.openstack.org/
- api-ref-blockstorage-v2.html#createVolumeTransfer
+ For a full list of available parameters, please refer to the official
+ API reference:
+ http://developer.openstack.org/api-ref-blockstorage-v2.html#createVolumeTransfer
"""
post_body = json.dumps({'transfer': kwargs})
resp, body = self.post('os-volume-transfer', post_body)
@@ -200,8 +206,9 @@
def list_volume_transfers(self, **params):
"""List all the volume transfers created.
- Available params: see http://developer.openstack.org/
- api-ref-blockstorage-v2.html#listVolumeTransfer
+ For a full list of available parameters, please refer to the official
+ API reference:
+ http://developer.openstack.org/api-ref-blockstorage-v2.html#listVolumeTransfer
"""
url = 'os-volume-transfer'
if params:
@@ -220,8 +227,9 @@
def accept_volume_transfer(self, transfer_id, **kwargs):
"""Accept a volume transfer.
- Available params: see http://developer.openstack.org/
- api-ref-blockstorage-v2.html#acceptVolumeTransfer
+ For a full list of available parameters, please refer to the official
+ API reference:
+ http://developer.openstack.org/api-ref-blockstorage-v2.html#acceptVolumeTransfer
"""
url = 'os-volume-transfer/%s/accept' % transfer_id
post_body = json.dumps({'accept': kwargs})
@@ -296,9 +304,9 @@
def update_volume_image_metadata(self, volume_id, **kwargs):
"""Update image metadata for the volume.
- Available params: see http://developer.openstack.org/
- api-ref-blockstorage-v2.html
- #setVolumeimagemetadata
+ For a full list of available parameters, please refer to the official
+ API reference:
+ http://developer.openstack.org/api-ref-blockstorage-v2.html#setVolumeimagemetadata
"""
post_body = json.dumps({'os-set_image_metadata': {'metadata': kwargs}})
url = "volumes/%s/action" % (volume_id)
@@ -329,9 +337,9 @@
def show_backend_capabilities(self, host):
"""Shows capabilities for a storage back end.
- Output params: see http://developer.openstack.org/
- api-ref-blockstorage-v2.html
- #showBackendCapabilities
+ For a full list of available parameters, please refer to the official
+ API reference:
+ http://developer.openstack.org/api-ref-blockstorage-v2.html#showBackendCapabilities
"""
url = 'capabilities/%s' % host
resp, body = self.get(url)