Merge "Adding compute server tests"
diff --git a/patrole_tempest_plugin/tests/api/compute/test_agents_rbac.py b/patrole_tempest_plugin/tests/api/compute/test_agents_rbac.py
index e2122c4..0de5e47 100644
--- a/patrole_tempest_plugin/tests/api/compute/test_agents_rbac.py
+++ b/patrole_tempest_plugin/tests/api/compute/test_agents_rbac.py
@@ -14,6 +14,8 @@
# under the License.
from tempest import config
+from tempest import test
+
from tempest.lib import decorators
from patrole_tempest_plugin import rbac_rule_validation
@@ -27,7 +29,7 @@
@classmethod
def skip_checks(cls):
super(AgentsRbacTest, cls).skip_checks()
- if not CONF.compute_feature_enabled.api_extensions:
+ if not test.is_extension_enabled('os-agents', 'compute'):
raise cls.skipException(
'%s skipped as no compute extensions enabled' % cls.__name__)
@@ -37,3 +39,16 @@
def test_list_agents_rbac(self):
self.rbac_utils.switch_role(self, switchToRbacRole=True)
self.agents_client.list_agents()
+
+ @rbac_rule_validation.action(
+ service="nova",
+ rule="os_compute_api:os-agents")
+ @decorators.idempotent_id('77d6cae4-1ced-47f7-af2e-3d6a45958fd6')
+ def test_create_agent(self):
+ params = {'hypervisor': 'kvm', 'os': 'win', 'architecture': 'x86',
+ 'version': '7.0', 'url': 'xxx://xxxx/xxx/xxx',
+ 'md5hash': 'add6bb58e139be103324d04d82d8f545'}
+ self.rbac_utils.switch_role(self, switchToRbacRole=True)
+ body = self.agents_client.create_agent(**params)['agent']
+ self.addCleanup(self.agents_client.delete_agent,
+ body['agent_id'])
diff --git a/patrole_tempest_plugin/tests/api/compute/test_server_migrations_rbac.py b/patrole_tempest_plugin/tests/api/compute/test_server_migrations_rbac.py
new file mode 100644
index 0000000..39afb4a
--- /dev/null
+++ b/patrole_tempest_plugin/tests/api/compute/test_server_migrations_rbac.py
@@ -0,0 +1,105 @@
+# Copyright 2017 AT&T 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.
+
+import testtools
+
+from tempest.common import waiters
+from tempest import config
+
+from tempest.lib import decorators
+
+from patrole_tempest_plugin import rbac_rule_validation
+from patrole_tempest_plugin.tests.api.compute import rbac_base as base
+
+CONF = config.CONF
+
+
+class MigrateServerRbacTest(base.BaseV2ComputeRbacTest):
+
+ @classmethod
+ def setup_clients(cls):
+ super(MigrateServerRbacTest, cls).setup_clients()
+ cls.client = cls.servers_client
+ cls.admin_servers_client = cls.os_adm.servers_client
+ cls.hosts_client = cls.os.hosts_client
+
+ def _get_server_details(self, server_id):
+ body = self.client.show_server(server_id)['server']
+ return body
+
+ def _get_host_for_server(self, server_id):
+ return self._get_server_details(server_id)['OS-EXT-SRV-ATTR:host']
+
+ def _get_host_other_than(self, host):
+ for target_host in self._get_compute_hostnames():
+ if host != target_host:
+ return target_host
+
+ def _get_compute_hostnames(self):
+ body = self.hosts_client.list_hosts()['hosts']
+ return [
+ host_record['host_name']
+ for host_record in body
+ if host_record['service'] == 'compute'
+ ]
+
+ def _migrate_server_to(self, server_id, dest_host, volume_backed=False):
+ kwargs = dict()
+ block_migration = getattr(self, 'block_migration', None)
+ if self.block_migration is None:
+ kwargs['disk_over_commit'] = False
+ block_migration = (CONF.compute_feature_enabled.
+ block_migration_for_live_migration and
+ not volume_backed)
+ self.client.live_migrate_server(
+ server_id, host=dest_host, block_migration=block_migration,
+ **kwargs)
+
+ @testtools.skipUnless(CONF.compute_feature_enabled.cold_migration,
+ 'Cold migration not available.')
+ @rbac_rule_validation.action(
+ service="nova",
+ rule="os_compute_api:os-migrate-server:migrate")
+ @decorators.idempotent_id('c6f1607c-9fed-4c00-807e-9ba675b98b1b')
+ def test_cold_migration(self):
+ if CONF.compute.min_compute_nodes < 2:
+ msg = "Less than 2 compute nodes, skipping multinode tests."
+ raise self.skipException(msg)
+
+ server = self.create_test_server(wait_until="ACTIVE")
+ self.rbac_utils.switch_role(self, switchToRbacRole=True)
+ self.client.migrate_server(server['id'])
+ waiters.wait_for_server_status(self.admin_servers_client,
+ server['id'], 'VERIFY_RESIZE')
+
+ @testtools.skipUnless(CONF.compute_feature_enabled.live_migration,
+ 'Live migration feature is not enabled.')
+ @rbac_rule_validation.action(
+ service="nova",
+ rule="os_compute_api:os-migrate-server:migrate_live")
+ @decorators.idempotent_id('33520834-72c8-4edb-a189-a2e0fc9eb0d3')
+ def test_migration_live(self):
+ if CONF.compute.min_compute_nodes < 2:
+ msg = "Less than 2 compute nodes, skipping multinode tests."
+ raise self.skipException(msg)
+
+ server_id = self.create_test_server(wait_until="ACTIVE",
+ volume_backed=False)['id']
+ actual_host = self._get_host_for_server(server_id)
+ target_host = self._get_host_other_than(actual_host)
+ self.rbac_utils.switch_role(self, switchToRbacRole=True)
+ self._migrate_server_to(server_id, target_host, volume_backed=False)
+ waiters.wait_for_server_status(self.admin_servers_client,
+ server_id, "ACTIVE")
diff --git a/patrole_tempest_plugin/tests/api/compute/test_server_password_rbac.py b/patrole_tempest_plugin/tests/api/compute/test_server_password_rbac.py
index 849a19a..5f90c97 100644
--- a/patrole_tempest_plugin/tests/api/compute/test_server_password_rbac.py
+++ b/patrole_tempest_plugin/tests/api/compute/test_server_password_rbac.py
@@ -44,6 +44,14 @@
@rbac_rule_validation.action(
service="nova",
rule="os_compute_api:os-server-password")
- def test_delete_password(self):
+ def test_delete_server_password(self):
self.rbac_utils.switch_role(self, switchToRbacRole=True)
self.client.delete_password(self.server['id'])
+
+ @rbac_rule_validation.action(
+ service="nova",
+ rule="os_compute_api:os-server-password")
+ @decorators.idempotent_id('f677971a-7d20-493c-977f-6ff0a74b5b2c')
+ def test_get_server_password(self):
+ self.rbac_utils.switch_role(self, switchToRbacRole=True)
+ self.client.show_password(self.server['id'])
diff --git a/patrole_tempest_plugin/tests/api/compute/test_server_rbac.py b/patrole_tempest_plugin/tests/api/compute/test_server_rbac.py
new file mode 100644
index 0000000..66676d1
--- /dev/null
+++ b/patrole_tempest_plugin/tests/api/compute/test_server_rbac.py
@@ -0,0 +1,70 @@
+# Copyright 2017 AT&T 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 oslo_log import log
+
+from tempest.common import waiters
+
+from tempest.lib.common.utils import data_utils
+from tempest.lib import decorators
+from tempest.lib import exceptions
+
+from patrole_tempest_plugin import rbac_exceptions
+from patrole_tempest_plugin import rbac_rule_validation
+from patrole_tempest_plugin.tests.api.compute import rbac_base as base
+
+LOG = log.getLogger(__name__)
+
+
+class ComputeServersRbacTest(base.BaseV2ComputeRbacTest):
+
+ @classmethod
+ def setup_clients(cls):
+ super(ComputeServersRbacTest, cls).setup_clients()
+ cls.client = cls.servers_client
+
+ @rbac_rule_validation.action(
+ service="nova",
+ rule="os_compute_api:servers:create")
+ @decorators.idempotent_id('4f34c73a-6ddc-4677-976f-71320fa855bd')
+ def test_create_server(self):
+ self.rbac_utils.switch_role(self, switchToRbacRole=True)
+ self.create_test_server(wait_until='ACTIVE')
+
+ @rbac_rule_validation.action(
+ service="nova",
+ rule="os_compute_api:servers:delete")
+ @decorators.idempotent_id('062e3440-e873-4b41-9317-bf6d8be50c12')
+ def test_delete_server(self):
+ server = self.create_test_server(wait_until='ACTIVE')
+ self.rbac_utils.switch_role(self, switchToRbacRole=True)
+ self.client.delete_server(server['id'])
+ waiters.wait_for_server_termination(self.client, server['id'])
+
+ @rbac_rule_validation.action(
+ service="nova",
+ rule="os_compute_api:servers:update")
+ @decorators.idempotent_id('077b17cb-5621-43b9-8adf-5725f0d7a863')
+ def test_update_server(self):
+ server = self.create_test_server(wait_until='ACTIVE')
+ new_name = data_utils.rand_name('server')
+ self.rbac_utils.switch_role(self, switchToRbacRole=True)
+ try:
+ self.client.update_server(server['id'], name=new_name)
+ except exceptions.ServerFault as e:
+ # Some other policy may have blocked it.
+ LOG.info("ServerFault exception caught. Some other policy "
+ "blocked updating of server")
+ raise rbac_exceptions.RbacActionFailed(e)
diff --git a/patrole_tempest_plugin/tests/api/compute/test_server_virtual_interfaces_rbac.py b/patrole_tempest_plugin/tests/api/compute/test_server_virtual_interfaces_rbac.py
new file mode 100644
index 0000000..c523e84
--- /dev/null
+++ b/patrole_tempest_plugin/tests/api/compute/test_server_virtual_interfaces_rbac.py
@@ -0,0 +1,51 @@
+# Copyright 2017 AT&T 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 import config
+
+from tempest.lib import decorators
+from tempest.lib import exceptions
+
+from patrole_tempest_plugin import rbac_exceptions
+from patrole_tempest_plugin import rbac_rule_validation
+from patrole_tempest_plugin.tests.api.compute import rbac_base as base
+
+CONF = config.CONF
+
+
+class ServerVirtualInterfacesRbacTest(base.BaseV2ComputeRbacTest):
+
+ @classmethod
+ def setup_clients(cls):
+ super(ServerVirtualInterfacesRbacTest, cls).setup_clients()
+ cls.client = cls.servers_client
+
+ @rbac_rule_validation.action(
+ service="nova",
+ rule="os_compute_api:os-virtual-interfaces")
+ @decorators.idempotent_id('fc719ae3-0f73-4689-8378-1b841f0f2818')
+ def test_list_virtual_interfaces(self):
+ server = self.create_test_server(wait_until='ACTIVE')
+ self.rbac_utils.switch_role(self, switchToRbacRole=True)
+ try:
+ self.client.list_virtual_interfaces(server['id'])
+ except exceptions.ServerFault as e:
+ raise rbac_exceptions.RbacActionFailed(e)
+ except exceptions.BadRequest as e:
+ msg = "Listing virtual interfaces is not supported by this cloud."
+ if msg == str(e.resp_body['message']):
+ raise self.skipException(msg)
+ else:
+ raise e