port flavors and server_password tests into nova v3 part1
This changeset only copies the v2 files into the appropriate v3 directories unchanged. This is being tried in order to make reviewing of the porting easier as gerrit will display only what is actually changed for v3 rather than entirely new files. Partially implements blueprint nova-v3-api-tests Change-Id: Ifd7409aa7ece0f3a882918cfde66f5e45cea6576
This commit is contained in:
parent
0155496ecd
commit
67984018df
316
tempest/api/compute/v3/admin/test_flavors.py
Normal file
316
tempest/api/compute/v3/admin/test_flavors.py
Normal file
@ -0,0 +1,316 @@
|
|||||||
|
# Copyright 2012 OpenStack Foundation
|
||||||
|
# All Rights Reserved.
|
||||||
|
#
|
||||||
|
# Licensed under the Apache License, Version 2.0 (the "License"); you may
|
||||||
|
# not use this file except in compliance with the License. You may obtain
|
||||||
|
# a copy of the License at
|
||||||
|
#
|
||||||
|
# http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
#
|
||||||
|
# Unless required by applicable law or agreed to in writing, software
|
||||||
|
# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
|
||||||
|
# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
|
||||||
|
# License for the specific language governing permissions and limitations
|
||||||
|
# under the License.
|
||||||
|
|
||||||
|
import uuid
|
||||||
|
|
||||||
|
from tempest.api.compute import base
|
||||||
|
from tempest.common.utils import data_utils
|
||||||
|
from tempest import exceptions
|
||||||
|
from tempest import test
|
||||||
|
|
||||||
|
|
||||||
|
class FlavorsAdminTestJSON(base.BaseV2ComputeAdminTest):
|
||||||
|
|
||||||
|
"""
|
||||||
|
Tests Flavors API Create and Delete that require admin privileges
|
||||||
|
"""
|
||||||
|
|
||||||
|
_interface = 'json'
|
||||||
|
|
||||||
|
@classmethod
|
||||||
|
def setUpClass(cls):
|
||||||
|
super(FlavorsAdminTestJSON, cls).setUpClass()
|
||||||
|
if not test.is_extension_enabled('FlavorExtraData', 'compute'):
|
||||||
|
msg = "FlavorExtraData extension not enabled."
|
||||||
|
raise cls.skipException(msg)
|
||||||
|
|
||||||
|
cls.client = cls.os_adm.flavors_client
|
||||||
|
cls.user_client = cls.os.flavors_client
|
||||||
|
cls.flavor_name_prefix = 'test_flavor_'
|
||||||
|
cls.ram = 512
|
||||||
|
cls.vcpus = 1
|
||||||
|
cls.disk = 10
|
||||||
|
cls.ephemeral = 10
|
||||||
|
cls.swap = 1024
|
||||||
|
cls.rxtx = 2
|
||||||
|
|
||||||
|
def flavor_clean_up(self, flavor_id):
|
||||||
|
resp, body = self.client.delete_flavor(flavor_id)
|
||||||
|
self.assertEqual(resp.status, 202)
|
||||||
|
self.client.wait_for_resource_deletion(flavor_id)
|
||||||
|
|
||||||
|
def _create_flavor(self, flavor_id):
|
||||||
|
# Create a flavor and ensure it is listed
|
||||||
|
# This operation requires the user to have 'admin' role
|
||||||
|
flavor_name = data_utils.rand_name(self.flavor_name_prefix)
|
||||||
|
|
||||||
|
# Create the flavor
|
||||||
|
resp, flavor = self.client.create_flavor(flavor_name,
|
||||||
|
self.ram, self.vcpus,
|
||||||
|
self.disk,
|
||||||
|
flavor_id,
|
||||||
|
ephemeral=self.ephemeral,
|
||||||
|
swap=self.swap,
|
||||||
|
rxtx=self.rxtx)
|
||||||
|
self.addCleanup(self.flavor_clean_up, flavor['id'])
|
||||||
|
self.assertEqual(200, resp.status)
|
||||||
|
self.assertEqual(flavor['name'], flavor_name)
|
||||||
|
self.assertEqual(flavor['vcpus'], self.vcpus)
|
||||||
|
self.assertEqual(flavor['disk'], self.disk)
|
||||||
|
self.assertEqual(flavor['ram'], self.ram)
|
||||||
|
self.assertEqual(flavor['swap'], self.swap)
|
||||||
|
self.assertEqual(flavor['rxtx_factor'], self.rxtx)
|
||||||
|
self.assertEqual(flavor['OS-FLV-EXT-DATA:ephemeral'],
|
||||||
|
self.ephemeral)
|
||||||
|
self.assertEqual(flavor['os-flavor-access:is_public'], True)
|
||||||
|
|
||||||
|
# Verify flavor is retrieved
|
||||||
|
resp, flavor = self.client.get_flavor_details(flavor['id'])
|
||||||
|
self.assertEqual(resp.status, 200)
|
||||||
|
self.assertEqual(flavor['name'], flavor_name)
|
||||||
|
|
||||||
|
return flavor['id']
|
||||||
|
|
||||||
|
@test.attr(type='gate')
|
||||||
|
def test_create_flavor_with_int_id(self):
|
||||||
|
flavor_id = data_utils.rand_int_id(start=1000)
|
||||||
|
new_flavor_id = self._create_flavor(flavor_id)
|
||||||
|
self.assertEqual(new_flavor_id, str(flavor_id))
|
||||||
|
|
||||||
|
@test.attr(type='gate')
|
||||||
|
def test_create_flavor_with_uuid_id(self):
|
||||||
|
flavor_id = str(uuid.uuid4())
|
||||||
|
new_flavor_id = self._create_flavor(flavor_id)
|
||||||
|
self.assertEqual(new_flavor_id, flavor_id)
|
||||||
|
|
||||||
|
@test.attr(type='gate')
|
||||||
|
def test_create_flavor_with_none_id(self):
|
||||||
|
# If nova receives a request with None as flavor_id,
|
||||||
|
# nova generates flavor_id of uuid.
|
||||||
|
flavor_id = None
|
||||||
|
new_flavor_id = self._create_flavor(flavor_id)
|
||||||
|
self.assertEqual(new_flavor_id, str(uuid.UUID(new_flavor_id)))
|
||||||
|
|
||||||
|
@test.attr(type='gate')
|
||||||
|
def test_create_flavor_verify_entry_in_list_details(self):
|
||||||
|
# Create a flavor and ensure it's details are listed
|
||||||
|
# This operation requires the user to have 'admin' role
|
||||||
|
flavor_name = data_utils.rand_name(self.flavor_name_prefix)
|
||||||
|
new_flavor_id = data_utils.rand_int_id(start=1000)
|
||||||
|
|
||||||
|
# Create the flavor
|
||||||
|
resp, flavor = self.client.create_flavor(flavor_name,
|
||||||
|
self.ram, self.vcpus,
|
||||||
|
self.disk,
|
||||||
|
new_flavor_id,
|
||||||
|
ephemeral=self.ephemeral,
|
||||||
|
swap=self.swap,
|
||||||
|
rxtx=self.rxtx)
|
||||||
|
self.addCleanup(self.flavor_clean_up, flavor['id'])
|
||||||
|
flag = False
|
||||||
|
# Verify flavor is retrieved
|
||||||
|
resp, flavors = self.client.list_flavors_with_detail()
|
||||||
|
self.assertEqual(resp.status, 200)
|
||||||
|
for flavor in flavors:
|
||||||
|
if flavor['name'] == flavor_name:
|
||||||
|
flag = True
|
||||||
|
self.assertTrue(flag)
|
||||||
|
|
||||||
|
@test.attr(type='gate')
|
||||||
|
def test_create_list_flavor_without_extra_data(self):
|
||||||
|
# Create a flavor and ensure it is listed
|
||||||
|
# This operation requires the user to have 'admin' role
|
||||||
|
|
||||||
|
def verify_flavor_response_extension(flavor):
|
||||||
|
# check some extensions for the flavor create/show/detail response
|
||||||
|
self.assertEqual(flavor['swap'], '')
|
||||||
|
self.assertEqual(int(flavor['rxtx_factor']), 1)
|
||||||
|
self.assertEqual(int(flavor['OS-FLV-EXT-DATA:ephemeral']), 0)
|
||||||
|
self.assertEqual(flavor['os-flavor-access:is_public'], True)
|
||||||
|
|
||||||
|
flavor_name = data_utils.rand_name(self.flavor_name_prefix)
|
||||||
|
new_flavor_id = data_utils.rand_int_id(start=1000)
|
||||||
|
|
||||||
|
# Create the flavor
|
||||||
|
resp, flavor = self.client.create_flavor(flavor_name,
|
||||||
|
self.ram, self.vcpus,
|
||||||
|
self.disk,
|
||||||
|
new_flavor_id)
|
||||||
|
self.addCleanup(self.flavor_clean_up, flavor['id'])
|
||||||
|
self.assertEqual(200, resp.status)
|
||||||
|
self.assertEqual(flavor['name'], flavor_name)
|
||||||
|
self.assertEqual(flavor['ram'], self.ram)
|
||||||
|
self.assertEqual(flavor['vcpus'], self.vcpus)
|
||||||
|
self.assertEqual(flavor['disk'], self.disk)
|
||||||
|
self.assertEqual(int(flavor['id']), new_flavor_id)
|
||||||
|
verify_flavor_response_extension(flavor)
|
||||||
|
|
||||||
|
# Verify flavor is retrieved
|
||||||
|
resp, flavor = self.client.get_flavor_details(new_flavor_id)
|
||||||
|
self.assertEqual(resp.status, 200)
|
||||||
|
self.assertEqual(flavor['name'], flavor_name)
|
||||||
|
verify_flavor_response_extension(flavor)
|
||||||
|
|
||||||
|
# Check if flavor is present in list
|
||||||
|
resp, flavors = self.user_client.list_flavors_with_detail()
|
||||||
|
self.assertEqual(resp.status, 200)
|
||||||
|
for flavor in flavors:
|
||||||
|
if flavor['name'] == flavor_name:
|
||||||
|
verify_flavor_response_extension(flavor)
|
||||||
|
flag = True
|
||||||
|
self.assertTrue(flag)
|
||||||
|
|
||||||
|
@test.skip_because(bug="1209101")
|
||||||
|
@test.attr(type='gate')
|
||||||
|
def test_list_non_public_flavor(self):
|
||||||
|
# Create a flavor with os-flavor-access:is_public false should
|
||||||
|
# be present in list_details.
|
||||||
|
# This operation requires the user to have 'admin' role
|
||||||
|
flavor_name = data_utils.rand_name(self.flavor_name_prefix)
|
||||||
|
new_flavor_id = data_utils.rand_int_id(start=1000)
|
||||||
|
|
||||||
|
# Create the flavor
|
||||||
|
resp, flavor = self.client.create_flavor(flavor_name,
|
||||||
|
self.ram, self.vcpus,
|
||||||
|
self.disk,
|
||||||
|
new_flavor_id,
|
||||||
|
is_public="False")
|
||||||
|
self.addCleanup(self.flavor_clean_up, flavor['id'])
|
||||||
|
# Verify flavor is retrieved
|
||||||
|
flag = False
|
||||||
|
resp, flavors = self.client.list_flavors_with_detail()
|
||||||
|
self.assertEqual(resp.status, 200)
|
||||||
|
for flavor in flavors:
|
||||||
|
if flavor['name'] == flavor_name:
|
||||||
|
flag = True
|
||||||
|
self.assertTrue(flag)
|
||||||
|
|
||||||
|
# Verify flavor is not retrieved with other user
|
||||||
|
flag = False
|
||||||
|
resp, flavors = self.user_client.list_flavors_with_detail()
|
||||||
|
self.assertEqual(resp.status, 200)
|
||||||
|
for flavor in flavors:
|
||||||
|
if flavor['name'] == flavor_name:
|
||||||
|
flag = True
|
||||||
|
self.assertFalse(flag)
|
||||||
|
|
||||||
|
@test.attr(type='gate')
|
||||||
|
def test_create_server_with_non_public_flavor(self):
|
||||||
|
# Create a flavor with os-flavor-access:is_public false
|
||||||
|
flavor_name = data_utils.rand_name(self.flavor_name_prefix)
|
||||||
|
new_flavor_id = data_utils.rand_int_id(start=1000)
|
||||||
|
|
||||||
|
# Create the flavor
|
||||||
|
resp, flavor = self.client.create_flavor(flavor_name,
|
||||||
|
self.ram, self.vcpus,
|
||||||
|
self.disk,
|
||||||
|
new_flavor_id,
|
||||||
|
is_public="False")
|
||||||
|
self.addCleanup(self.flavor_clean_up, flavor['id'])
|
||||||
|
self.assertEqual(200, resp.status)
|
||||||
|
|
||||||
|
# Verify flavor is not used by other user
|
||||||
|
self.assertRaises(exceptions.BadRequest,
|
||||||
|
self.os.servers_client.create_server,
|
||||||
|
'test', self.image_ref, flavor['id'])
|
||||||
|
|
||||||
|
@test.attr(type='gate')
|
||||||
|
def test_list_public_flavor_with_other_user(self):
|
||||||
|
# Create a Flavor with public access.
|
||||||
|
# Try to List/Get flavor with another user
|
||||||
|
flavor_name = data_utils.rand_name(self.flavor_name_prefix)
|
||||||
|
new_flavor_id = data_utils.rand_int_id(start=1000)
|
||||||
|
|
||||||
|
# Create the flavor
|
||||||
|
resp, flavor = self.client.create_flavor(flavor_name,
|
||||||
|
self.ram, self.vcpus,
|
||||||
|
self.disk,
|
||||||
|
new_flavor_id,
|
||||||
|
is_public="True")
|
||||||
|
self.addCleanup(self.flavor_clean_up, flavor['id'])
|
||||||
|
flag = False
|
||||||
|
self.new_client = self.flavors_client
|
||||||
|
# Verify flavor is retrieved with new user
|
||||||
|
resp, flavors = self.new_client.list_flavors_with_detail()
|
||||||
|
self.assertEqual(resp.status, 200)
|
||||||
|
for flavor in flavors:
|
||||||
|
if flavor['name'] == flavor_name:
|
||||||
|
flag = True
|
||||||
|
self.assertTrue(flag)
|
||||||
|
|
||||||
|
@test.attr(type='gate')
|
||||||
|
def test_is_public_string_variations(self):
|
||||||
|
flavor_id_not_public = data_utils.rand_int_id(start=1000)
|
||||||
|
flavor_name_not_public = data_utils.rand_name(self.flavor_name_prefix)
|
||||||
|
flavor_id_public = data_utils.rand_int_id(start=1000)
|
||||||
|
flavor_name_public = data_utils.rand_name(self.flavor_name_prefix)
|
||||||
|
|
||||||
|
# Create a non public flavor
|
||||||
|
resp, flavor = self.client.create_flavor(flavor_name_not_public,
|
||||||
|
self.ram, self.vcpus,
|
||||||
|
self.disk,
|
||||||
|
flavor_id_not_public,
|
||||||
|
is_public="False")
|
||||||
|
self.addCleanup(self.flavor_clean_up, flavor['id'])
|
||||||
|
|
||||||
|
# Create a public flavor
|
||||||
|
resp, flavor = self.client.create_flavor(flavor_name_public,
|
||||||
|
self.ram, self.vcpus,
|
||||||
|
self.disk,
|
||||||
|
flavor_id_public,
|
||||||
|
is_public="True")
|
||||||
|
self.addCleanup(self.flavor_clean_up, flavor['id'])
|
||||||
|
|
||||||
|
def _flavor_lookup(flavors, flavor_name):
|
||||||
|
for flavor in flavors:
|
||||||
|
if flavor['name'] == flavor_name:
|
||||||
|
return flavor
|
||||||
|
return None
|
||||||
|
|
||||||
|
def _test_string_variations(variations, flavor_name):
|
||||||
|
for string in variations:
|
||||||
|
params = {'is_public': string}
|
||||||
|
r, flavors = self.client.list_flavors_with_detail(params)
|
||||||
|
self.assertEqual(r.status, 200)
|
||||||
|
flavor = _flavor_lookup(flavors, flavor_name)
|
||||||
|
self.assertIsNotNone(flavor)
|
||||||
|
|
||||||
|
_test_string_variations(['f', 'false', 'no', '0'],
|
||||||
|
flavor_name_not_public)
|
||||||
|
|
||||||
|
_test_string_variations(['t', 'true', 'yes', '1'],
|
||||||
|
flavor_name_public)
|
||||||
|
|
||||||
|
@test.attr(type='gate')
|
||||||
|
def test_create_flavor_using_string_ram(self):
|
||||||
|
flavor_name = data_utils.rand_name(self.flavor_name_prefix)
|
||||||
|
new_flavor_id = data_utils.rand_int_id(start=1000)
|
||||||
|
|
||||||
|
ram = " 1024 "
|
||||||
|
resp, flavor = self.client.create_flavor(flavor_name,
|
||||||
|
ram, self.vcpus,
|
||||||
|
self.disk,
|
||||||
|
new_flavor_id)
|
||||||
|
self.addCleanup(self.flavor_clean_up, flavor['id'])
|
||||||
|
self.assertEqual(200, resp.status)
|
||||||
|
self.assertEqual(flavor['name'], flavor_name)
|
||||||
|
self.assertEqual(flavor['vcpus'], self.vcpus)
|
||||||
|
self.assertEqual(flavor['disk'], self.disk)
|
||||||
|
self.assertEqual(flavor['ram'], int(ram))
|
||||||
|
self.assertEqual(int(flavor['id']), new_flavor_id)
|
||||||
|
|
||||||
|
|
||||||
|
class FlavorsAdminTestXML(FlavorsAdminTestJSON):
|
||||||
|
_interface = 'xml'
|
342
tempest/api/compute/v3/admin/test_flavors_negative.py
Normal file
342
tempest/api/compute/v3/admin/test_flavors_negative.py
Normal file
@ -0,0 +1,342 @@
|
|||||||
|
# Copyright 2012 OpenStack Foundation
|
||||||
|
# All Rights Reserved.
|
||||||
|
#
|
||||||
|
# Licensed under the Apache License, Version 2.0 (the "License"); you may
|
||||||
|
# not use this file except in compliance with the License. You may obtain
|
||||||
|
# a copy of the License at
|
||||||
|
#
|
||||||
|
# http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
#
|
||||||
|
# Unless required by applicable law or agreed to in writing, software
|
||||||
|
# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
|
||||||
|
# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
|
||||||
|
# License for the specific language governing permissions and limitations
|
||||||
|
# under the License.
|
||||||
|
|
||||||
|
import uuid
|
||||||
|
|
||||||
|
from tempest.api.compute import base
|
||||||
|
from tempest.common.utils import data_utils
|
||||||
|
from tempest import exceptions
|
||||||
|
from tempest import test
|
||||||
|
|
||||||
|
|
||||||
|
class FlavorsAdminNegativeTestJSON(base.BaseV2ComputeAdminTest):
|
||||||
|
|
||||||
|
"""
|
||||||
|
Tests Flavors API Create and Delete that require admin privileges
|
||||||
|
"""
|
||||||
|
|
||||||
|
_interface = 'json'
|
||||||
|
|
||||||
|
@classmethod
|
||||||
|
def setUpClass(cls):
|
||||||
|
super(FlavorsAdminNegativeTestJSON, cls).setUpClass()
|
||||||
|
if not test.is_extension_enabled('FlavorExtraData', 'compute'):
|
||||||
|
msg = "FlavorExtraData extension not enabled."
|
||||||
|
raise cls.skipException(msg)
|
||||||
|
|
||||||
|
cls.client = cls.os_adm.flavors_client
|
||||||
|
cls.user_client = cls.os.flavors_client
|
||||||
|
cls.flavor_name_prefix = 'test_flavor_'
|
||||||
|
cls.ram = 512
|
||||||
|
cls.vcpus = 1
|
||||||
|
cls.disk = 10
|
||||||
|
cls.ephemeral = 10
|
||||||
|
cls.swap = 1024
|
||||||
|
cls.rxtx = 2
|
||||||
|
|
||||||
|
def flavor_clean_up(self, flavor_id):
|
||||||
|
resp, body = self.client.delete_flavor(flavor_id)
|
||||||
|
self.assertEqual(resp.status, 202)
|
||||||
|
self.client.wait_for_resource_deletion(flavor_id)
|
||||||
|
|
||||||
|
@test.attr(type=['negative', 'gate'])
|
||||||
|
def test_get_flavor_details_for_deleted_flavor(self):
|
||||||
|
# Delete a flavor and ensure it is not listed
|
||||||
|
# Create a test flavor
|
||||||
|
flavor_name = data_utils.rand_name(self.flavor_name_prefix)
|
||||||
|
|
||||||
|
# no need to specify flavor_id, we can get the flavor_id from a
|
||||||
|
# response of create_flavor() call.
|
||||||
|
resp, flavor = self.client.create_flavor(flavor_name,
|
||||||
|
self.ram,
|
||||||
|
self.vcpus, self.disk,
|
||||||
|
'',
|
||||||
|
ephemeral=self.ephemeral,
|
||||||
|
swap=self.swap,
|
||||||
|
rxtx=self.rxtx)
|
||||||
|
# Delete the flavor
|
||||||
|
new_flavor_id = flavor['id']
|
||||||
|
resp_delete, body = self.client.delete_flavor(new_flavor_id)
|
||||||
|
self.assertEqual(200, resp.status)
|
||||||
|
self.assertEqual(202, resp_delete.status)
|
||||||
|
|
||||||
|
# Deleted flavors can be seen via detailed GET
|
||||||
|
resp, flavor = self.client.get_flavor_details(new_flavor_id)
|
||||||
|
self.assertEqual(resp.status, 200)
|
||||||
|
self.assertEqual(flavor['name'], flavor_name)
|
||||||
|
|
||||||
|
# Deleted flavors should not show up in a list however
|
||||||
|
resp, flavors = self.client.list_flavors_with_detail()
|
||||||
|
self.assertEqual(resp.status, 200)
|
||||||
|
flag = True
|
||||||
|
for flavor in flavors:
|
||||||
|
if flavor['name'] == flavor_name:
|
||||||
|
flag = False
|
||||||
|
self.assertTrue(flag)
|
||||||
|
|
||||||
|
@test.attr(type=['negative', 'gate'])
|
||||||
|
def test_invalid_is_public_string(self):
|
||||||
|
# the 'is_public' parameter can be 'none/true/false' if it exists
|
||||||
|
self.assertRaises(exceptions.BadRequest,
|
||||||
|
self.client.list_flavors_with_detail,
|
||||||
|
{'is_public': 'invalid'})
|
||||||
|
|
||||||
|
@test.attr(type=['negative', 'gate'])
|
||||||
|
def test_create_flavor_as_user(self):
|
||||||
|
# only admin user can create a flavor
|
||||||
|
flavor_name = data_utils.rand_name(self.flavor_name_prefix)
|
||||||
|
new_flavor_id = str(uuid.uuid4())
|
||||||
|
|
||||||
|
self.assertRaises(exceptions.Unauthorized,
|
||||||
|
self.user_client.create_flavor,
|
||||||
|
flavor_name, self.ram, self.vcpus, self.disk,
|
||||||
|
new_flavor_id, ephemeral=self.ephemeral,
|
||||||
|
swap=self.swap, rxtx=self.rxtx)
|
||||||
|
|
||||||
|
@test.attr(type=['negative', 'gate'])
|
||||||
|
def test_delete_flavor_as_user(self):
|
||||||
|
# only admin user can delete a flavor
|
||||||
|
self.assertRaises(exceptions.Unauthorized,
|
||||||
|
self.user_client.delete_flavor,
|
||||||
|
self.flavor_ref_alt)
|
||||||
|
|
||||||
|
@test.attr(type=['negative', 'gate'])
|
||||||
|
def test_create_flavor_using_invalid_ram(self):
|
||||||
|
# the 'ram' attribute must be positive integer
|
||||||
|
flavor_name = data_utils.rand_name(self.flavor_name_prefix)
|
||||||
|
new_flavor_id = str(uuid.uuid4())
|
||||||
|
|
||||||
|
self.assertRaises(exceptions.BadRequest,
|
||||||
|
self.client.create_flavor,
|
||||||
|
flavor_name, -1, self.vcpus,
|
||||||
|
self.disk, new_flavor_id)
|
||||||
|
|
||||||
|
@test.attr(type=['negative', 'gate'])
|
||||||
|
def test_create_flavor_using_invalid_vcpus(self):
|
||||||
|
# the 'vcpu' attribute must be positive integer
|
||||||
|
flavor_name = data_utils.rand_name(self.flavor_name_prefix)
|
||||||
|
new_flavor_id = str(uuid.uuid4())
|
||||||
|
|
||||||
|
self.assertRaises(exceptions.BadRequest,
|
||||||
|
self.client.create_flavor,
|
||||||
|
flavor_name, self.ram, -1,
|
||||||
|
self.disk, new_flavor_id)
|
||||||
|
|
||||||
|
@test.attr(type=['negative', 'gate'])
|
||||||
|
def test_create_flavor_with_name_length_less_than_1(self):
|
||||||
|
# ensure name length >= 1
|
||||||
|
new_flavor_id = str(uuid.uuid4())
|
||||||
|
|
||||||
|
self.assertRaises(exceptions.BadRequest,
|
||||||
|
self.client.create_flavor,
|
||||||
|
'',
|
||||||
|
self.ram, self.vcpus,
|
||||||
|
self.disk,
|
||||||
|
new_flavor_id,
|
||||||
|
ephemeral=self.ephemeral,
|
||||||
|
swap=self.swap,
|
||||||
|
rxtx=self.rxtx,
|
||||||
|
is_public='False')
|
||||||
|
|
||||||
|
@test.attr(type=['negative', 'gate'])
|
||||||
|
def test_create_flavor_with_name_length_exceeds_255(self):
|
||||||
|
# ensure name do not exceed 255 characters
|
||||||
|
new_flavor_name = 'a' * 256
|
||||||
|
new_flavor_id = str(uuid.uuid4())
|
||||||
|
|
||||||
|
self.assertRaises(exceptions.BadRequest,
|
||||||
|
self.client.create_flavor,
|
||||||
|
new_flavor_name,
|
||||||
|
self.ram, self.vcpus,
|
||||||
|
self.disk,
|
||||||
|
new_flavor_id,
|
||||||
|
ephemeral=self.ephemeral,
|
||||||
|
swap=self.swap,
|
||||||
|
rxtx=self.rxtx,
|
||||||
|
is_public='False')
|
||||||
|
|
||||||
|
@test.attr(type=['negative', 'gate'])
|
||||||
|
def test_create_flavor_with_invalid_name(self):
|
||||||
|
# the regex of flavor_name is '^[\w\.\- ]*$'
|
||||||
|
invalid_flavor_name = data_utils.rand_name('invalid-!@#$%-')
|
||||||
|
new_flavor_id = str(uuid.uuid4())
|
||||||
|
|
||||||
|
self.assertRaises(exceptions.BadRequest,
|
||||||
|
self.client.create_flavor,
|
||||||
|
invalid_flavor_name,
|
||||||
|
self.ram, self.vcpus,
|
||||||
|
self.disk,
|
||||||
|
new_flavor_id,
|
||||||
|
ephemeral=self.ephemeral,
|
||||||
|
swap=self.swap,
|
||||||
|
rxtx=self.rxtx,
|
||||||
|
is_public='False')
|
||||||
|
|
||||||
|
@test.attr(type=['negative', 'gate'])
|
||||||
|
def test_create_flavor_with_invalid_flavor_id(self):
|
||||||
|
# the regex of flavor_id is '^[\w\.\- ]*$', and it cannot contain
|
||||||
|
# leading and/or trailing whitespace
|
||||||
|
new_flavor_name = data_utils.rand_name(self.flavor_name_prefix)
|
||||||
|
invalid_flavor_id = '!@#$%'
|
||||||
|
|
||||||
|
self.assertRaises(exceptions.BadRequest,
|
||||||
|
self.client.create_flavor,
|
||||||
|
new_flavor_name,
|
||||||
|
self.ram, self.vcpus,
|
||||||
|
self.disk,
|
||||||
|
invalid_flavor_id,
|
||||||
|
ephemeral=self.ephemeral,
|
||||||
|
swap=self.swap,
|
||||||
|
rxtx=self.rxtx,
|
||||||
|
is_public='False')
|
||||||
|
|
||||||
|
@test.attr(type=['negative', 'gate'])
|
||||||
|
def test_create_flavor_with_id_length_exceeds_255(self):
|
||||||
|
# the length of flavor_id should not exceed 255 characters
|
||||||
|
new_flavor_name = data_utils.rand_name(self.flavor_name_prefix)
|
||||||
|
invalid_flavor_id = 'a' * 256
|
||||||
|
|
||||||
|
self.assertRaises(exceptions.BadRequest,
|
||||||
|
self.client.create_flavor,
|
||||||
|
new_flavor_name,
|
||||||
|
self.ram, self.vcpus,
|
||||||
|
self.disk,
|
||||||
|
invalid_flavor_id,
|
||||||
|
ephemeral=self.ephemeral,
|
||||||
|
swap=self.swap,
|
||||||
|
rxtx=self.rxtx,
|
||||||
|
is_public='False')
|
||||||
|
|
||||||
|
@test.attr(type=['negative', 'gate'])
|
||||||
|
def test_create_flavor_with_invalid_root_gb(self):
|
||||||
|
# root_gb attribute should be non-negative ( >= 0) integer
|
||||||
|
new_flavor_name = data_utils.rand_name(self.flavor_name_prefix)
|
||||||
|
new_flavor_id = str(uuid.uuid4())
|
||||||
|
|
||||||
|
self.assertRaises(exceptions.BadRequest,
|
||||||
|
self.client.create_flavor,
|
||||||
|
new_flavor_name,
|
||||||
|
self.ram, self.vcpus,
|
||||||
|
-1,
|
||||||
|
new_flavor_id,
|
||||||
|
ephemeral=self.ephemeral,
|
||||||
|
swap=self.swap,
|
||||||
|
rxtx=self.rxtx,
|
||||||
|
is_public='False')
|
||||||
|
|
||||||
|
@test.attr(type=['negative', 'gate'])
|
||||||
|
def test_create_flavor_with_invalid_ephemeral_gb(self):
|
||||||
|
# ephemeral_gb attribute should be non-negative ( >= 0) integer
|
||||||
|
new_flavor_name = data_utils.rand_name(self.flavor_name_prefix)
|
||||||
|
new_flavor_id = str(uuid.uuid4())
|
||||||
|
|
||||||
|
self.assertRaises(exceptions.BadRequest,
|
||||||
|
self.client.create_flavor,
|
||||||
|
new_flavor_name,
|
||||||
|
self.ram, self.vcpus,
|
||||||
|
self.disk,
|
||||||
|
new_flavor_id,
|
||||||
|
ephemeral=-1,
|
||||||
|
swap=self.swap,
|
||||||
|
rxtx=self.rxtx,
|
||||||
|
is_public='False')
|
||||||
|
|
||||||
|
@test.attr(type=['negative', 'gate'])
|
||||||
|
def test_create_flavor_with_invalid_swap(self):
|
||||||
|
# swap attribute should be non-negative ( >= 0) integer
|
||||||
|
new_flavor_name = data_utils.rand_name(self.flavor_name_prefix)
|
||||||
|
new_flavor_id = str(uuid.uuid4())
|
||||||
|
|
||||||
|
self.assertRaises(exceptions.BadRequest,
|
||||||
|
self.client.create_flavor,
|
||||||
|
new_flavor_name,
|
||||||
|
self.ram, self.vcpus,
|
||||||
|
self.disk,
|
||||||
|
new_flavor_id,
|
||||||
|
ephemeral=self.ephemeral,
|
||||||
|
swap=-1,
|
||||||
|
rxtx=self.rxtx,
|
||||||
|
is_public='False')
|
||||||
|
|
||||||
|
@test.attr(type=['negative', 'gate'])
|
||||||
|
def test_create_flavor_with_invalid_rxtx_factor(self):
|
||||||
|
# rxtx_factor attribute should be a positive float
|
||||||
|
new_flavor_name = data_utils.rand_name(self.flavor_name_prefix)
|
||||||
|
new_flavor_id = str(uuid.uuid4())
|
||||||
|
|
||||||
|
self.assertRaises(exceptions.BadRequest,
|
||||||
|
self.client.create_flavor,
|
||||||
|
new_flavor_name,
|
||||||
|
self.ram, self.vcpus,
|
||||||
|
self.disk,
|
||||||
|
new_flavor_id,
|
||||||
|
ephemeral=self.ephemeral,
|
||||||
|
swap=self.swap,
|
||||||
|
rxtx=-1.5,
|
||||||
|
is_public='False')
|
||||||
|
|
||||||
|
@test.attr(type=['negative', 'gate'])
|
||||||
|
def test_create_flavor_with_invalid_is_public(self):
|
||||||
|
# is_public attribute should be boolean
|
||||||
|
new_flavor_name = data_utils.rand_name(self.flavor_name_prefix)
|
||||||
|
new_flavor_id = str(uuid.uuid4())
|
||||||
|
|
||||||
|
self.assertRaises(exceptions.BadRequest,
|
||||||
|
self.client.create_flavor,
|
||||||
|
new_flavor_name,
|
||||||
|
self.ram, self.vcpus,
|
||||||
|
self.disk,
|
||||||
|
new_flavor_id,
|
||||||
|
ephemeral=self.ephemeral,
|
||||||
|
swap=self.swap,
|
||||||
|
rxtx=self.rxtx,
|
||||||
|
is_public='Invalid')
|
||||||
|
|
||||||
|
@test.attr(type=['negative', 'gate'])
|
||||||
|
def test_create_flavor_already_exists(self):
|
||||||
|
flavor_name = data_utils.rand_name(self.flavor_name_prefix)
|
||||||
|
new_flavor_id = str(uuid.uuid4())
|
||||||
|
|
||||||
|
resp, flavor = self.client.create_flavor(flavor_name,
|
||||||
|
self.ram, self.vcpus,
|
||||||
|
self.disk,
|
||||||
|
new_flavor_id,
|
||||||
|
ephemeral=self.ephemeral,
|
||||||
|
swap=self.swap,
|
||||||
|
rxtx=self.rxtx)
|
||||||
|
self.assertEqual(200, resp.status)
|
||||||
|
self.addCleanup(self.flavor_clean_up, flavor['id'])
|
||||||
|
|
||||||
|
self.assertRaises(exceptions.Conflict,
|
||||||
|
self.client.create_flavor,
|
||||||
|
flavor_name,
|
||||||
|
self.ram, self.vcpus,
|
||||||
|
self.disk,
|
||||||
|
new_flavor_id,
|
||||||
|
ephemeral=self.ephemeral,
|
||||||
|
swap=self.swap,
|
||||||
|
rxtx=self.rxtx)
|
||||||
|
|
||||||
|
@test.attr(type=['negative', 'gate'])
|
||||||
|
def test_delete_nonexistent_flavor(self):
|
||||||
|
nonexistent_flavor_id = str(uuid.uuid4())
|
||||||
|
|
||||||
|
self.assertRaises(exceptions.NotFound,
|
||||||
|
self.client.delete_flavor,
|
||||||
|
nonexistent_flavor_id)
|
||||||
|
|
||||||
|
|
||||||
|
class FlavorsAdminNegativeTestXML(FlavorsAdminNegativeTestJSON):
|
||||||
|
_interface = 'xml'
|
0
tempest/api/compute/v3/flavors/__init__.py
Normal file
0
tempest/api/compute/v3/flavors/__init__.py
Normal file
132
tempest/api/compute/v3/flavors/test_flavors.py
Normal file
132
tempest/api/compute/v3/flavors/test_flavors.py
Normal file
@ -0,0 +1,132 @@
|
|||||||
|
# Copyright 2012 OpenStack Foundation
|
||||||
|
# All Rights Reserved.
|
||||||
|
#
|
||||||
|
# Licensed under the Apache License, Version 2.0 (the "License"); you may
|
||||||
|
# not use this file except in compliance with the License. You may obtain
|
||||||
|
# a copy of the License at
|
||||||
|
#
|
||||||
|
# http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
#
|
||||||
|
# Unless required by applicable law or agreed to in writing, software
|
||||||
|
# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
|
||||||
|
# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
|
||||||
|
# License for the specific language governing permissions and limitations
|
||||||
|
# under the License.
|
||||||
|
|
||||||
|
from tempest.api.compute import base
|
||||||
|
from tempest.test import attr
|
||||||
|
|
||||||
|
|
||||||
|
class FlavorsTestJSON(base.BaseV2ComputeTest):
|
||||||
|
_interface = 'json'
|
||||||
|
|
||||||
|
@classmethod
|
||||||
|
def setUpClass(cls):
|
||||||
|
super(FlavorsTestJSON, cls).setUpClass()
|
||||||
|
cls.client = cls.flavors_client
|
||||||
|
|
||||||
|
@attr(type='smoke')
|
||||||
|
def test_list_flavors(self):
|
||||||
|
# List of all flavors should contain the expected flavor
|
||||||
|
resp, flavors = self.client.list_flavors()
|
||||||
|
resp, flavor = self.client.get_flavor_details(self.flavor_ref)
|
||||||
|
flavor_min_detail = {'id': flavor['id'], 'links': flavor['links'],
|
||||||
|
'name': flavor['name']}
|
||||||
|
self.assertIn(flavor_min_detail, flavors)
|
||||||
|
|
||||||
|
@attr(type='smoke')
|
||||||
|
def test_list_flavors_with_detail(self):
|
||||||
|
# Detailed list of all flavors should contain the expected flavor
|
||||||
|
resp, flavors = self.client.list_flavors_with_detail()
|
||||||
|
resp, flavor = self.client.get_flavor_details(self.flavor_ref)
|
||||||
|
self.assertIn(flavor, flavors)
|
||||||
|
|
||||||
|
@attr(type='smoke')
|
||||||
|
def test_get_flavor(self):
|
||||||
|
# The expected flavor details should be returned
|
||||||
|
resp, flavor = self.client.get_flavor_details(self.flavor_ref)
|
||||||
|
self.assertEqual(self.flavor_ref, flavor['id'])
|
||||||
|
|
||||||
|
@attr(type='gate')
|
||||||
|
def test_list_flavors_limit_results(self):
|
||||||
|
# Only the expected number of flavors should be returned
|
||||||
|
params = {'limit': 1}
|
||||||
|
resp, flavors = self.client.list_flavors(params)
|
||||||
|
self.assertEqual(1, len(flavors))
|
||||||
|
|
||||||
|
@attr(type='gate')
|
||||||
|
def test_list_flavors_detailed_limit_results(self):
|
||||||
|
# Only the expected number of flavors (detailed) should be returned
|
||||||
|
params = {'limit': 1}
|
||||||
|
resp, flavors = self.client.list_flavors_with_detail(params)
|
||||||
|
self.assertEqual(1, len(flavors))
|
||||||
|
|
||||||
|
@attr(type='gate')
|
||||||
|
def test_list_flavors_using_marker(self):
|
||||||
|
# The list of flavors should start from the provided marker
|
||||||
|
resp, flavors = self.client.list_flavors()
|
||||||
|
flavor_id = flavors[0]['id']
|
||||||
|
|
||||||
|
params = {'marker': flavor_id}
|
||||||
|
resp, flavors = self.client.list_flavors(params)
|
||||||
|
self.assertFalse(any([i for i in flavors if i['id'] == flavor_id]),
|
||||||
|
'The list of flavors did not start after the marker.')
|
||||||
|
|
||||||
|
@attr(type='gate')
|
||||||
|
def test_list_flavors_detailed_using_marker(self):
|
||||||
|
# The list of flavors should start from the provided marker
|
||||||
|
resp, flavors = self.client.list_flavors_with_detail()
|
||||||
|
flavor_id = flavors[0]['id']
|
||||||
|
|
||||||
|
params = {'marker': flavor_id}
|
||||||
|
resp, flavors = self.client.list_flavors_with_detail(params)
|
||||||
|
self.assertFalse(any([i for i in flavors if i['id'] == flavor_id]),
|
||||||
|
'The list of flavors did not start after the marker.')
|
||||||
|
|
||||||
|
@attr(type='gate')
|
||||||
|
def test_list_flavors_detailed_filter_by_min_disk(self):
|
||||||
|
# The detailed list of flavors should be filtered by disk space
|
||||||
|
resp, flavors = self.client.list_flavors_with_detail()
|
||||||
|
flavors = sorted(flavors, key=lambda k: k['disk'])
|
||||||
|
flavor_id = flavors[0]['id']
|
||||||
|
|
||||||
|
params = {'minDisk': flavors[0]['disk'] + 1}
|
||||||
|
resp, flavors = self.client.list_flavors_with_detail(params)
|
||||||
|
self.assertFalse(any([i for i in flavors if i['id'] == flavor_id]))
|
||||||
|
|
||||||
|
@attr(type='gate')
|
||||||
|
def test_list_flavors_detailed_filter_by_min_ram(self):
|
||||||
|
# The detailed list of flavors should be filtered by RAM
|
||||||
|
resp, flavors = self.client.list_flavors_with_detail()
|
||||||
|
flavors = sorted(flavors, key=lambda k: k['ram'])
|
||||||
|
flavor_id = flavors[0]['id']
|
||||||
|
|
||||||
|
params = {'minRam': flavors[0]['ram'] + 1}
|
||||||
|
resp, flavors = self.client.list_flavors_with_detail(params)
|
||||||
|
self.assertFalse(any([i for i in flavors if i['id'] == flavor_id]))
|
||||||
|
|
||||||
|
@attr(type='gate')
|
||||||
|
def test_list_flavors_filter_by_min_disk(self):
|
||||||
|
# The list of flavors should be filtered by disk space
|
||||||
|
resp, flavors = self.client.list_flavors_with_detail()
|
||||||
|
flavors = sorted(flavors, key=lambda k: k['disk'])
|
||||||
|
flavor_id = flavors[0]['id']
|
||||||
|
|
||||||
|
params = {'minDisk': flavors[0]['disk'] + 1}
|
||||||
|
resp, flavors = self.client.list_flavors(params)
|
||||||
|
self.assertFalse(any([i for i in flavors if i['id'] == flavor_id]))
|
||||||
|
|
||||||
|
@attr(type='gate')
|
||||||
|
def test_list_flavors_filter_by_min_ram(self):
|
||||||
|
# The list of flavors should be filtered by RAM
|
||||||
|
resp, flavors = self.client.list_flavors_with_detail()
|
||||||
|
flavors = sorted(flavors, key=lambda k: k['ram'])
|
||||||
|
flavor_id = flavors[0]['id']
|
||||||
|
|
||||||
|
params = {'minRam': flavors[0]['ram'] + 1}
|
||||||
|
resp, flavors = self.client.list_flavors(params)
|
||||||
|
self.assertFalse(any([i for i in flavors if i['id'] == flavor_id]))
|
||||||
|
|
||||||
|
|
||||||
|
class FlavorsTestXML(FlavorsTestJSON):
|
||||||
|
_interface = 'xml'
|
54
tempest/api/compute/v3/flavors/test_flavors_negative.py
Normal file
54
tempest/api/compute/v3/flavors/test_flavors_negative.py
Normal file
@ -0,0 +1,54 @@
|
|||||||
|
# Copyright 2013 OpenStack Foundation
|
||||||
|
# All Rights Reserved.
|
||||||
|
#
|
||||||
|
# Licensed under the Apache License, Version 2.0 (the "License"); you may
|
||||||
|
# not use this file except in compliance with the License. You may obtain
|
||||||
|
# a copy of the License at
|
||||||
|
#
|
||||||
|
# http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
#
|
||||||
|
# Unless required by applicable law or agreed to in writing, software
|
||||||
|
# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
|
||||||
|
# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
|
||||||
|
# License for the specific language governing permissions and limitations
|
||||||
|
# under the License.
|
||||||
|
|
||||||
|
import testscenarios
|
||||||
|
|
||||||
|
from tempest.api.compute import base
|
||||||
|
from tempest import test
|
||||||
|
|
||||||
|
|
||||||
|
load_tests = testscenarios.load_tests_apply_scenarios
|
||||||
|
|
||||||
|
|
||||||
|
class FlavorsListNegativeTestJSON(base.BaseV2ComputeTest,
|
||||||
|
test.NegativeAutoTest):
|
||||||
|
_interface = 'json'
|
||||||
|
_service = 'compute'
|
||||||
|
_schema_file = 'compute/flavors/flavors_list.json'
|
||||||
|
|
||||||
|
scenarios = test.NegativeAutoTest.generate_scenario(_schema_file)
|
||||||
|
|
||||||
|
@test.attr(type=['negative', 'gate'])
|
||||||
|
def test_list_flavors_with_detail(self):
|
||||||
|
self.execute(self._schema_file)
|
||||||
|
|
||||||
|
|
||||||
|
class FlavorDetailsNegativeTestJSON(base.BaseV2ComputeTest,
|
||||||
|
test.NegativeAutoTest):
|
||||||
|
_interface = 'json'
|
||||||
|
_service = 'compute'
|
||||||
|
_schema_file = 'compute/flavors/flavor_details.json'
|
||||||
|
|
||||||
|
scenarios = test.NegativeAutoTest.generate_scenario(_schema_file)
|
||||||
|
|
||||||
|
@classmethod
|
||||||
|
def setUpClass(cls):
|
||||||
|
super(FlavorDetailsNegativeTestJSON, cls).setUpClass()
|
||||||
|
cls.set_resource("flavor", cls.flavor_ref)
|
||||||
|
|
||||||
|
@test.attr(type=['negative', 'gate'])
|
||||||
|
def test_get_flavor_details(self):
|
||||||
|
# flavor details are not returned for non-existent flavors
|
||||||
|
self.execute(self._schema_file)
|
42
tempest/api/compute/v3/servers/test_server_password.py
Normal file
42
tempest/api/compute/v3/servers/test_server_password.py
Normal file
@ -0,0 +1,42 @@
|
|||||||
|
# Copyright 2013 IBM Corporation
|
||||||
|
# All Rights Reserved.
|
||||||
|
#
|
||||||
|
# Licensed under the Apache License, Version 2.0 (the "License"); you may
|
||||||
|
# not use this file except in compliance with the License. You may obtain
|
||||||
|
# a copy of the License at
|
||||||
|
#
|
||||||
|
# http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
#
|
||||||
|
# Unless required by applicable law or agreed to in writing, software
|
||||||
|
# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
|
||||||
|
# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
|
||||||
|
# License for the specific language governing permissions and limitations
|
||||||
|
# under the License.
|
||||||
|
|
||||||
|
|
||||||
|
from tempest.api.compute import base
|
||||||
|
from tempest.test import attr
|
||||||
|
|
||||||
|
|
||||||
|
class ServerPasswordTestJSON(base.BaseV2ComputeTest):
|
||||||
|
_interface = 'json'
|
||||||
|
|
||||||
|
@classmethod
|
||||||
|
def setUpClass(cls):
|
||||||
|
super(ServerPasswordTestJSON, cls).setUpClass()
|
||||||
|
cls.client = cls.servers_client
|
||||||
|
resp, cls.server = cls.create_test_server(wait_until="ACTIVE")
|
||||||
|
|
||||||
|
@attr(type='gate')
|
||||||
|
def test_get_server_password(self):
|
||||||
|
resp, body = self.client.get_password(self.server['id'])
|
||||||
|
self.assertEqual(200, resp.status)
|
||||||
|
|
||||||
|
@attr(type='gate')
|
||||||
|
def test_delete_server_password(self):
|
||||||
|
resp, body = self.client.delete_password(self.server['id'])
|
||||||
|
self.assertEqual(204, resp.status)
|
||||||
|
|
||||||
|
|
||||||
|
class ServerPasswordTestXML(ServerPasswordTestJSON):
|
||||||
|
_interface = 'xml'
|
Loading…
Reference in New Issue
Block a user