Merge "Refactoring skip conditions process"
diff --git a/manila_tempest_tests/config.py b/manila_tempest_tests/config.py
index e0e8ea3..042be5a 100644
--- a/manila_tempest_tests/config.py
+++ b/manila_tempest_tests/config.py
@@ -30,7 +30,7 @@
help="The minimum api microversion is configured to be the "
"value of the minimum microversion supported by Manila."),
cfg.StrOpt("max_api_microversion",
- default="2.51",
+ default="2.53",
help="The maximum api microversion is configured to be the "
"value of the latest microversion supported by Manila."),
cfg.StrOpt("region",
diff --git a/manila_tempest_tests/services/share/json/shares_client.py b/manila_tempest_tests/services/share/json/shares_client.py
index 3481151..b2eabb4 100644
--- a/manila_tempest_tests/services/share/json/shares_client.py
+++ b/manila_tempest_tests/services/share/json/shares_client.py
@@ -467,9 +467,9 @@
metadata = {}
post_body = {"metadata": metadata}
body = json.dumps(post_body)
- if method is "post":
+ if method == "post":
resp, metadata = self.post(uri, body)
- if method is "put":
+ if method == "put":
resp, metadata = self.put(uri, body)
self.expected_success(200, resp.status)
return self._parse_resp(metadata)
diff --git a/manila_tempest_tests/services/share/v2/json/shares_client.py b/manila_tempest_tests/services/share/v2/json/shares_client.py
index 3c1f5a4..d8b7ed4 100644
--- a/manila_tempest_tests/services/share/v2/json/shares_client.py
+++ b/manila_tempest_tests/services/share/v2/json/shares_client.py
@@ -869,7 +869,6 @@
self.expected_success(200, resp.status)
return body
-
###############
def list_availability_zones(self, url='availability-zones',
@@ -1033,8 +1032,9 @@
snapshots=None, gigabytes=None, snapshot_gigabytes=None,
share_networks=None,
share_groups=None, share_group_snapshots=None,
- force=True, share_type=None,
- url=None, version=LATEST_MICROVERSION):
+ force=True, share_type=None, share_replicas=None,
+ replica_gigabytes=None, url=None,
+ version=LATEST_MICROVERSION):
if url is None:
url = self._get_quotas_url(version)
url += '/%s' % tenant_id
@@ -1057,6 +1057,10 @@
put_body["share_groups"] = share_groups
if share_group_snapshots is not None:
put_body["share_group_snapshots"] = share_group_snapshots
+ if share_replicas is not None:
+ put_body["share_replicas"] = share_replicas
+ if replica_gigabytes is not None:
+ put_body["replica_gigabytes"] = replica_gigabytes
put_body = json.dumps({"quota_set": put_body})
resp, body = self.put(url, put_body, version=version)
diff --git a/manila_tempest_tests/tests/api/admin/test_export_locations_negative.py b/manila_tempest_tests/tests/api/admin/test_export_locations_negative.py
index fe211ff..ef4f80b 100644
--- a/manila_tempest_tests/tests/api/admin/test_export_locations_negative.py
+++ b/manila_tempest_tests/tests/api/admin/test_export_locations_negative.py
@@ -33,8 +33,12 @@
@classmethod
def resource_setup(cls):
super(ExportLocationsNegativeTest, cls).resource_setup()
+ # admin_client and different_project_client pertain to isolated
+ # projects, admin_member_client is a regular user in admin's project
cls.admin_client = cls.admin_shares_v2_client
- cls.member_client = cls.shares_v2_client
+ cls.admin_member_client = (
+ cls.admin_project_member_client.shares_v2_client)
+ cls.different_project_client = cls.shares_v2_client
# create share type
cls.share_type = cls._create_share_type()
cls.share_type_id = cls.share_type['id']
@@ -65,26 +69,43 @@
)
@tc.attr(base.TAG_NEGATIVE, base.TAG_API_WITH_BACKEND)
- def test_list_share_instance_export_locations_by_member(self):
+ def test_list_share_instance_export_locations_as_member(self):
for share_instance in self.share_instances:
self.assertRaises(
lib_exc.Forbidden,
- self.member_client.list_share_instance_export_locations,
- "fake-inexistent-share-instance-id",
- )
+ self.admin_member_client.list_share_instance_export_locations,
+ share_instance['id'])
@tc.attr(base.TAG_NEGATIVE, base.TAG_API_WITH_BACKEND)
- def test_get_share_instance_export_location_by_member(self):
+ def test_get_share_instance_export_locations_as_member(self):
for share_instance in self.share_instances:
export_locations = (
self.admin_client.list_share_instance_export_locations(
share_instance['id']))
for el in export_locations:
- self.assertRaises(
- lib_exc.Forbidden,
- self.member_client.get_share_instance_export_location,
- share_instance['id'], el['id'],
- )
+ self.assertRaises(lib_exc.Forbidden,
+ (self.admin_member_client.
+ get_share_instance_export_location),
+ share_instance['id'], el['id'])
+
+ @tc.attr(base.TAG_NEGATIVE, base.TAG_API_WITH_BACKEND)
+ def test_list_share_export_locations_by_different_project_user(self):
+ self.assertRaises(
+ lib_exc.Forbidden,
+ self.different_project_client.list_share_export_locations,
+ self.share['id'])
+
+ @tc.attr(base.TAG_NEGATIVE, base.TAG_API_WITH_BACKEND)
+ def test_get_share_export_location_by_different_project_user(self):
+ export_locations = self.admin_client.list_share_export_locations(
+ self.share['id'])
+
+ for export_location in export_locations:
+ self.assertRaises(
+ lib_exc.Forbidden,
+ self.different_project_client.get_share_export_location,
+ self.share['id'],
+ export_location['id'])
class ExportLocationsAPIOnlyNegativeTest(base.BaseSharesAdminTest):
diff --git a/manila_tempest_tests/tests/api/admin/test_quotas.py b/manila_tempest_tests/tests/api/admin/test_quotas.py
index ab0d665..215b25d 100644
--- a/manila_tempest_tests/tests/api/admin/test_quotas.py
+++ b/manila_tempest_tests/tests/api/admin/test_quotas.py
@@ -26,6 +26,8 @@
CONF = config.CONF
PRE_SHARE_GROUPS_MICROVERSION = "2.39"
SHARE_GROUPS_MICROVERSION = "2.40"
+PRE_SHARE_REPLICA_QUOTAS_MICROVERSION = "2.52"
+SHARE_REPLICA_QUOTAS_MICROVERSION = "2.53"
@ddt.ddt
@@ -54,6 +56,9 @@
if utils.is_microversion_supported(SHARE_GROUPS_MICROVERSION):
self.assertGreater(int(quotas["share_groups"]), -2)
self.assertGreater(int(quotas["share_group_snapshots"]), -2)
+ if utils.share_replica_quotas_are_supported():
+ self.assertGreater(int(quotas["share_replicas"]), -2)
+ self.assertGreater(int(quotas["replica_gigabytes"]), -2)
@tc.attr(base.TAG_POSITIVE, base.TAG_API)
def test_show_quotas(self):
@@ -66,6 +71,9 @@
if utils.is_microversion_supported(SHARE_GROUPS_MICROVERSION):
self.assertGreater(int(quotas["share_groups"]), -2)
self.assertGreater(int(quotas["share_group_snapshots"]), -2)
+ if utils.share_replica_quotas_are_supported():
+ self.assertGreater(int(quotas["share_replicas"]), -2)
+ self.assertGreater(int(quotas["replica_gigabytes"]), -2)
@tc.attr(base.TAG_POSITIVE, base.TAG_API)
def test_show_quotas_for_user(self):
@@ -79,6 +87,9 @@
if utils.is_microversion_supported(SHARE_GROUPS_MICROVERSION):
self.assertGreater(int(quotas["share_groups"]), -2)
self.assertGreater(int(quotas["share_group_snapshots"]), -2)
+ if utils.share_replica_quotas_are_supported():
+ self.assertGreater(int(quotas["share_replicas"]), -2)
+ self.assertGreater(int(quotas["replica_gigabytes"]), -2)
@tc.attr(base.TAG_POSITIVE, base.TAG_API)
@base.skip_if_microversion_not_supported(PRE_SHARE_GROUPS_MICROVERSION)
@@ -99,6 +110,17 @@
for key in ('share_groups', 'share_group_snapshots'):
self.assertNotIn(key, quotas)
+ @tc.attr(base.TAG_POSITIVE, base.TAG_API)
+ @base.skip_if_microversion_not_supported(
+ PRE_SHARE_REPLICA_QUOTAS_MICROVERSION)
+ def test_show_replica_quotas_for_user_using_too_old_microversion(self):
+ quotas = self.shares_v2_client.show_quotas(
+ self.tenant_id, self.user_id,
+ version=PRE_SHARE_REPLICA_QUOTAS_MICROVERSION)
+
+ for key in('share_replicas', 'replica_gigabytes'):
+ self.assertNotIn(key, quotas)
+
@ddt.data(
('id', True),
('name', False),
@@ -107,6 +129,10 @@
@tc.attr(base.TAG_POSITIVE, base.TAG_API)
@base.skip_if_microversion_lt("2.39")
def test_show_share_type_quotas(self, share_type_key, is_st_public):
+ # Check if the used microversion supports 'share_replica' and
+ # 'replica_gigabytes' quotas
+ replica_quotas_supported = utils.share_replica_quotas_are_supported()
+
# Create share type
share_type = self.create_share_type(
data_utils.rand_name("tempest-manila"),
@@ -117,6 +143,12 @@
if 'share_type' in share_type:
share_type = share_type['share_type']
+ keys = ['shares', 'gigabytes', 'snapshots', 'snapshot_gigabytes']
+
+ if replica_quotas_supported:
+ keys.append('share_replicas')
+ keys.append('replica_gigabytes')
+
# Get current project quotas
p_quotas = self.shares_v2_client.show_quotas(self.tenant_id)
@@ -125,7 +157,7 @@
self.tenant_id, share_type=share_type[share_type_key])
# Share type quotas have values equal to project's
- for key in ('shares', 'gigabytes', 'snapshots', 'snapshot_gigabytes'):
+ for key in keys:
self.assertEqual(st_quotas[key], p_quotas[key])
# Verify that we do not have share groups related quotas
@@ -215,6 +247,31 @@
self.tenant_id, self.user_id, **{quota_key: new_quota})
self.assertEqual(new_quota, int(updated[quota_key]))
+ @ddt.data(("share_replicas", False),
+ ("share_replicas", True),
+ ("replica_gigabytes", False),
+ ("replica_gigabytes", True),
+ )
+ @ddt.unpack
+ @tc.attr(base.TAG_POSITIVE, base.TAG_API)
+ @base.skip_if_microversion_not_supported(SHARE_REPLICA_QUOTAS_MICROVERSION)
+ def test_update_user_quota_replica_related(self, quota_key, use_user_id):
+ kwargs = {}
+
+ # Update the kwargs with user_id in case the user_id need to be
+ # specified in the request
+ kwargs.update({'user_id': self.user_id}) if use_user_id else None
+ quotas = self.client.show_quotas(self.tenant_id, **kwargs)
+ new_quota = int(quotas[quota_key]) - 1
+
+ # Add the updated quota into the kwargs
+ kwargs.update({quota_key: new_quota})
+
+ # Set the new quota based on tenant or tenant and user_id
+ updated = self.client.update_quotas(
+ self.tenant_id, **kwargs)
+ self.assertEqual(new_quota, int(updated[quota_key]))
+
@ddt.data(
('id', True),
('name', False),
@@ -223,14 +280,22 @@
@tc.attr(base.TAG_POSITIVE, base.TAG_API)
@base.skip_if_microversion_lt("2.39")
def test_update_share_type_quota(self, share_type_key, is_st_public):
+ # Check if the used microversion supports 'share_replica' and
+ # 'replica_gigabytes' quotas
+ replica_quotas_supported = utils.share_replica_quotas_are_supported()
share_type = self._create_share_type()
# Get current quotas
quotas = self.client.show_quotas(
self.tenant_id, share_type=share_type[share_type_key])
+ quota_keys = ['shares', 'gigabytes', 'snapshots', 'snapshot_gigabytes']
+
+ if replica_quotas_supported:
+ quota_keys.append('share_replicas')
+ quota_keys.append('replica_gigabytes')
# Update quotas
- for q in ('shares', 'gigabytes', 'snapshots', 'snapshot_gigabytes'):
+ for q in quota_keys:
new_quota = int(quotas[q]) - 1
# Set new quota
@@ -242,7 +307,7 @@
current_quotas = self.client.show_quotas(
self.tenant_id, share_type=share_type[share_type_key])
- for q in ('shares', 'gigabytes', 'snapshots', 'snapshot_gigabytes'):
+ for q in quota_keys:
self.assertEqual(int(quotas[q]) - 1, current_quotas[q])
@tc.attr(base.TAG_POSITIVE, base.TAG_API)
@@ -368,6 +433,9 @@
data["share_groups"] = int(custom["share_groups"]) + 2
data["share_group_snapshots"] = (
int(custom["share_group_snapshots"]) + 2)
+ if utils.share_replica_quotas_are_supported():
+ data["share_replicas"] = int(custom["share_replicas"]) + 2
+ data["replica_gigabytes"] = int(custom["replica_gigabytes"]) + 2
# set new quota
updated = self.client.update_quotas(self.tenant_id, **data)
@@ -385,6 +453,11 @@
self.assertEqual(
data["share_group_snapshots"],
int(updated["share_group_snapshots"]))
+ if utils.share_replica_quotas_are_supported():
+ self.assertEqual(
+ data["share_replicas"], int(updated["share_replicas"]))
+ self.assertEqual(
+ data["replica_gigabytes"], int(updated["replica_gigabytes"]))
# Reset customized quotas
self.client.reset_quotas(self.tenant_id)
@@ -406,6 +479,21 @@
self.assertEqual(
int(default["share_group_snapshots"]),
int(reseted["share_group_snapshots"]))
+ if utils.share_replica_quotas_are_supported():
+ self.assertEqual(
+ int(default["share_replicas"]), int(reseted["share_replicas"]))
+ self.assertEqual(
+ int(default["replica_gigabytes"]),
+ int(reseted["replica_gigabytes"]))
+
+ def _get_new_replica_quota_values(self, default_quotas, value_to_set):
+ new_values = {
+ 'share_replicas': int(
+ default_quotas['share_replicas']) + value_to_set,
+ 'replica_gigabytes': int(
+ default_quotas['replica_gigabytes']) + value_to_set
+ }
+ return new_values
@ddt.data(
('id', True),
@@ -416,17 +504,34 @@
@base.skip_if_microversion_lt("2.39")
def test_reset_share_type_quotas(self, share_type_key, is_st_public):
share_type = self._create_share_type()
+ quota_keys = ['shares', 'snapshots', 'gigabytes', 'snapshot_gigabytes']
# get default_quotas
default_quotas = self.client.default_quotas(self.tenant_id)
+ kwargs = {}
+
+ # check if the replica_gigabytes and share_replicas quotas are
+ # supported
+ if utils.share_replica_quotas_are_supported():
+ kwargs.update(self._get_new_replica_quota_values(
+ default_quotas, 5))
+ quota_keys.append('share_replicas')
+ quota_keys.append('replica_gigabytes')
+
# set new quota for project
updated_p_quota = self.client.update_quotas(
self.tenant_id,
shares=int(default_quotas['shares']) + 5,
snapshots=int(default_quotas['snapshots']) + 5,
gigabytes=int(default_quotas['gigabytes']) + 5,
- snapshot_gigabytes=int(default_quotas['snapshot_gigabytes']) + 5)
+ snapshot_gigabytes=int(default_quotas['snapshot_gigabytes']) + 5,
+ **kwargs
+ )
+
+ if utils.share_replica_quotas_are_supported():
+ kwargs.update(self._get_new_replica_quota_values(
+ default_quotas, 3))
# set new quota for project
self.client.update_quotas(
@@ -435,7 +540,9 @@
shares=int(default_quotas['shares']) + 3,
snapshots=int(default_quotas['snapshots']) + 3,
gigabytes=int(default_quotas['gigabytes']) + 3,
- snapshot_gigabytes=int(default_quotas['snapshot_gigabytes']) + 3)
+ snapshot_gigabytes=int(default_quotas['snapshot_gigabytes']) + 3,
+ **kwargs
+ )
# reset share type quotas
self.client.reset_quotas(
@@ -445,7 +552,7 @@
current_p_quota = self.client.show_quotas(self.tenant_id)
current_st_quota = self.client.show_quotas(
self.tenant_id, share_type=share_type[share_type_key])
- for key in ('shares', 'snapshots', 'gigabytes', 'snapshot_gigabytes'):
+ for key in quota_keys:
self.assertEqual(updated_p_quota[key], current_p_quota[key])
# Default share type quotas are current project quotas
@@ -561,6 +668,30 @@
self.assertEqual(-1, quotas.get('share_group_snapshots'))
+ @ddt.data("share_replicas", "replica_gigabytes")
+ @tc.attr(base.TAG_POSITIVE, base.TAG_API)
+ @utils.skip_if_microversion_not_supported(
+ SHARE_REPLICA_QUOTAS_MICROVERSION)
+ def test_unlimited_quota_for_replica_quotas(self, quota_key):
+ kwargs = {quota_key: -1}
+ self.client.update_quotas(self.tenant_id, **kwargs)
+
+ quotas = self.client.show_quotas(self.tenant_id)
+
+ self.assertEqual(-1, quotas.get(quota_key))
+
+ @ddt.data("share_replicas", "replica_gigabytes")
+ @tc.attr(base.TAG_POSITIVE, base.TAG_API)
+ @utils.skip_if_microversion_not_supported(
+ SHARE_REPLICA_QUOTAS_MICROVERSION)
+ def test_unlimited_user_quota_for_replica_quotas(self, quota_key):
+ kwargs = {quota_key: -1}
+ self.client.update_quotas(self.tenant_id, self.user_id, **kwargs)
+
+ quotas = self.client.show_quotas(self.tenant_id, self.user_id)
+
+ self.assertEqual(-1, quotas.get(quota_key))
+
@ddt.data(11, -1)
@tc.attr(base.TAG_POSITIVE, base.TAG_API)
def test_update_user_quotas_bigger_than_project_quota(self, user_quota):
diff --git a/manila_tempest_tests/tests/api/admin/test_quotas_negative.py b/manila_tempest_tests/tests/api/admin/test_quotas_negative.py
index 299d54d..ae5e227 100644
--- a/manila_tempest_tests/tests/api/admin/test_quotas_negative.py
+++ b/manila_tempest_tests/tests/api/admin/test_quotas_negative.py
@@ -14,6 +14,7 @@
# under the License.
import ddt
+import manila_tempest_tests.tests.api.test_replication_negative as rep_neg_test
from tempest import config
from tempest.lib import exceptions as lib_exc
import testtools
@@ -25,6 +26,8 @@
CONF = config.CONF
PRE_SHARE_GROUPS_MICROVERSION = "2.39"
SHARE_GROUPS_MICROVERSION = "2.40"
+PRE_SHARE_REPLICA_QUOTAS_MICROVERSION = "2.52"
+SHARE_REPLICA_QUOTAS_MICROVERSION = "2.53"
@ddt.ddt
@@ -88,6 +91,21 @@
lib_exc.BadRequest,
client.update_quotas, client.tenant_id, **kwargs)
+ @ddt.data(
+ {"share_replicas": -2},
+ {"replica_gigabytes": -2},
+ )
+ @tc.attr(base.TAG_NEGATIVE, base.TAG_API)
+ @utils.skip_if_microversion_not_supported(
+ SHARE_REPLICA_QUOTAS_MICROVERSION)
+ def test_update_replica_quotas_wrong_data(self, kwargs):
+ # -1 is acceptable value as unlimited
+
+ client = self.get_client_with_isolated_creds(client_version='2')
+ self.assertRaises(
+ lib_exc.BadRequest,
+ client.update_quotas, client.tenant_id, **kwargs)
+
@tc.attr(base.TAG_NEGATIVE, base.TAG_API)
def test_create_share_with_size_bigger_than_quota(self):
quotas = self.shares_client.show_quotas(
@@ -196,6 +214,26 @@
force=False,
share_networks=bigger_value)
+ @ddt.data("share_replicas", "replica_gigabytes")
+ @tc.attr(base.TAG_NEGATIVE, base.TAG_API)
+ @utils.skip_if_microversion_not_supported(
+ SHARE_REPLICA_QUOTAS_MICROVERSION)
+ def test_try_set_user_quota_replicas_bigger_than_tenant_quota(self, key):
+ client = self.get_client_with_isolated_creds(client_version='2')
+
+ # get current quotas for tenant
+ tenant_quotas = client.show_quotas(client.tenant_id)
+
+ # try set user quota for snapshots bigger than tenant quota
+ bigger_value = int(tenant_quotas[key]) + 2
+ kwargs = {key: bigger_value}
+ self.assertRaises(lib_exc.BadRequest,
+ client.update_quotas,
+ client.tenant_id,
+ client.user_id,
+ force=False,
+ **kwargs)
+
@ddt.data(
('quota-sets', '2.0', 'show_quotas'),
('quota-sets', '2.0', 'default_quotas'),
@@ -302,6 +340,24 @@
client.tenant_id,
**kwargs)
+ @ddt.data("share_replicas", "replica_gigabytes")
+ @tc.attr(base.TAG_NEGATIVE, base.TAG_API)
+ @base.skip_if_microversion_not_supported(SHARE_REPLICA_QUOTAS_MICROVERSION)
+ def test_share_replica_quotas_using_too_old_microversion(self, quota_key):
+ client = self.get_client_with_isolated_creds(client_version='2')
+ tenant_quotas = client.show_quotas(
+ client.tenant_id, version=SHARE_REPLICA_QUOTAS_MICROVERSION)
+ kwargs = {
+ "version": PRE_SHARE_REPLICA_QUOTAS_MICROVERSION,
+ quota_key: tenant_quotas[quota_key],
+ }
+
+ self.assertRaises(
+ lib_exc.BadRequest,
+ client.update_quotas,
+ client.tenant_id,
+ **kwargs)
+
@ddt.data('show', 'reset', 'update')
@tc.attr(base.TAG_NEGATIVE, base.TAG_API)
@base.skip_if_microversion_lt("2.38")
@@ -366,3 +422,77 @@
self.assertRaises(lib_exc.OverLimit,
self.create_share,
share_type_id=self.share_type_id)
+
+
+@ddt.ddt
+class ReplicaQuotasNegativeTest(rep_neg_test.ReplicationNegativeBase):
+
+ @classmethod
+ def skip_checks(cls):
+ super(ReplicaQuotasNegativeTest, cls).skip_checks()
+ if not CONF.share.run_quota_tests:
+ msg = "Quota tests are disabled."
+ raise cls.skipException(msg)
+
+ utils.check_skip_if_microversion_lt(SHARE_REPLICA_QUOTAS_MICROVERSION)
+
+ def _modify_quotas_for_test(self, quota_key, new_limit):
+ kwargs = {quota_key: new_limit}
+
+ # Get the original quota values
+ original_quota = self.admin_client.show_quotas(self.tenant_id)
+
+ # Update the current quotas
+ self.admin_client.update_quotas(self.tenant_id, **kwargs)
+
+ # Save the previous value
+ old_quota_values = {quota_key: original_quota[quota_key]}
+
+ # Get the updated quotas and add a cleanup
+ updated_quota = self.admin_client.show_quotas(self.tenant_id)
+ self.addCleanup(self.admin_client.update_quotas,
+ self.tenant_id,
+ **old_quota_values)
+
+ # Make sure that the new value was properly set
+ self.assertEqual(new_limit, updated_quota[quota_key])
+
+ @tc.attr(base.TAG_NEGATIVE, base.TAG_API_WITH_BACKEND)
+ @ddt.data(('share_replicas', 2), ('replica_gigabytes', None))
+ @ddt.unpack
+ def test_create_replica_over_replica_limit(self, quota_key, new_limit):
+ # Define the quota values to be updated
+ new_limit = (int(self.share1['size'] * 2)
+ if quota_key == 'replica_gigabytes' else new_limit)
+
+ # Create an inactive share replica
+ self.create_share_replica(
+ self.share1["id"], self.replica_zone, cleanup_in_class=False)
+
+ # Modify the quota limit for this test
+ self._modify_quotas_for_test(quota_key, new_limit)
+
+ # Make sure that the request to create a third one will fail
+ self.assertRaises(lib_exc.OverLimit,
+ self.create_share_replica,
+ self.share1['id'],
+ availability_zone=self.replica_zone)
+
+ @testtools.skipUnless(
+ CONF.share.run_extend_tests,
+ "Share extend tests are disabled.")
+ @tc.attr(base.TAG_NEGATIVE, base.TAG_API_WITH_BACKEND)
+ def test_extend_replica_over_limit(self):
+ # Define the quota values to be updated
+ quota_key = 'replica_gigabytes'
+
+ # Modify the quota limit for this test
+ self._modify_quotas_for_test(quota_key, new_limit=self.share1['size'])
+
+ new_size = self.share1['size'] + 1
+
+ # Make sure that the request to create a third one will fail
+ self.assertRaises(lib_exc.OverLimit,
+ self.shares_v2_client.extend_share,
+ self.share1['id'],
+ new_size)
diff --git a/manila_tempest_tests/tests/api/admin/test_user_messages.py b/manila_tempest_tests/tests/api/admin/test_user_messages.py
index 8a11b1c..9d69f90 100644
--- a/manila_tempest_tests/tests/api/admin/test_user_messages.py
+++ b/manila_tempest_tests/tests/api/admin/test_user_messages.py
@@ -10,6 +10,8 @@
# License for the specific language governing permissions and limitations
# under the License.
+import datetime
+
from oslo_utils import timeutils
from oslo_utils import uuidutils
from tempest import config
@@ -21,6 +23,7 @@
CONF = config.CONF
MICROVERSION = '2.37'
+QUERY_BY_TIMESTAMP_MICROVERSION = '2.52'
MESSAGE_KEYS = (
'created_at',
'action_id',
@@ -111,3 +114,40 @@
self.shares_v2_client.delete_message(self.message['id'])
self.shares_v2_client.wait_for_resource_deletion(
message_id=self.message['id'])
+
+ @decorators.attr(type=[base.TAG_POSITIVE, base.TAG_API])
+ @base.skip_if_microversion_not_supported(QUERY_BY_TIMESTAMP_MICROVERSION)
+ def test_list_messages_with_since_and_before_filters(self):
+ new_message = self.create_user_message()
+ created_at_1 = timeutils.parse_strtime(self.message['created_at'])
+ created_at_2 = timeutils.parse_strtime(new_message['created_at'])
+ time_1 = created_at_1 - datetime.timedelta(seconds=1)
+ time_2 = created_at_2 - datetime.timedelta(seconds=1)
+
+ params1 = {'created_since': str(created_at_1)}
+ # should return all user messages created by this test including
+ # self.message
+ messages = self.shares_v2_client.list_messages(params=params1)
+ ids = [x['id'] for x in messages]
+ self.assertGreaterEqual(len(ids), 2)
+ self.assertIn(self.message['id'], ids)
+ self.assertIn(new_message['id'], ids)
+
+ params2 = {'created_since': str(time_1),
+ 'created_before': str(time_2)}
+ # should not return new_message, but return a list that is equal to 1
+ # and include self.message
+ messages = self.shares_v2_client.list_messages(params=params2)
+ self.assertIsInstance(messages, list)
+ ids = [x['id'] for x in messages]
+ self.assertGreaterEqual(len(ids), 1)
+ self.assertIn(self.message['id'], ids)
+ self.assertNotIn(new_message['id'], ids)
+
+ params3 = {'created_before': str(time_2)}
+ # should not include self.message
+ messages = self.shares_v2_client.list_messages(params=params3)
+ ids = [x['id'] for x in messages]
+ self.assertGreaterEqual(len(ids), 1)
+ self.assertNotIn(new_message['id'], ids)
+ self.assertIn(self.message['id'], ids)
diff --git a/manila_tempest_tests/tests/api/admin/test_user_messages_negative.py b/manila_tempest_tests/tests/api/admin/test_user_messages_negative.py
index c9debdd..cf592e4 100644
--- a/manila_tempest_tests/tests/api/admin/test_user_messages_negative.py
+++ b/manila_tempest_tests/tests/api/admin/test_user_messages_negative.py
@@ -21,6 +21,7 @@
CONF = config.CONF
MICROVERSION = '2.37'
+QUERY_BY_TIMESTAMP_MICROVERSION = '2.52'
class UserMessageNegativeTest(base.BaseSharesAdminTest):
@@ -61,3 +62,13 @@
self.assertRaises(lib_exc.NotFound,
self.shares_v2_client.delete_message,
six.text_type(uuidutils.generate_uuid()))
+
+ @decorators.attr(type=[base.TAG_NEGATIVE, base.TAG_API])
+ @base.skip_if_microversion_not_supported(QUERY_BY_TIMESTAMP_MICROVERSION)
+ def test_list_messages_with_invalid_time_format(self):
+ params_key = ['created_since', 'created_before']
+ for key in params_key:
+ params = {key: 'invalid_time'}
+ self.assertRaises(lib_exc.BadRequest,
+ self.shares_v2_client.list_messages,
+ params=params)
diff --git a/manila_tempest_tests/tests/api/base.py b/manila_tempest_tests/tests/api/base.py
index 89f2e92..22b1d72 100644
--- a/manila_tempest_tests/tests/api/base.py
+++ b/manila_tempest_tests/tests/api/base.py
@@ -980,7 +980,7 @@
res_id = res['id']
client = res["client"]
with handle_cleanup_exceptions():
- if res["type"] is "share":
+ if res["type"] == "share":
cls.clear_share_replicas(res_id)
share_group_id = res.get('share_group_id')
if share_group_id:
@@ -989,35 +989,35 @@
else:
client.delete_share(res_id)
client.wait_for_resource_deletion(share_id=res_id)
- elif res["type"] is "snapshot":
+ elif res["type"] == "snapshot":
client.delete_snapshot(res_id)
client.wait_for_resource_deletion(snapshot_id=res_id)
- elif (res["type"] is "share_network" and
+ elif (res["type"] == "share_network" and
res_id != CONF.share.share_network_id):
client.delete_share_network(res_id)
client.wait_for_resource_deletion(sn_id=res_id)
- elif res["type"] is "security_service":
+ elif res["type"] == "security_service":
client.delete_security_service(res_id)
client.wait_for_resource_deletion(ss_id=res_id)
- elif res["type"] is "share_type":
+ elif res["type"] == "share_type":
client.delete_share_type(res_id)
client.wait_for_resource_deletion(st_id=res_id)
- elif res["type"] is "share_group":
+ elif res["type"] == "share_group":
client.delete_share_group(res_id)
client.wait_for_resource_deletion(
share_group_id=res_id)
- elif res["type"] is "share_group_type":
+ elif res["type"] == "share_group_type":
client.delete_share_group_type(res_id)
client.wait_for_resource_deletion(
share_group_type_id=res_id)
- elif res["type"] is "share_group_snapshot":
+ elif res["type"] == "share_group_snapshot":
client.delete_share_group_snapshot(res_id)
client.wait_for_resource_deletion(
share_group_snapshot_id=res_id)
- elif res["type"] is "share_replica":
+ elif res["type"] == "share_replica":
client.delete_share_replica(res_id)
client.wait_for_resource_deletion(replica_id=res_id)
- elif res["type"] is "share_network_subnet":
+ elif res["type"] == "share_network_subnet":
sn_id = res["extra_params"]["share_network_id"]
client.delete_subnet(sn_id, res_id)
client.wait_for_resource_deletion(
diff --git a/manila_tempest_tests/tests/api/test_quotas.py b/manila_tempest_tests/tests/api/test_quotas.py
index 83c776f..d7137f5 100644
--- a/manila_tempest_tests/tests/api/test_quotas.py
+++ b/manila_tempest_tests/tests/api/test_quotas.py
@@ -15,12 +15,15 @@
import ddt
import itertools
+from manila_tempest_tests import utils
from tempest import config
from testtools import testcase as tc
from manila_tempest_tests.tests.api import base
CONF = config.CONF
+PRE_SHARE_REPLICAS_MICROVERSION = "2.52"
+SHARE_REPLICAS_MICROVERSION = "2.53"
@ddt.ddt
@@ -39,35 +42,49 @@
@ddt.data('shares_client', 'shares_v2_client')
def test_default_quotas(self, client_name):
quotas = getattr(self, client_name).default_quotas(self.tenant_id)
+ uses_v2_client = client_name == 'shares_v2_client'
self.assertGreater(int(quotas["gigabytes"]), -2)
self.assertGreater(int(quotas["snapshot_gigabytes"]), -2)
self.assertGreater(int(quotas["shares"]), -2)
self.assertGreater(int(quotas["snapshots"]), -2)
self.assertGreater(int(quotas["share_networks"]), -2)
+ if utils.share_replica_quotas_are_supported() and uses_v2_client:
+ self.assertGreater(int(quotas["share_replicas"]), -2)
+ self.assertGreater(int(quotas["replica_gigabytes"]), -2)
@tc.attr(base.TAG_POSITIVE, base.TAG_API)
@ddt.data('shares_client', 'shares_v2_client')
def test_show_quotas(self, client_name):
quotas = getattr(self, client_name).show_quotas(self.tenant_id)
+ uses_v2_client = client_name == 'shares_v2_client'
self.assertGreater(int(quotas["gigabytes"]), -2)
self.assertGreater(int(quotas["snapshot_gigabytes"]), -2)
self.assertGreater(int(quotas["shares"]), -2)
self.assertGreater(int(quotas["snapshots"]), -2)
self.assertGreater(int(quotas["share_networks"]), -2)
+ if utils.share_replica_quotas_are_supported() and uses_v2_client:
+ self.assertGreater(int(quotas["share_replicas"]), -2)
+ self.assertGreater(int(quotas["replica_gigabytes"]), -2)
@tc.attr(base.TAG_POSITIVE, base.TAG_API)
@ddt.data('shares_client', 'shares_v2_client')
def test_show_quotas_for_user(self, client_name):
quotas = getattr(self, client_name).show_quotas(
self.tenant_id, self.user_id)
+ uses_v2_client = client_name == 'shares_v2_client'
self.assertGreater(int(quotas["gigabytes"]), -2)
self.assertGreater(int(quotas["snapshot_gigabytes"]), -2)
self.assertGreater(int(quotas["shares"]), -2)
self.assertGreater(int(quotas["snapshots"]), -2)
self.assertGreater(int(quotas["share_networks"]), -2)
+ if utils.share_replica_quotas_are_supported() and uses_v2_client:
+ self.assertGreater(int(quotas["share_replicas"]), -2)
+ self.assertGreater(int(quotas["replica_gigabytes"]), -2)
@ddt.data(
*itertools.product(set(("2.25", CONF.share.max_api_microversion)),
+ (True, False)),
+ *itertools.product(set(("2.53", CONF.share.max_api_microversion)),
(True, False))
)
@ddt.unpack
@@ -75,14 +92,27 @@
@base.skip_if_microversion_not_supported("2.25")
def test_show_quotas_detail(self, microversion, with_user):
quota_args = {"tenant_id": self.tenant_id, "version": microversion, }
+ keys = ['gigabytes', 'snapshot_gigabytes', 'shares',
+ 'snapshots', 'share_networks']
+ if utils.is_microversion_ge(microversion, SHARE_REPLICAS_MICROVERSION):
+ keys.append('share_replicas')
+ keys.append('replica_gigabytes')
if with_user:
quota_args.update({"user_id": self.user_id})
quotas = self.shares_v2_client.detail_quotas(**quota_args)
quota_keys = list(quotas.keys())
- for outer in ('gigabytes', 'snapshot_gigabytes', 'shares',
- 'snapshots', 'share_networks'):
+ for outer in keys:
self.assertIn(outer, quota_keys)
outer_keys = list(quotas[outer].keys())
for inner in ('in_use', 'limit', 'reserved'):
self.assertIn(inner, outer_keys)
self.assertGreater(int(quotas[outer][inner]), -2)
+
+ @tc.attr(base.TAG_POSITIVE, base.TAG_API)
+ @base.skip_if_microversion_not_supported(PRE_SHARE_REPLICAS_MICROVERSION)
+ def test_quota_detail_2_52_no_share_replica_quotas(self):
+ quota_args = {"tenant_id": self.tenant_id,
+ "version": PRE_SHARE_REPLICAS_MICROVERSION}
+ quotas = self.shares_v2_client.detail_quotas(**quota_args)
+ self.assertNotIn('share_replicas', quotas.keys())
+ self.assertNotIn('replica_gigabytes', quotas.keys())
diff --git a/manila_tempest_tests/tests/api/test_replication_negative.py b/manila_tempest_tests/tests/api/test_replication_negative.py
index a71449e..3215641 100644
--- a/manila_tempest_tests/tests/api/test_replication_negative.py
+++ b/manila_tempest_tests/tests/api/test_replication_negative.py
@@ -28,11 +28,10 @@
_MIN_SUPPORTED_MICROVERSION = '2.11'
-class ReplicationNegativeTest(base.BaseSharesMixedTest):
-
+class ReplicationNegativeBase(base.BaseSharesMixedTest):
@classmethod
def skip_checks(cls):
- super(ReplicationNegativeTest, cls).skip_checks()
+ super(ReplicationNegativeBase, cls).skip_checks()
if not CONF.share.run_replication_tests:
raise cls.skipException('Replication tests are disabled.')
@@ -40,7 +39,7 @@
@classmethod
def resource_setup(cls):
- super(ReplicationNegativeTest, cls).resource_setup()
+ super(ReplicationNegativeBase, cls).resource_setup()
cls.admin_client = cls.admin_shares_v2_client
cls.replication_type = CONF.share.backend_replication_type
cls.multitenancy_enabled = (
@@ -80,6 +79,9 @@
instance_id = share_instances[0]["id"]
return share, instance_id
+
+class ReplicationNegativeTest(ReplicationNegativeBase):
+
def _is_replication_type_promotable(self):
if (self.replication_type
not in constants.REPLICATION_PROMOTION_CHOICES):
diff --git a/manila_tempest_tests/tests/scenario/test_share_basic_ops.py b/manila_tempest_tests/tests/scenario/test_share_basic_ops.py
index 882f7cb..5603fab 100644
--- a/manila_tempest_tests/tests/scenario/test_share_basic_ops.py
+++ b/manila_tempest_tests/tests/scenario/test_share_basic_ops.py
@@ -190,8 +190,8 @@
if (force_host_assisted and
not CONF.share.run_host_assisted_migration_tests):
- raise self.skipException("Host-assisted migration tests are "
- "disabled.")
+ raise self.skipException("Host-assisted migration tests are "
+ "disabled.")
elif (not force_host_assisted and
not CONF.share.run_driver_assisted_migration_tests):
raise self.skipException("Driver-assisted migration tests are "
diff --git a/manila_tempest_tests/utils.py b/manila_tempest_tests/utils.py
index 2ea623d..b22a5c1 100644
--- a/manila_tempest_tests/utils.py
+++ b/manila_tempest_tests/utils.py
@@ -23,6 +23,7 @@
CONF = config.CONF
SHARE_NETWORK_SUBNETS_MICROVERSION = '2.51'
+SHARE_REPLICA_QUOTAS_MICROVERSION = "2.53"
def get_microversion_as_tuple(microversion_str):
@@ -202,6 +203,10 @@
return is_microversion_supported(SHARE_NETWORK_SUBNETS_MICROVERSION)
+def share_replica_quotas_are_supported():
+ return is_microversion_supported(SHARE_REPLICA_QUOTAS_MICROVERSION)
+
+
def share_network_get_default_subnet(share_network):
return next((
subnet for subnet in share_network.get('share_network_subnets', [])
diff --git a/test-requirements.txt b/test-requirements.txt
index 337b82e..6a6ab89 100644
--- a/test-requirements.txt
+++ b/test-requirements.txt
@@ -2,7 +2,7 @@
# of appearance. Changing the order has an impact on the overall integration
# process, which may cause wedges in the gate later.
-hacking<0.13,>=0.12.0 # Apache-2.0
+hacking>=3.0,<3.1.0;python_version>'3' # Apache-2.0
coverage!=4.4,>=4.0 # Apache-2.0
python-subunit>=1.0.0 # Apache-2.0/BSD
diff --git a/tox.ini b/tox.ini
index 0218477..59764db 100644
--- a/tox.ini
+++ b/tox.ini
@@ -35,8 +35,9 @@
[flake8]
# E123, E125 skipped as they are invalid PEP-8.
-
+# W503 line break before binary operator
+# W504 line break after binary operator
show-source = True
-ignore = E123,E125
+ignore = E123,E125,W503,W504
builtins = _
exclude=.venv,.git,.tox,dist,doc,*lib/python*,*egg,build