diff --git a/fuel_health/heatmanager.py b/fuel_health/heatmanager.py index d93413c6..7e32f984 100644 --- a/fuel_health/heatmanager.py +++ b/fuel_health/heatmanager.py @@ -22,6 +22,7 @@ import heatclient.v1.client from fuel_health.common.utils.data_utils import rand_name from fuel_health import config +from fuel_health import exceptions import fuel_health.nmanager import fuel_health.test @@ -98,12 +99,22 @@ class HeatBaseTest(fuel_health.nmanager.OfficialClientTest): @classmethod def setUpClass(cls): super(HeatBaseTest, cls).setUpClass() + cls.heat_service_available = False + for service in cls.identity_client.services.list(): + if service.name == 'heat': + cls.heat_service_available = True + break + cls.stacks = [] cls.flavor = None - cls.wait_interval = cls.config.compute.build_interval cls.wait_timeout = cls.config.compute.build_timeout + def setUp(self): + super(HeatBaseTest, self).setUp() + if not self.heat_service_available: + self.fail('Heat is unavailable.') + @classmethod def tearDownClass(cls): cls.clean_stacks() diff --git a/fuel_health/tests/heat/__init__.py b/fuel_health/tests/heat/__init__.py new file mode 100644 index 00000000..30a94d00 --- /dev/null +++ b/fuel_health/tests/heat/__init__.py @@ -0,0 +1,15 @@ +# vim: tabstop=4 shiftwidth=4 softtabstop=4 + +# Copyright 2013 Mirantis, Inc. +# +# 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. diff --git a/fuel_health/tests/smoke/test_heat_actions.py b/fuel_health/tests/heat/test_heat_actions.py similarity index 59% rename from fuel_health/tests/smoke/test_heat_actions.py rename to fuel_health/tests/heat/test_heat_actions.py index bba8fea6..8ceaa186 100644 --- a/fuel_health/tests/smoke/test_heat_actions.py +++ b/fuel_health/tests/heat/test_heat_actions.py @@ -23,22 +23,26 @@ from fuel_health import heatmanager LOG = logging.getLogger(__name__) -class HeatTest(heatmanager.HeatBaseTest): - """Test class contains tests that check typical stack-related actions. +class TestStackAction(heatmanager.HeatBaseTest): + """ + Test class verifies that stack can be created, updated and deleted. Special requirements: 1. Heat component should be installed. """ @attr(type=["fuel", "smoke"]) - def test_manipulate_stack(self): - """Check typical stack-related actions + def test_stack(self): + """Create stack, check its details, then update and delete stack. Target component: Heat Scenario: 1. Create stack. - 2. Get details of the created stack by its name. - 3. Update stack. - 4. Delete stack. + 2. Wait for stack status to become 'CREATE_COMPLETE'. + 3. Get details of the created stack by its name. + 4. Update stack. + 5. Wait for stack to be updated. + 6. Delete stack. + 7. Wait for stack to be deleted. Duration: 60 s. """ @@ -49,42 +53,50 @@ class HeatTest(heatmanager.HeatBaseTest): "stack creation", self.heat_client) - self.verify(100, self.wait_for_stack_status, 1, + self.verify(100, self.wait_for_stack_status, 2, fail_msg, "stack status becoming 'CREATE_COMPLETE'", stack.id, 'CREATE_COMPLETE') # get stack details - stack_details = self.verify(20, self.heat_client.stacks.get, 2, - "Cannot retrieve stack details.", - "retrieving stack details", - stack.stack_name) + details = self.verify(20, self.heat_client.stacks.get, 3, + "Cannot retrieve stack details.", + "retrieving stack details", + stack.stack_name) + + fail_msg = "Stack details contain incorrect values." + self.verify_response_body_content( + details.id, stack.id, + fail_msg, 3) self.verify_response_body_content( - stack_details.id, - stack.id, - "Stack details contain incorrect values.", 2) + self.config.compute.image_name, details.parameters['ImageId'], + fail_msg, 3) + + self.verify_response_body_content( + details.stack_status, 'CREATE_COMPLETE', + fail_msg, 3) # update stack fail_msg = "Cannot update stack." - stack = self.verify(20, self.update_stack, 3, + stack = self.verify(20, self.update_stack, 4, fail_msg, "updating stack.", self.heat_client, stack.id) - self.verify(100, self.wait_for_stack_status, 3, + self.verify(100, self.wait_for_stack_status, 5, fail_msg, "stack status becoming 'UPDATE_COMPLETE'", stack.id, 'UPDATE_COMPLETE') # delete stack fail_msg = "Cannot delete stack." - self.verify(20, self.heat_client.stacks.delete, 4, + self.verify(20, self.heat_client.stacks.delete, 6, fail_msg, "volume deletion", stack.id) - self.verify(100, self.wait_for_stack_deleted, 4, + self.verify(100, self.wait_for_stack_deleted, 7, fail_msg, "deleting stack", stack.id) diff --git a/setup.py b/setup.py index fd59ecb8..14678dc2 100644 --- a/setup.py +++ b/setup.py @@ -22,6 +22,7 @@ fuel_health_reqs = [ 'python-glanceclient>=0.9.0', 'python-keystoneclient>=0.3.1', 'python-novaclient>=2.13.0', + 'python-heatclient==0.2.2', 'paramiko>=1.10.1', 'requests>=1.2.3', 'unittest2>=0.5.1',