Merge "Added missing xml tests of volume"
diff --git a/.testr.conf b/.testr.conf
index 510f4c9..05b12c4 100644
--- a/.testr.conf
+++ b/.testr.conf
@@ -1,7 +1,7 @@
 [DEFAULT]
 test_command=OS_STDOUT_CAPTURE=${OS_STDOUT_CAPTURE:-1} \
              OS_STDERR_CAPTURE=${OS_STDERR_CAPTURE:-1} \
-             OS_TEST_TIMEOUT=${OS_TEST_TIMEOUT:-250} \
+             OS_TEST_TIMEOUT=${OS_TEST_TIMEOUT:-500} \
              ${PYTHON:-python} -m subunit.run discover -t ./ ./tempest $LISTOPT $IDOPTION
 test_id_option=--load-list $IDFILE
 test_list_option=--list
diff --git a/HACKING.rst b/HACKING.rst
index 1eb2d4f..03e7dc3 100644
--- a/HACKING.rst
+++ b/HACKING.rst
@@ -68,16 +68,34 @@
  the ``self.fail`` line as the origin of the error.
 
 Avoid constructing complex boolean expressions for assertion.
-The ``self.assertTrue`` or ``self.assertFalse`` will just tell you the
-single boolean, and you will not know anything about the values used in
-the formula. Most other assert method can include more information.
+The ``self.assertTrue`` or ``self.assertFalse`` without a ``msg`` argument,
+will just tell you the single boolean value, and you will not know anything
+about the values used in the formula, the ``msg`` argument might be good enough
+for providing more information.
+
+Most other assert method can include more information by default.
 For example ``self.assertIn`` can include the whole set.
 
+Recommended to use testtools matcher for more tricky assertion.
+`[doc] <http://testtools.readthedocs.org/en/latest/for-test-authors.html#matchers>`_
+
+You can implement your own specific matcher as well.
+`[doc] <http://testtools.readthedocs.org/en/latest/for-test-authors.html#writing-your-own-matchers>`_
+
 If the test case fails you can see the related logs and the information
 carried by the exception (exception class, backtrack and exception info).
 This and the service logs are your only guide to find the root cause of flaky
 issue.
 
+Test cases are independent
+--------------------------
+Every ``test_method`` must be callable individually and MUST NOT depends on,
+any other ``test_method`` or ``test_method`` ordering.
+
+Test cases MAY depend on commonly initialized resources/facilities, like
+credentials management, testresources and so on. These facilities, MUST be able
+to work even if just one ``test_method`` selected for execution.
+
 Guidelines
 ----------
 - Do not submit changesets with only testcases which are skipped as
diff --git a/run_tests.sh b/run_tests.sh
index 856ce54..d672b62 100755
--- a/run_tests.sh
+++ b/run_tests.sh
@@ -124,7 +124,11 @@
 }
 
 function run_pep8 {
-  echo "Running pep8 ..."
+  echo "Running flake8 ..."
+  if [ $never_venv -eq 1 ]; then
+      echo "**WARNING**:" >&2
+      echo "Running flake8 without virtual env may miss OpenStack HACKING detection" >&2
+  fi
   ${wrapper} flake8
 }
 
diff --git a/tempest/api/compute/admin/test_flavors.py b/tempest/api/compute/admin/test_flavors.py
index 5f31084..7efd3c1 100644
--- a/tempest/api/compute/admin/test_flavors.py
+++ b/tempest/api/compute/admin/test_flavors.py
@@ -296,6 +296,24 @@
         _test_string_variations(['t', 'true', 'yes', '1'],
                                 flavor_name_public)
 
+    @attr(type='gate')
+    def test_create_flavor_using_string_ram(self):
+        flavor_name = rand_name(self.flavor_name_prefix)
+        new_flavor_id = 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)
+
     @attr(type=['negative', 'gate'])
     def test_invalid_is_public_string(self):
         self.assertRaises(exceptions.BadRequest,
@@ -319,6 +337,26 @@
                           self.user_client.delete_flavor,
                           self.flavor_ref_alt)
 
+    @attr(type=['negative', 'gate'])
+    def test_create_flavor_using_invalid_ram(self):
+        flavor_name = rand_name(self.flavor_name_prefix)
+        new_flavor_id = rand_int_id(start=1000)
+
+        self.assertRaises(exceptions.BadRequest,
+                          self.client.create_flavor,
+                          flavor_name, -1, self.vcpus,
+                          self.disk, new_flavor_id)
+
+    @attr(type=['negative', 'gate'])
+    def test_create_flavor_using_invalid_vcpus(self):
+        flavor_name = rand_name(self.flavor_name_prefix)
+        new_flavor_id = rand_int_id(start=1000)
+
+        self.assertRaises(exceptions.BadRequest,
+                          self.client.create_flavor,
+                          flavor_name, self.ram, 0,
+                          self.disk, new_flavor_id)
+
 
 class FlavorsAdminTestXML(FlavorsAdminTestJSON):
     _interface = 'xml'
diff --git a/tempest/api/compute/admin/test_flavors_extra_specs.py b/tempest/api/compute/admin/test_flavors_extra_specs.py
index 7b79a12..f2f82b5 100644
--- a/tempest/api/compute/admin/test_flavors_extra_specs.py
+++ b/tempest/api/compute/admin/test_flavors_extra_specs.py
@@ -58,6 +58,7 @@
     @classmethod
     def tearDownClass(cls):
         resp, body = cls.client.delete_flavor(cls.flavor['id'])
+        cls.client.wait_for_resource_deletion(cls.flavor['id'])
         super(FlavorsExtraSpecsTestJSON, cls).tearDownClass()
 
     @attr(type='gate')
diff --git a/tempest/api/compute/images/test_images_oneserver.py b/tempest/api/compute/images/test_images_oneserver.py
index 0052a30..06e9ab2 100644
--- a/tempest/api/compute/images/test_images_oneserver.py
+++ b/tempest/api/compute/images/test_images_oneserver.py
@@ -64,7 +64,7 @@
                 cls.alt_manager = clients.AltManager()
             cls.alt_client = cls.alt_manager.images_client
 
-    @testtools.skip("Until Bug #1006725 is fixed")
+    @testtools.skip("Skipped until the Bug #1006725 is resolved.")
     @attr(type=['negative', 'gate'])
     def test_create_image_specify_multibyte_character_image_name(self):
         # Return an error if the image name has multi-byte characters
diff --git a/tempest/api/compute/keypairs/test_keypairs.py b/tempest/api/compute/keypairs/test_keypairs.py
index 4848cce..083fbd7 100644
--- a/tempest/api/compute/keypairs/test_keypairs.py
+++ b/tempest/api/compute/keypairs/test_keypairs.py
@@ -84,9 +84,9 @@
         # Keypair should be created, Got details by name and deleted
         k_name = rand_name('keypair-')
         resp, keypair = self.client.create_keypair(k_name)
+        self.addCleanup(self.client.delete_keypair, k_name)
         resp, keypair_detail = self.client.get_keypair(k_name)
         self.assertEqual(200, resp.status)
-        self.addCleanup(self.client.delete_keypair, k_name)
         self.assertIn('name', keypair_detail)
         self.assertIn('public_key', keypair_detail)
         self.assertEqual(keypair_detail['name'], k_name,
diff --git a/tempest/api/compute/servers/test_list_server_filters.py b/tempest/api/compute/servers/test_list_server_filters.py
index ade7604..8d31598 100644
--- a/tempest/api/compute/servers/test_list_server_filters.py
+++ b/tempest/api/compute/servers/test_list_server_filters.py
@@ -205,7 +205,7 @@
         self.assertNotIn(self.s2_name, map(lambda x: x['name'], servers))
         self.assertNotIn(self.s3_name, map(lambda x: x['name'], servers))
 
-    @testtools.skip('Until Bug #1170718 is resolved.')
+    @testtools.skip('Skipped until the Bug #1170718 is resolved.')
     @attr(type='gate')
     def test_list_servers_filtered_by_ip(self):
         # Filter servers by ip
diff --git a/tempest/api/compute/servers/test_server_actions.py b/tempest/api/compute/servers/test_server_actions.py
index 25df6e6..76ef461 100644
--- a/tempest/api/compute/servers/test_server_actions.py
+++ b/tempest/api/compute/servers/test_server_actions.py
@@ -86,7 +86,7 @@
             new_boot_time = linux_client.get_boot_time()
             self.assertGreater(new_boot_time, boot_time)
 
-    @testtools.skip('Until Bug #1014647 is dealt with.')
+    @testtools.skip('Skipped until the Bug #1014647 is resolved.')
     @attr(type='smoke')
     def test_reboot_server_soft(self):
         # The server should be signaled to reboot gracefully
@@ -238,7 +238,7 @@
                           self.servers_client.get_console_output,
                           '!@#$%^&*()', 10)
 
-    @testtools.skip('Until tempest Bug #1014683 is fixed.')
+    @testtools.skip('Skipped until the Bug #1014683 is resolved.')
     @attr(type='gate')
     def test_get_console_output_server_id_in_reboot_status(self):
         # Positive test:Should be able to GET the console output
diff --git a/tempest/api/compute/servers/test_virtual_interfaces.py b/tempest/api/compute/servers/test_virtual_interfaces.py
index e5ea30e..b743a85 100644
--- a/tempest/api/compute/servers/test_virtual_interfaces.py
+++ b/tempest/api/compute/servers/test_virtual_interfaces.py
@@ -37,8 +37,8 @@
         resp, server = cls.create_server(wait_until='ACTIVE')
         cls.server_id = server['id']
 
-    @testtools.skipIf(CONF.service_available.neutron, "This feature is not " +
-                      "implemented by Neutron. See bug: #1183436")
+    @testtools.skipIf(CONF.service_available.neutron, "Not implemented by " +
+                      "Neutron. Skipped until the Bug #1183436 is resolved.")
     @attr(type='gate')
     def test_list_virtual_interfaces(self):
         # Positive test:Should be able to GET the virtual interfaces list
diff --git a/tempest/api/network/test_networks.py b/tempest/api/network/test_networks.py
index 7f49452..f3d1485 100644
--- a/tempest/api/network/test_networks.py
+++ b/tempest/api/network/test_networks.py
@@ -75,7 +75,7 @@
         for n in created_networks:
             self.assertNotIn(n['id'], networks_list)
 
-    @attr(type='gate')
+    @attr(type='smoke')
     def test_create_update_delete_network_subnet(self):
         # Creates a network
         name = rand_name('network-')
@@ -116,7 +116,7 @@
         resp, body = self.client.delete_network(net_id)
         self.assertEqual('204', resp['status'])
 
-    @attr(type='gate')
+    @attr(type='smoke')
     def test_show_network(self):
         # Verifies the details of a network
         resp, body = self.client.show_network(self.network['id'])
@@ -125,7 +125,7 @@
         self.assertEqual(self.network['id'], network['id'])
         self.assertEqual(self.name, network['name'])
 
-    @attr(type='gate')
+    @attr(type='smoke')
     def test_list_networks(self):
         # Verify the network exists in the list of all networks
         resp, body = self.client.list_networks()
@@ -138,7 +138,7 @@
         msg = "Network list doesn't contain created network"
         self.assertIsNotNone(found, msg)
 
-    @attr(type='gate')
+    @attr(type='smoke')
     def test_show_subnet(self):
         # Verifies the details of a subnet
         resp, body = self.client.show_subnet(self.subnet['id'])
@@ -147,7 +147,7 @@
         self.assertEqual(self.subnet['id'], subnet['id'])
         self.assertEqual(self.cidr, subnet['cidr'])
 
-    @attr(type='gate')
+    @attr(type='smoke')
     def test_list_subnets(self):
         # Verify the subnet exists in the list of all subnets
         resp, body = self.client.list_subnets()
@@ -160,7 +160,7 @@
         msg = "Subnet list doesn't contain created subnet"
         self.assertIsNotNone(found, msg)
 
-    @attr(type='gate')
+    @attr(type='smoke')
     def test_create_update_delete_port(self):
         # Verify that successful port creation, update & deletion
         resp, body = self.client.create_port(self.network['id'])
@@ -176,7 +176,7 @@
         resp, body = self.client.delete_port(port['id'])
         self.assertEqual('204', resp['status'])
 
-    @attr(type='gate')
+    @attr(type='smoke')
     def test_show_port(self):
         # Verify the details of port
         resp, body = self.client.show_port(self.port['id'])
@@ -184,7 +184,7 @@
         port = body['port']
         self.assertEqual(self.port['id'], port['id'])
 
-    @attr(type='gate')
+    @attr(type='smoke')
     def test_list_ports(self):
         # Verify the port exists in the list of all ports
         resp, body = self.client.list_ports()
@@ -196,19 +196,19 @@
                 found = n['id']
         self.assertIsNotNone(found, "Port list doesn't contain created port")
 
-    @attr(type=['negative', 'gate'])
+    @attr(type=['negative', 'smoke'])
     def test_show_non_existent_network(self):
         non_exist_id = rand_name('network')
         self.assertRaises(exceptions.NotFound, self.client.show_network,
                           non_exist_id)
 
-    @attr(type=['negative', 'gate'])
+    @attr(type=['negative', 'smoke'])
     def test_show_non_existent_subnet(self):
         non_exist_id = rand_name('subnet')
         self.assertRaises(exceptions.NotFound, self.client.show_subnet,
                           non_exist_id)
 
-    @attr(type='gate')
+    @attr(type='smoke')
     def test_bulk_create_delete_network(self):
         # Creates 2 networks in one request
         network_names = [rand_name('network-'), rand_name('network-')]
diff --git a/tempest/api/network/test_routers.py b/tempest/api/network/test_routers.py
index 4f687b0..9f8c742 100644
--- a/tempest/api/network/test_routers.py
+++ b/tempest/api/network/test_routers.py
@@ -49,7 +49,7 @@
             router_id, port_id)
         self.assertEqual('200', resp['status'])
 
-    @attr(type='gate')
+    @attr(type='smoke')
     def test_create_show_list_update_delete_router(self):
         # Create a router
         name = rand_name('router-')
@@ -90,7 +90,7 @@
             create_body['router']['id'])
         self.assertEqual(show_body['router']['name'], updated_name)
 
-    @attr(type='gate')
+    @attr(type='smoke')
     def test_add_remove_router_interface_with_subnet_id(self):
         network = self.create_network()
         subnet = self.create_subnet(network)
@@ -111,7 +111,7 @@
         self.assertEqual(show_port_body['port']['device_id'],
                          create_body['router']['id'])
 
-    @attr(type='gate')
+    @attr(type='smoke')
     def test_add_remove_router_interface_with_port_id(self):
         network = self.create_network()
         self.create_subnet(network)
diff --git a/tempest/api/object_storage/test_container_staticweb.py b/tempest/api/object_storage/test_container_staticweb.py
new file mode 100644
index 0000000..d07697a
--- /dev/null
+++ b/tempest/api/object_storage/test_container_staticweb.py
@@ -0,0 +1,94 @@
+# Copyright (C) 2013 eNovance SAS <licensing@enovance.com>
+#
+# Author: Joe H. Rahme <joe.hakim.rahme@enovance.com>
+#
+# 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.object_storage import base
+from tempest.common.utils.data_utils import arbitrary_string
+from tempest.common.utils.data_utils import rand_name
+from tempest.test import attr
+
+
+class StaticWebTest(base.BaseObjectTest):
+
+    @classmethod
+    def setUpClass(cls):
+        super(StaticWebTest, cls).setUpClass()
+        cls.container_name = rand_name(name="TestContainer")
+
+        # This header should be posted on the container before every test
+        cls.headers_public_read_acl = {'Read': '.r:*'}
+
+        # Create test container and create one object in it
+        cls.container_client.create_container(cls.container_name)
+        cls.object_name = rand_name(name="TestObject")
+        cls.object_data = arbitrary_string()
+        cls.object_client.create_object(cls.container_name,
+                                        cls.object_name,
+                                        cls.object_data)
+
+        cls.container_client.update_container_metadata(
+            cls.container_name,
+            metadata=cls.headers_public_read_acl,
+            metadata_prefix="X-Container-")
+
+    @classmethod
+    def tearDownClass(cls):
+        cls.delete_containers([cls.container_name])
+        cls.data.teardown_all()
+        super(StaticWebTest, cls).tearDownClass()
+
+    @attr('gate')
+    def test_web_index(self):
+        headers = {'web-index': self.object_name}
+
+        self.container_client.update_container_metadata(
+            self.container_name, metadata=headers)
+
+        # test GET on http://account_url/container_name
+        # we should retrieve the self.object_name file
+        resp, body = self.custom_account_client.request("GET",
+                                                        self.container_name)
+        self.assertEqual(resp['status'], '200')
+        self.assertEqual(body, self.object_data)
+
+        # clean up before exiting
+        self.container_client.update_container_metadata(self.container_name,
+                                                        {'web-index': ""})
+
+        _, body = self.container_client.list_container_metadata(
+            self.container_name)
+        self.assertNotIn('x-container-meta-web-index', body)
+
+    @attr('gate')
+    def test_web_listing(self):
+        headers = {'web-listings': 'true'}
+
+        self.container_client.update_container_metadata(
+            self.container_name, metadata=headers)
+
+        # test GET on http://account_url/container_name
+        # we should retrieve a listing of objects
+        resp, body = self.custom_account_client.request("GET",
+                                                        self.container_name)
+        self.assertEqual(resp['status'], '200')
+        self.assertIn(self.object_name, body)
+
+        # clean up before exiting
+        self.container_client.update_container_metadata(self.container_name,
+                                                        {'web-listings': ""})
+
+        _, body = self.container_client.list_container_metadata(
+            self.container_name)
+        self.assertNotIn('x-container-meta-web-listings', body)
diff --git a/tempest/api/object_storage/test_container_sync.py b/tempest/api/object_storage/test_container_sync.py
index d18c2ad..66a74e4 100644
--- a/tempest/api/object_storage/test_container_sync.py
+++ b/tempest/api/object_storage/test_container_sync.py
@@ -52,7 +52,7 @@
             cls.delete_containers(cls.containers, client[0], client[1])
         super(ContainerSyncTest, cls).tearDownClass()
 
-    @testtools.skip('Until Bug #1093743 is resolved.')
+    @testtools.skip('Skipped until the Bug #1093743 is resolved.')
     @attr(type='gate')
     def test_container_synchronization(self):
         # container to container synchronization
diff --git a/tempest/api/object_storage/test_object_expiry.py b/tempest/api/object_storage/test_object_expiry.py
index 8703480..889436d 100644
--- a/tempest/api/object_storage/test_object_expiry.py
+++ b/tempest/api/object_storage/test_object_expiry.py
@@ -43,7 +43,7 @@
         cls.delete_containers([cls.container_name])
         super(ObjectExpiryTest, cls).tearDownClass()
 
-    @testtools.skip('Until Bug #1069849 is resolved.')
+    @testtools.skip('Skipped until the Bug #1069849 is resolved.')
     @attr(type='gate')
     def test_get_object_after_expiry_time(self):
         # TODO(harika-vakadi): similar test case has to be created for
diff --git a/tempest/api/orchestration/base.py b/tempest/api/orchestration/base.py
index 745dd87..2a72c95 100644
--- a/tempest/api/orchestration/base.py
+++ b/tempest/api/orchestration/base.py
@@ -89,8 +89,8 @@
                 pass
 
     @classmethod
-    def _create_keypair(cls, namestart='keypair-heat-'):
-        kp_name = rand_name(namestart)
+    def _create_keypair(cls, name_start='keypair-heat-'):
+        kp_name = rand_name(name_start)
         resp, body = cls.keypairs_client.create_keypair(kp_name)
         cls.keypairs.append(kp_name)
         return body
diff --git a/tempest/api/orchestration/stacks/test_neutron_resources.py b/tempest/api/orchestration/stacks/test_neutron_resources.py
new file mode 100644
index 0000000..c934020
--- /dev/null
+++ b/tempest/api/orchestration/stacks/test_neutron_resources.py
@@ -0,0 +1,211 @@
+# vim: tabstop=4 shiftwidth=4 softtabstop=4
+
+#    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 logging
+
+from tempest.api.orchestration import base
+from tempest import clients
+from tempest.common.utils.data_utils import rand_name
+from tempest.test import attr
+
+
+LOG = logging.getLogger(__name__)
+
+
+class NeutronResourcesTestJSON(base.BaseOrchestrationTest):
+    _interface = 'json'
+
+    template = """
+HeatTemplateFormatVersion: '2012-12-12'
+Description: |
+  Template which creates single EC2 instance
+Parameters:
+  KeyName:
+    Type: String
+  InstanceType:
+    Type: String
+  ImageId:
+    Type: String
+  ExternalRouterId:
+    Type: String
+Resources:
+  Network:
+    Type: OS::Quantum::Net
+    Properties: {name: NewNetwork}
+  Subnet:
+    Type: OS::Quantum::Subnet
+    Properties:
+      network_id: {Ref: Network}
+      name: NewSubnet
+      ip_version: 4
+      cidr: 10.0.3.0/24
+      dns_nameservers: ["8.8.8.8"]
+      allocation_pools:
+      - {end: 10.0.3.150, start: 10.0.3.20}
+  RouterInterface:
+    Type: OS::Quantum::RouterInterface
+    Properties:
+      router_id: {Ref: ExternalRouterId}
+      subnet_id: {Ref: Subnet}
+  Server:
+    Type: AWS::EC2::Instance
+    Metadata:
+      Name: SmokeServer
+    Properties:
+      ImageId: {Ref: ImageId}
+      InstanceType: {Ref: InstanceType}
+      KeyName: {Ref: KeyName}
+      SubnetId: {Ref: Subnet}
+      UserData:
+        Fn::Base64:
+          Fn::Join:
+          - ''
+          - - '#!/bin/bash -v
+
+              '
+            - /opt/aws/bin/cfn-signal -e 0 -r "SmokeServer created" '
+            - {Ref: WaitHandle}
+            - '''
+
+              '
+  WaitHandle:
+    Type: AWS::CloudFormation::WaitConditionHandle
+  WaitCondition:
+    Type: AWS::CloudFormation::WaitCondition
+    DependsOn: Server
+    Properties:
+      Handle: {Ref: WaitHandle}
+      Timeout: '600'
+"""
+
+    @classmethod
+    def setUpClass(cls):
+        super(NeutronResourcesTestJSON, cls).setUpClass()
+        if not cls.orchestration_cfg.image_ref:
+            raise cls.skipException("No image available to test")
+        cls.client = cls.orchestration_client
+        os = clients.Manager()
+        cls.network_cfg = os.config.network
+        if not cls.config.service_available.neutron:
+            raise cls.skipException("Neutron support is required")
+        cls.network_client = os.network_client
+        cls.stack_name = rand_name('heat')
+        cls.keypair_name = (cls.orchestration_cfg.keypair_name or
+                            cls._create_keypair()['name'])
+        cls.external_router_id = cls._get_external_router_id()
+
+        # create the stack
+        cls.stack_identifier = cls.create_stack(
+            cls.stack_name,
+            cls.template,
+            parameters={
+                'KeyName': cls.keypair_name,
+                'InstanceType': cls.orchestration_cfg.instance_type,
+                'ImageId': cls.orchestration_cfg.image_ref,
+                'ExternalRouterId': cls.external_router_id
+            })
+        cls.stack_id = cls.stack_identifier.split('/')[1]
+        cls.client.wait_for_stack_status(cls.stack_id, 'CREATE_COMPLETE')
+        _, resources = cls.client.list_resources(cls.stack_identifier)
+        cls.test_resources = {}
+        for resource in resources:
+            cls.test_resources[resource['logical_resource_id']] = resource
+
+    @classmethod
+    def _get_external_router_id(cls):
+        resp, body = cls.network_client.list_ports()
+        ports = body['ports']
+        router_ports = filter(lambda port: port['device_owner'] ==
+                              'network:router_interface', ports)
+        return router_ports[0]['device_id']
+
+    @attr(type='slow')
+    def test_created_resources(self):
+        """Verifies created neutron resources."""
+        resources = [('Network', 'OS::Quantum::Net'),
+                     ('Subnet', 'OS::Quantum::Subnet'),
+                     ('RouterInterface', 'OS::Quantum::RouterInterface'),
+                     ('Server', 'AWS::EC2::Instance')]
+        for resource_name, resource_type in resources:
+            resource = self.test_resources.get(resource_name, None)
+            self.assertIsInstance(resource, dict)
+            self.assertEqual(resource_name, resource['logical_resource_id'])
+            self.assertEqual(resource_type, resource['resource_type'])
+            self.assertEqual('CREATE_COMPLETE', resource['resource_status'])
+
+    @attr(type='slow')
+    def test_created_network(self):
+        """Verifies created netowrk."""
+        network_id = self.test_resources.get('Network')['physical_resource_id']
+        resp, body = self.network_client.show_network(network_id)
+        self.assertEqual('200', resp['status'])
+        network = body['network']
+        self.assertIsInstance(network, dict)
+        self.assertEqual(network_id, network['id'])
+        self.assertEqual('NewNetwork', network['name'])
+
+    @attr(type='slow')
+    def test_created_subnet(self):
+        """Verifies created subnet."""
+        subnet_id = self.test_resources.get('Subnet')['physical_resource_id']
+        resp, body = self.network_client.show_subnet(subnet_id)
+        self.assertEqual('200', resp['status'])
+        subnet = body['subnet']
+        network_id = self.test_resources.get('Network')['physical_resource_id']
+        self.assertEqual(subnet_id, subnet['id'])
+        self.assertEqual(network_id, subnet['network_id'])
+        self.assertEqual('NewSubnet', subnet['name'])
+        self.assertEqual('8.8.8.8', subnet['dns_nameservers'][0])
+        self.assertEqual('10.0.3.20', subnet['allocation_pools'][0]['start'])
+        self.assertEqual('10.0.3.150', subnet['allocation_pools'][0]['end'])
+        self.assertEqual(4, subnet['ip_version'])
+        self.assertEqual('10.0.3.0/24', subnet['cidr'])
+
+    @attr(type='slow')
+    def test_created_router_interface(self):
+        """Verifies created router interface."""
+        network_id = self.test_resources.get('Network')['physical_resource_id']
+        subnet_id = self.test_resources.get('Subnet')['physical_resource_id']
+        resp, body = self.network_client.list_ports()
+        self.assertEqual('200', resp['status'])
+        ports = body['ports']
+        router_ports = filter(lambda port: port['device_id'] ==
+                              self.external_router_id, ports)
+        created_network_ports = filter(lambda port: port['network_id'] ==
+                                       network_id, router_ports)
+        self.assertEqual(1, len(created_network_ports))
+        router_interface = created_network_ports[0]
+        fixed_ips = router_interface['fixed_ips']
+        subnet_fixed_ips = filter(lambda port: port['subnet_id'] ==
+                                  subnet_id, fixed_ips)
+        self.assertEqual(1, len(subnet_fixed_ips))
+        router_interface_ip = subnet_fixed_ips[0]['ip_address']
+        self.assertEqual('10.0.3.1', router_interface_ip)
+
+    @attr(type='slow')
+    def test_created_server(self):
+        """Verifies created sever."""
+        server_id = self.test_resources.get('Server')['physical_resource_id']
+        resp, server = self.servers_client.get_server(server_id)
+        self.assertEqual('200', resp['status'])
+        self.assertEqual(self.keypair_name, server['key_name'])
+        self.assertEqual('ACTIVE', server['status'])
+        network = server['addresses']['NewNetwork'][0]
+        self.assertEqual(4, network['version'])
+        ip_addr_prefix = network['addr'][:7]
+        ip_addr_suffix = int(network['addr'].split('.')[3])
+        self.assertEqual('10.0.3.', ip_addr_prefix)
+        self.assertTrue(ip_addr_suffix >= 20)
+        self.assertTrue(ip_addr_suffix <= 150)
diff --git a/tempest/api/orchestration/stacks/test_non_empty_stack.py b/tempest/api/orchestration/stacks/test_non_empty_stack.py
new file mode 100644
index 0000000..defb910
--- /dev/null
+++ b/tempest/api/orchestration/stacks/test_non_empty_stack.py
@@ -0,0 +1,169 @@
+# vim: tabstop=4 shiftwidth=4 softtabstop=4
+
+#    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 logging
+
+from tempest.api.orchestration import base
+from tempest.common.utils.data_utils import rand_name
+from tempest.test import attr
+
+
+LOG = logging.getLogger(__name__)
+
+
+class StacksTestJSON(base.BaseOrchestrationTest):
+    _interface = 'json'
+
+    template = """
+HeatTemplateFormatVersion: '2012-12-12'
+Description: |
+  Template which creates single EC2 instance
+Parameters:
+  KeyName:
+    Type: String
+  InstanceType:
+    Type: String
+  ImageId:
+    Type: String
+Resources:
+  SmokeServer:
+    Type: AWS::EC2::Instance
+    Metadata:
+      Name: SmokeServer
+    Properties:
+      ImageId: {Ref: ImageId}
+      InstanceType: {Ref: InstanceType}
+      KeyName: {Ref: KeyName}
+      UserData:
+        Fn::Base64:
+          Fn::Join:
+          - ''
+          - - '#!/bin/bash -v
+
+              '
+            - /opt/aws/bin/cfn-signal -e 0 -r "SmokeServer created" '
+            - {Ref: WaitHandle}
+            - '''
+
+              '
+  WaitHandle:
+    Type: AWS::CloudFormation::WaitConditionHandle
+  WaitCondition:
+    Type: AWS::CloudFormation::WaitCondition
+    DependsOn: SmokeServer
+    Properties:
+      Handle: {Ref: WaitHandle}
+      Timeout: '600'
+"""
+
+    @classmethod
+    def setUpClass(cls):
+        super(StacksTestJSON, cls).setUpClass()
+        if not cls.orchestration_cfg.image_ref:
+            raise cls.skipException("No image available to test")
+        cls.client = cls.orchestration_client
+        cls.stack_name = rand_name('heat')
+        keypair_name = (cls.orchestration_cfg.keypair_name or
+                        cls._create_keypair()['name'])
+
+        # create the stack
+        cls.stack_identifier = cls.create_stack(
+            cls.stack_name,
+            cls.template,
+            parameters={
+                'KeyName': keypair_name,
+                'InstanceType': cls.orchestration_cfg.instance_type,
+                'ImageId': cls.orchestration_cfg.image_ref
+            })
+        cls.stack_id = cls.stack_identifier.split('/')[1]
+        cls.resource_name = 'SmokeServer'
+        cls.resource_type = 'AWS::EC2::Instance'
+        cls.client.wait_for_stack_status(cls.stack_id, 'CREATE_COMPLETE')
+
+    @attr(type='slow')
+    def test_stack_list(self):
+        """Created stack should be on the list of existing stacks."""
+        resp, stacks = self.client.list_stacks()
+        self.assertEqual('200', resp['status'])
+        self.assertIsInstance(stacks, list)
+        stacks_names = map(lambda stack: stack['stack_name'], stacks)
+        self.assertIn(self.stack_name, stacks_names)
+
+    @attr(type='slow')
+    def test_stack_show(self):
+        """Getting details about created stack should be possible."""
+        resp, stack = self.client.get_stack(self.stack_name)
+        self.assertEqual('200', resp['status'])
+        self.assertIsInstance(stack, dict)
+        self.assertEqual(self.stack_name, stack['stack_name'])
+        self.assertEqual(self.stack_id, stack['id'])
+
+    @attr(type='slow')
+    def test_list_resources(self):
+        """Getting list of created resources for the stack should be possible.
+        """
+        resp, resources = self.client.list_resources(self.stack_identifier)
+        self.assertEqual('200', resp['status'])
+        self.assertIsInstance(resources, list)
+        resources_names = map(lambda resource: resource['logical_resource_id'],
+                              resources)
+        self.assertIn(self.resource_name, resources_names)
+        resources_types = map(lambda resource: resource['resource_type'],
+                              resources)
+        self.assertIn(self.resource_type, resources_types)
+
+    @attr(type='slow')
+    def test_show_resource(self):
+        """Getting details about created resource should be possible."""
+        resp, resource = self.client.get_resource(self.stack_identifier,
+                                                  self.resource_name)
+        self.assertIsInstance(resource, dict)
+        self.assertEqual(self.resource_name, resource['logical_resource_id'])
+        self.assertEqual(self.resource_type, resource['resource_type'])
+
+    @attr(type='slow')
+    def test_resource_metadata(self):
+        """Getting metadata for created resource should be possible."""
+        resp, metadata = self.client.show_resource_metadata(
+            self.stack_identifier,
+            self.resource_name)
+        self.assertEqual('200', resp['status'])
+        self.assertIsInstance(metadata, dict)
+        self.assertEqual(self.resource_name, metadata.get('Name', None))
+
+    @attr(type='slow')
+    def test_list_events(self):
+        """Getting list of created events for the stack should be possible."""
+        resp, events = self.client.list_events(self.stack_identifier)
+        self.assertEqual('200', resp['status'])
+        self.assertIsInstance(events, list)
+        resource_statuses = map(lambda event: event['resource_status'], events)
+        self.assertIn('CREATE_IN_PROGRESS', resource_statuses)
+        self.assertIn('CREATE_COMPLETE', resource_statuses)
+
+    @attr(type='slow')
+    def test_show_event(self):
+        """Getting details about existing event should be possible."""
+        resp, events = self.client.list_resource_events(self.stack_identifier,
+                                                        self.resource_name)
+        self.assertNotEqual([], events)
+        events.sort(key=lambda event: event['event_time'])
+        event_id = events[0]['id']
+        resp, event = self.client.show_event(self.stack_identifier,
+                                             self.resource_name, event_id)
+        self.assertEqual('200', resp['status'])
+        self.assertEqual('CREATE_IN_PROGRESS', event['resource_status'])
+        self.assertEqual('state changed', event['resource_status_reason'])
+        self.assertEqual(self.resource_name, event['logical_resource_id'])
+        self.assertIsInstance(event, dict)
diff --git a/tempest/api/orchestration/stacks/test_instance_cfn_init.py b/tempest/api/orchestration/stacks/test_server_cfn_init.py
similarity index 90%
rename from tempest/api/orchestration/stacks/test_instance_cfn_init.py
rename to tempest/api/orchestration/stacks/test_server_cfn_init.py
index fe55ecf..ffe8def 100644
--- a/tempest/api/orchestration/stacks/test_instance_cfn_init.py
+++ b/tempest/api/orchestration/stacks/test_server_cfn_init.py
@@ -26,7 +26,7 @@
 LOG = logging.getLogger(__name__)
 
 
-class InstanceCfnInitTestJSON(base.BaseOrchestrationTest):
+class ServerCfnInitTestJSON(base.BaseOrchestrationTest):
     _interface = 'json'
     existing_keypair = (tempest.config.TempestConfig().
                         orchestration.keypair_name is not None)
@@ -37,11 +37,11 @@
   Template which uses a wait condition to confirm that a minimal
   cfn-init and cfn-signal has worked
 Parameters:
-  KeyName:
+  key_name:
     Type: String
-  InstanceType:
+  flavor:
     Type: String
-  ImageId:
+  image:
     Type: String
 Resources:
   CfnUser:
@@ -58,7 +58,7 @@
     Properties:
       UserName: {Ref: CfnUser}
   SmokeServer:
-    Type: AWS::EC2::Instance
+    Type: OS::Nova::Server
     Metadata:
       AWS::CloudFormation::Init:
         config:
@@ -83,12 +83,12 @@
               owner: root
               group: root
     Properties:
-      ImageId: {Ref: ImageId}
-      InstanceType: {Ref: InstanceType}
-      KeyName: {Ref: KeyName}
-      SecurityGroups:
+      image: {Ref: image}
+      flavor: {Ref: flavor}
+      key_name: {Ref: key_name}
+      security_groups:
       - {Ref: SmokeSecurityGroup}
-      UserData:
+      user_data:
         Fn::Base64:
           Fn::Join:
           - ''
@@ -118,12 +118,12 @@
   SmokeServerIp:
     Description: IP address of server
     Value:
-      Fn::GetAtt: [SmokeServer, PublicIp]
+      Fn::GetAtt: [SmokeServer, first_private_address]
 """
 
     @classmethod
     def setUpClass(cls):
-        super(InstanceCfnInitTestJSON, cls).setUpClass()
+        super(ServerCfnInitTestJSON, cls).setUpClass()
         if not cls.orchestration_cfg.image_ref:
             raise cls.skipException("No image available to test")
         cls.client = cls.orchestration_client
@@ -140,9 +140,9 @@
             stack_name,
             cls.template,
             parameters={
-                'KeyName': keypair_name,
-                'InstanceType': cls.orchestration_cfg.instance_type,
-                'ImageId': cls.orchestration_cfg.image_ref
+                'key_name': keypair_name,
+                'flavor': cls.orchestration_cfg.instance_type,
+                'image': cls.orchestration_cfg.image_ref
             })
 
     @attr(type='slow')
@@ -187,7 +187,7 @@
         # This is an assert of great significance, as it means the following
         # has happened:
         # - cfn-init read the provided metadata and wrote out a file
-        # - a user was created and credentials written to the instance
+        # - a user was created and credentials written to the server
         # - a cfn-signal was built which was signed with provided credentials
         # - the wait condition was fulfilled and the stack has changed state
         wait_status = json.loads(
diff --git a/tempest/api/orchestration/stacks/test_stacks.py b/tempest/api/orchestration/stacks/test_stacks.py
index f1f1f7e..4bda5ab 100644
--- a/tempest/api/orchestration/stacks/test_stacks.py
+++ b/tempest/api/orchestration/stacks/test_stacks.py
@@ -33,8 +33,7 @@
 
     @attr(type='smoke')
     def test_stack_list_responds(self):
-        resp, body = self.client.list_stacks()
-        stacks = body['stacks']
+        resp, stacks = self.client.list_stacks()
         self.assertEqual('200', resp['status'])
         self.assertIsInstance(stacks, list)
 
@@ -42,9 +41,6 @@
     def test_stack_crud_no_resources(self):
         stack_name = rand_name('heat')
 
-        # count how many stacks to start with
-        resp, body = self.client.list_stacks()
-
         # create the stack
         stack_identifier = self.create_stack(
             stack_name, self.empty_template)
@@ -54,21 +50,21 @@
         self.client.wait_for_stack_status(stack_identifier, 'CREATE_COMPLETE')
 
         # check for stack in list
-        resp, body = self.client.list_stacks()
-        list_ids = list([stack['id'] for stack in body['stacks']])
+        resp, stacks = self.client.list_stacks()
+        list_ids = list([stack['id'] for stack in stacks])
         self.assertIn(stack_id, list_ids)
 
         # fetch the stack
-        resp, body = self.client.get_stack(stack_identifier)
-        self.assertEqual('CREATE_COMPLETE', body['stack_status'])
+        resp, stack = self.client.get_stack(stack_identifier)
+        self.assertEqual('CREATE_COMPLETE', stack['stack_status'])
 
         # fetch the stack by name
-        resp, body = self.client.get_stack(stack_name)
-        self.assertEqual('CREATE_COMPLETE', body['stack_status'])
+        resp, stack = self.client.get_stack(stack_name)
+        self.assertEqual('CREATE_COMPLETE', stack['stack_status'])
 
         # fetch the stack by id
-        resp, body = self.client.get_stack(stack_id)
-        self.assertEqual('CREATE_COMPLETE', body['stack_status'])
+        resp, stack = self.client.get_stack(stack_id)
+        self.assertEqual('CREATE_COMPLETE', stack['stack_status'])
 
         # delete the stack
         resp = self.client.delete_stack(stack_identifier)
diff --git a/tempest/api/orchestration/stacks/test_templates.py b/tempest/api/orchestration/stacks/test_templates.py
new file mode 100644
index 0000000..6a7c541
--- /dev/null
+++ b/tempest/api/orchestration/stacks/test_templates.py
@@ -0,0 +1,86 @@
+# vim: tabstop=4 shiftwidth=4 softtabstop=4
+
+#    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 logging
+
+from tempest.api.orchestration import base
+from tempest.common.utils.data_utils import rand_name
+from tempest import exceptions
+from tempest.test import attr
+
+
+LOG = logging.getLogger(__name__)
+
+
+class TemplateYAMLTestJSON(base.BaseOrchestrationTest):
+    _interface = 'json'
+
+    template = """
+HeatTemplateFormatVersion: '2012-12-12'
+Description: |
+  Template which creates only a new user
+Resources:
+  CfnUser:
+    Type: AWS::IAM::User
+"""
+
+    invalid_template_url = 'http://www.example.com/template.yaml'
+
+    @classmethod
+    def setUpClass(cls):
+        super(TemplateYAMLTestJSON, cls).setUpClass()
+        cls.client = cls.orchestration_client
+        cls.stack_name = rand_name('heat')
+        cls.stack_identifier = cls.create_stack(cls.stack_name, cls.template)
+        cls.client.wait_for_stack_status(cls.stack_identifier,
+                                         'CREATE_COMPLETE')
+        cls.stack_id = cls.stack_identifier.split('/')[1]
+        cls.parameters = {}
+
+    @attr(type='gate')
+    def test_show_template(self):
+        """Getting template used to create the stack."""
+        resp, template = self.client.show_template(self.stack_identifier)
+        self.assertEqual('200', resp['status'])
+
+    @attr(type='gate')
+    def test_validate_template(self):
+        """Validating template passing it content."""
+        resp, parameters = self.client.validate_template(self.template,
+                                                         self.parameters)
+        self.assertEqual('200', resp['status'])
+
+    @attr(type=['gate', 'negative'])
+    def test_validate_template_url(self):
+        """Validating template passing url to it."""
+        self.assertRaises(exceptions.BadRequest,
+                          self.client.validate_template_url,
+                          template_url=self.invalid_template_url,
+                          parameters=self.parameters)
+
+
+class TemplateAWSTestJSON(TemplateYAMLTestJSON):
+    template = """
+{
+  "AWSTemplateFormatVersion" : "2010-09-09",
+  "Description" : "Template which creates only a new user",
+  "Resources" : {
+    "CfnUser" : {
+      "Type" : "AWS::IAM::User"
+    }
+  }
+}
+"""
+
+    invalid_template_url = 'http://www.example.com/template.template'
diff --git a/tempest/api/volume/admin/test_volume_types.py b/tempest/api/volume/admin/test_volume_types.py
index 822f691..b15f8dd 100644
--- a/tempest/api/volume/admin/test_volume_types.py
+++ b/tempest/api/volume/admin/test_volume_types.py
@@ -41,6 +41,7 @@
     def _delete_volume(self, volume_id):
         resp, _ = self.volumes_client.delete_volume(volume_id)
         self.assertEqual(202, resp.status)
+        self.volumes_client.wait_for_resource_deletion(volume_id)
 
     def _delete_volume_type(self, volume_type_id):
         resp, _ = self.client.delete_volume_type(volume_type_id)
diff --git a/tempest/api/volume/test_volumes_list.py b/tempest/api/volume/test_volumes_list.py
index 5d5fd7e..8c39e08 100644
--- a/tempest/api/volume/test_volumes_list.py
+++ b/tempest/api/volume/test_volumes_list.py
@@ -32,6 +32,19 @@
 
     _interface = 'json'
 
+    def assertVolumesIn(self, fetched_list, expected_list):
+        missing_vols = [v for v in expected_list if v not in fetched_list]
+        if len(missing_vols) == 0:
+            return
+
+        def str_vol(vol):
+            return "%s:%s" % (vol['id'], vol['display_name'])
+
+        raw_msg = "Could not find volumes %s in expected list %s; fetched %s"
+        self.fail(raw_msg % ([str_vol(v) for v in missing_vols],
+                             [str_vol(v) for v in expected_list],
+                             [str_vol(v) for v in fetched_list]))
+
     @classmethod
     def setUpClass(cls):
         super(VolumesListTest, cls).setUpClass()
@@ -82,12 +95,7 @@
         # Fetch all volumes
         resp, fetched_list = self.client.list_volumes()
         self.assertEqual(200, resp.status)
-        # Now check if all the volumes created in setup are in fetched list
-        missing_vols = [v for v in self.volume_list if v not in fetched_list]
-        self.assertFalse(missing_vols,
-                         "Failed to find volume %s in fetched list" %
-                         ', '.join(m_vol['display_name']
-                                   for m_vol in missing_vols))
+        self.assertVolumesIn(fetched_list, self.volume_list)
 
     @attr(type='gate')
     def test_volume_list_with_details(self):
@@ -95,12 +103,7 @@
         # Fetch all Volumes
         resp, fetched_list = self.client.list_volumes_with_detail()
         self.assertEqual(200, resp.status)
-        # Verify that all the volumes are returned
-        missing_vols = [v for v in self.volume_list if v not in fetched_list]
-        self.assertFalse(missing_vols,
-                         "Failed to find volume %s in fetched list" %
-                         ', '.join(m_vol['display_name']
-                                   for m_vol in missing_vols))
+        self.assertVolumesIn(fetched_list, self.volume_list)
 
 
 class VolumeListTestXML(VolumesListTest):
diff --git a/tempest/common/rest_client.py b/tempest/common/rest_client.py
index d744e3d..8dfff6e 100644
--- a/tempest/common/rest_client.py
+++ b/tempest/common/rest_client.py
@@ -307,6 +307,12 @@
         self.LOG.info("Response Status: " + status)
         headers = resp.copy()
         del headers['status']
+        if headers.get('x-compute-request-id'):
+            self.LOG.info("Nova request id: %s" %
+                          headers.pop('x-compute-request-id'))
+        elif headers.get('x-openstack-request-id'):
+            self.LOG.info("Glance request id %s" %
+                          headers.pop('x-openstack-request-id'))
         if len(headers):
             self.LOG.debug('Response Headers: ' + str(headers))
         if resp_body:
diff --git a/tempest/common/ssh.py b/tempest/common/ssh.py
index be350c8..2052705 100644
--- a/tempest/common/ssh.py
+++ b/tempest/common/ssh.py
@@ -56,7 +56,7 @@
             paramiko.AutoAddPolicy())
         _start_time = time.time()
 
-        while not self._is_timed_out(self.timeout, _start_time):
+        while not self._is_timed_out(_start_time):
             try:
                 ssh.connect(self.host, username=self.username,
                             password=self.password,
@@ -76,8 +76,8 @@
                                         password=self.password)
         return ssh
 
-    def _is_timed_out(self, timeout, start_time):
-        return (time.time() - timeout) > start_time
+    def _is_timed_out(self, start_time):
+        return (time.time() - self.timeout) > start_time
 
     def connect_until_closed(self):
         """Connect to the server and wait until connection is lost."""
@@ -85,10 +85,10 @@
             ssh = self._get_ssh_connection()
             _transport = ssh.get_transport()
             _start_time = time.time()
-            _timed_out = self._is_timed_out(self.timeout, _start_time)
+            _timed_out = self._is_timed_out(_start_time)
             while _transport.is_active() and not _timed_out:
                 time.sleep(5)
-                _timed_out = self._is_timed_out(self.timeout, _start_time)
+                _timed_out = self._is_timed_out(_start_time)
             ssh.close()
         except (EOFError, paramiko.AuthenticationException, socket.error):
             return
@@ -114,9 +114,13 @@
         err_data = []
         poll = select.poll()
         poll.register(channel, select.POLLIN)
+        start_time = time.time()
+
         while True:
             ready = poll.poll(self.channel_timeout)
             if not any(ready):
+                if not self._is_timed_out(start_time):
+                    continue
                 raise exceptions.TimeoutException(
                     "Command: '{0}' executed on host '{1}'.".format(
                         cmd, self.host))
diff --git a/tempest/scenario/manager.py b/tempest/scenario/manager.py
index 1703248..7681f04 100644
--- a/tempest/scenario/manager.py
+++ b/tempest/scenario/manager.py
@@ -371,6 +371,24 @@
         LOG.debug("Created volume: %s", volume)
         return volume
 
+    def create_server_snapshot(self, server, compute_client=None,
+                               image_client=None, name=None):
+        if compute_client is None:
+            compute_client = self.compute_client
+        if image_client is None:
+            image_client = self.image_client
+        if name is None:
+            name = rand_name('scenario-snapshot-')
+        LOG.debug("Creating a snapshot image for server: %s", server.name)
+        image_id = compute_client.servers.create_image(server, name)
+        self.addCleanup(image_client.images.delete, image_id)
+        self.status_timeout(image_client.images, image_id, 'active')
+        snapshot_image = image_client.images.get(image_id)
+        self.assertEquals(name, snapshot_image.name)
+        LOG.debug("Created snapshot image %s for server %s",
+                  snapshot_image.name, server.name)
+        return snapshot_image
+
     def create_keypair(self, client=None, name=None):
         if client is None:
             client = self.compute_client
diff --git a/tempest/scenario/orchestration/test_autoscaling.py b/tempest/scenario/orchestration/test_autoscaling.py
index 17870a1..78025ee 100644
--- a/tempest/scenario/orchestration/test_autoscaling.py
+++ b/tempest/scenario/orchestration/test_autoscaling.py
@@ -12,16 +12,12 @@
 #    License for the specific language governing permissions and limitations
 #    under the License.
 
-from tempest.openstack.common import log as logging
 from tempest.scenario import manager
 from tempest.test import attr
 from tempest.test import call_until_true
 import time
 
 
-LOG = logging.getLogger(__name__)
-
-
 class AutoScalingTest(manager.OrchestrationScenarioTest):
 
     def setUp(self):
diff --git a/tempest/scenario/test_snapshot_pattern.py b/tempest/scenario/test_snapshot_pattern.py
index c55e2a3..003c264 100644
--- a/tempest/scenario/test_snapshot_pattern.py
+++ b/tempest/scenario/test_snapshot_pattern.py
@@ -15,14 +15,9 @@
 #    License for the specific language governing permissions and limitations
 #    under the License.
 
-from tempest.common.utils.data_utils import rand_name
-from tempest.openstack.common import log as logging
 from tempest.scenario import manager
 
 
-LOG = logging.getLogger(__name__)
-
-
 class TestSnapshotPattern(manager.OfficialClientTest):
     """
     This test is for snapshotting an instance and booting with it.
@@ -34,14 +29,6 @@
 
     """
 
-    def _wait_for_server_status(self, server, status):
-        self.status_timeout(self.compute_client.servers,
-                            server.id,
-                            status)
-
-    def _wait_for_image_status(self, image_id, status):
-        self.status_timeout(self.image_client.images, image_id, status)
-
     def _boot_image(self, image_id):
         create_kwargs = {
             'key_name': self.keypair.name
@@ -61,17 +48,6 @@
         ssh_client.exec_command('date > /tmp/timestamp; sync')
         self.timestamp = ssh_client.exec_command('cat /tmp/timestamp')
 
-    def _create_image(self, server):
-        snapshot_name = rand_name('scenario-snapshot-')
-        create_image_client = self.compute_client.servers.create_image
-        image_id = create_image_client(server, snapshot_name)
-        self.addCleanup(self.image_client.images.delete, image_id)
-        self._wait_for_server_status(server, 'ACTIVE')
-        self._wait_for_image_status(image_id, 'active')
-        snapshot_image = self.image_client.images.get(image_id)
-        self.assertEquals(snapshot_name, snapshot_image.name)
-        return image_id
-
     def _check_timestamp(self, server_or_ip):
         ssh_client = self._ssh_to_server(server_or_ip)
         got_timestamp = ssh_client.exec_command('cat /tmp/timestamp')
@@ -100,10 +76,10 @@
             self._write_timestamp(server)
 
         # snapshot the instance
-        snapshot_image_id = self._create_image(server)
+        snapshot_image = self.create_server_snapshot(server=server)
 
         # boot a second instance from the snapshot
-        server_from_snapshot = self._boot_image(snapshot_image_id)
+        server_from_snapshot = self._boot_image(snapshot_image.id)
 
         # check the existence of the timestamp file in the second instance
         if self.config.compute.use_floatingip_for_ssh:
diff --git a/tempest/scenario/test_stamp_pattern.py b/tempest/scenario/test_stamp_pattern.py
index c74b88d..5af4bb2 100644
--- a/tempest/scenario/test_stamp_pattern.py
+++ b/tempest/scenario/test_stamp_pattern.py
@@ -50,14 +50,6 @@
     14. Check the existence of a file which created at 6. in volume2
     """
 
-    def _wait_for_server_status(self, server, status):
-        self.status_timeout(self.compute_client.servers,
-                            server.id,
-                            status)
-
-    def _wait_for_image_status(self, image_id, status):
-        self.status_timeout(self.image_client.images, image_id, status)
-
     def _wait_for_volume_snapshot_status(self, volume_snapshot, status):
         self.status_timeout(self.volume_client.volume_snapshots,
                             volume_snapshot.id, status)
@@ -84,17 +76,6 @@
         linux_client = self.get_remote_client(server_or_ip)
         return linux_client.ssh_client
 
-    def _create_image(self, server):
-        snapshot_name = rand_name('scenario-snapshot-')
-        create_image_client = self.compute_client.servers.create_image
-        image_id = create_image_client(server, snapshot_name)
-        self.addCleanup(self.image_client.images.delete, image_id)
-        self._wait_for_server_status(server, 'ACTIVE')
-        self._wait_for_image_status(image_id, 'active')
-        snapshot_image = self.image_client.images.get(image_id)
-        self.assertEquals(snapshot_name, snapshot_image.name)
-        return image_id
-
     def _create_volume_snapshot(self, volume):
         snapshot_name = rand_name('scenario-snapshot-')
         volume_snapshots = self.volume_client.volume_snapshots
@@ -162,7 +143,7 @@
         got_timestamp = ssh_client.exec_command('sudo cat /mnt/timestamp')
         self.assertEqual(self.timestamp, got_timestamp)
 
-    @testtools.skip("Until Bug #1205344 is fixed")
+    @testtools.skip("Skipped until the Bug #1205344 is resolved.")
     def test_stamp_pattern(self):
         # prepare for booting a instance
         self._add_keypair()
@@ -189,14 +170,14 @@
         volume_snapshot = self._create_volume_snapshot(volume)
 
         # snapshot the instance
-        snapshot_image_id = self._create_image(server)
+        snapshot_image = self.create_server_snapshot(server=server)
 
         # create second volume from the snapshot(volume2)
         volume_from_snapshot = self._create_volume(
             snapshot_id=volume_snapshot.id)
 
         # boot second instance from the snapshot(instance2)
-        server_from_snapshot = self._boot_image(snapshot_image_id)
+        server_from_snapshot = self._boot_image(snapshot_image.id)
 
         # create and add floating IP to server_from_snapshot
         if self.config.compute.use_floatingip_for_ssh:
diff --git a/tempest/scenario/test_volume_snapshot_pattern.py b/tempest/scenario/test_volume_snapshot_pattern.py
index 8fa177e..d873d30 100644
--- a/tempest/scenario/test_volume_snapshot_pattern.py
+++ b/tempest/scenario/test_volume_snapshot_pattern.py
@@ -12,13 +12,9 @@
 #    License for the specific language governing permissions and limitations
 #    under the License.
 
-from tempest.openstack.common import log as logging
-
 from tempest.common.utils.data_utils import rand_name
 from tempest.scenario import manager
 
-LOG = logging.getLogger(__name__)
-
 
 class TestVolumeSnapshotPattern(manager.OfficialClientTest):
 
diff --git a/tempest/services/orchestration/json/orchestration_client.py b/tempest/services/orchestration/json/orchestration_client.py
index ef88eed..e896e0d 100644
--- a/tempest/services/orchestration/json/orchestration_client.py
+++ b/tempest/services/orchestration/json/orchestration_client.py
@@ -42,7 +42,7 @@
 
         resp, body = self.get(uri)
         body = json.loads(body)
-        return resp, body
+        return resp, body['stacks']
 
     def create_stack(self, name, disable_rollback=True, parameters={},
                      timeout_mins=60, template=None, template_url=None):
@@ -176,3 +176,64 @@
                            (stack_name, status, self.build_timeout))
                 raise exceptions.TimeoutException(message)
             time.sleep(self.build_interval)
+
+    def show_resource_metadata(self, stack_identifier, resource_name):
+        """Returns the resource's metadata."""
+        url = ('stacks/{stack_identifier}/resources/{resource_name}'
+               '/metadata'.format(**locals()))
+        resp, body = self.get(url)
+        body = json.loads(body)
+        return resp, body['metadata']
+
+    def list_events(self, stack_identifier):
+        """Returns list of all events for a stack."""
+        url = 'stacks/{stack_identifier}/events'.format(**locals())
+        resp, body = self.get(url)
+        body = json.loads(body)
+        return resp, body['events']
+
+    def list_resource_events(self, stack_identifier, resource_name):
+        """Returns list of all events for a resource from stack."""
+        url = ('stacks/{stack_identifier}/resources/{resource_name}'
+               '/events'.format(**locals()))
+        resp, body = self.get(url)
+        body = json.loads(body)
+        return resp, body['events']
+
+    def show_event(self, stack_identifier, resource_name, event_id):
+        """Returns the details of a single stack's event."""
+        url = ('stacks/{stack_identifier}/resources/{resource_name}/events'
+               '/{event_id}'.format(**locals()))
+        resp, body = self.get(url)
+        body = json.loads(body)
+        return resp, body['event']
+
+    def show_template(self, stack_identifier):
+        """Returns the template for the stack."""
+        url = ('stacks/{stack_identifier}/template'.format(**locals()))
+        resp, body = self.get(url)
+        body = json.loads(body)
+        return resp, body
+
+    def _validate_template(self, post_body):
+        """Returns the validation request result."""
+        post_body = json.dumps(post_body)
+        resp, body = self.post('validate', post_body, self.headers)
+        body = json.loads(body)
+        return resp, body
+
+    def validate_template(self, template, parameters={}):
+        """Returns the validation result for a template with parameters."""
+        post_body = {
+            'template': template,
+            'parameters': parameters,
+        }
+        return self._validate_template(post_body)
+
+    def validate_template_url(self, template_url, parameters={}):
+        """Returns the validation result for a template with parameters."""
+        post_body = {
+            'template_url': template_url,
+            'parameters': parameters,
+        }
+        return self._validate_template(post_body)
diff --git a/tempest/stress/actions/ssh_floating.py b/tempest/stress/actions/ssh_floating.py
new file mode 100644
index 0000000..36ef023
--- /dev/null
+++ b/tempest/stress/actions/ssh_floating.py
@@ -0,0 +1,189 @@
+# vim: tabstop=4 shiftwidth=4 softtabstop=4
+
+#    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 socket
+import subprocess
+
+from tempest.common.utils.data_utils import rand_name
+import tempest.stress.stressaction as stressaction
+import tempest.test
+
+
+class FloatingStress(stressaction.StressAction):
+
+    # from the scenario manager
+    def ping_ip_address(self, ip_address):
+        cmd = ['ping', '-c1', '-w1', ip_address]
+
+        proc = subprocess.Popen(cmd,
+                                stdout=subprocess.PIPE,
+                                stderr=subprocess.PIPE)
+        proc.wait()
+        success = proc.returncode == 0
+        self.logger.info("%s(%s): %s", self.server_id, self.floating['ip'],
+                         "pong!" if success else "no pong :(")
+        return success
+
+    def tcp_connect_scan(self, addr, port):
+        # like tcp
+        s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
+        try:
+            s.connect((addr, port))
+        except socket.error as exc:
+            self.logger.info("%s(%s): %s", self.server_id, self.floating['ip'],
+                             str(exc))
+            return False
+        self.logger.info("%s(%s): Connected :)", self.server_id,
+                         self.floating['ip'])
+        s.close()
+        return True
+
+    def check_port_ssh(self):
+        def func():
+            return self.tcp_connect_scan(self.floating['ip'], 22)
+        if not tempest.test.call_until_true(func, self.check_timeout,
+                                            self.check_interval):
+            raise RuntimeError("Cannot connect to the ssh port.")
+
+    def check_icmp_echo(self):
+        def func():
+            return self.ping_ip_address(self.floating['ip'])
+        if not tempest.test.call_until_true(func, self.check_timeout,
+                                            self.check_interval):
+            raise RuntimeError("Cannot ping the machine.")
+
+    def _create_vm(self):
+        self.name = name = rand_name("instance")
+        servers_client = self.manager.servers_client
+        self.logger.info("creating %s" % name)
+        vm_args = self.vm_extra_args.copy()
+        vm_args['security_groups'] = [{'name': self.sec_grp}]
+        resp, server = servers_client.create_server(name, self.image,
+                                                    self.flavor,
+                                                    **vm_args)
+        self.server_id = server['id']
+        assert(resp.status == 202)
+        if self.wait_after_vm_create:
+            self.manager.servers_client.wait_for_server_status(self.server_id,
+                                                               'ACTIVE')
+
+    def _destroy_vm(self):
+        self.logger.info("deleting %s" % self.server_id)
+        resp, _ = self.manager.servers_client.delete_server(self.server_id)
+        assert(resp.status == 204)  # It cannot be 204 if I had to wait..
+        self.manager.servers_client.wait_for_server_termination(self.server_id)
+        self.logger.info("deleted %s" % self.server_id)
+
+    def _create_sec_group(self):
+        sec_grp_cli = self.manager.security_groups_client
+        s_name = rand_name('sec_grp-')
+        s_description = rand_name('desc-')
+        _, _sec_grp = sec_grp_cli.create_security_group(s_name,
+                                                        s_description)
+        self.sec_grp = _sec_grp['id']
+        create_rule = sec_grp_cli.create_security_group_rule
+        create_rule(self.sec_grp, 'tcp', 22, 22)
+        create_rule(self.sec_grp, 'icmp', -1, -1)
+
+    def _destroy_sec_grp(self):
+        sec_grp_cli = self.manager.security_groups_client
+        sec_grp_cli.delete_security_group(self.sec_grp)
+
+    def _create_floating_ip(self):
+        floating_cli = self.manager.floating_ips_client
+        _, self.floating = floating_cli.create_floating_ip(self.floating_pool)
+
+    def _destroy_floating_ip(self):
+        cli = self.manager.floating_ips_client
+        cli.delete_floating_ip(self.floating['id'])
+        cli.wait_for_resource_deletion(self.floating['id'])
+        self.logger.info("Deleted Floating IP %s", str(self.floating['ip']))
+
+    def setUp(self, **kwargs):
+        self.image = self.manager.config.compute.image_ref
+        self.flavor = self.manager.config.compute.flavor_ref
+        self.vm_extra_args = kwargs.get('vm_extra_args', {})
+        self.wait_after_vm_create = kwargs.get('wait_after_vm_create',
+                                               True)
+        self.new_vm = kwargs.get('new_vm', False)
+        self.new_sec_grp = kwargs.get('new_sec_group', False)
+        self.new_floating = kwargs.get('new_floating', False)
+        self.reboot = kwargs.get('reboot', False)
+        self.floating_pool = kwargs.get('floating_pool', None)
+        self.verify = kwargs.get('verify', ('check_port_ssh',
+                                            'check_icmp_echo'))
+        self.check_timeout = kwargs.get('check_timeout', 120)
+        self.check_interval = kwargs.get('check_interval', 1)
+        self.wait_for_disassociate = kwargs.get('wait_for_disassociate',
+                                                True)
+
+        # allocate floating
+        if not self.new_floating:
+            self._create_floating_ip()
+        # add security group
+        if not self.new_sec_grp:
+            self._create_sec_group()
+        # create vm
+        if not self.new_vm:
+            self._create_vm()
+
+    def wait_disassociate(self):
+        cli = self.manager.floating_ips_client
+
+        def func():
+            _, floating = cli.get_floating_ip_details(self.floating['id'])
+            return floating['instance_id'] is None
+
+        if not tempest.test.call_until_true(func, self.check_timeout,
+                                            self.check_interval):
+            raise RuntimeError("IP disassociate timeout!")
+
+    def run_core(self):
+        cli = self.manager.floating_ips_client
+        cli.associate_floating_ip_to_server(self.floating['ip'],
+                                            self.server_id)
+        for method in self.verify:
+            m = getattr(self, method)
+            m()
+        cli.disassociate_floating_ip_from_server(self.floating['ip'],
+                                                 self.server_id)
+        if self.wait_for_disassociate:
+            self.wait_disassociate()
+
+    def run(self):
+        if self.new_sec_grp:
+            self._create_sec_group()
+        if self.new_floating:
+            self._create_floating_ip()
+        if self.new_vm:
+            self._create_vm()
+        if self.reboot:
+            self.manager.servers_client.reboot(self.server_id, 'HARD')
+
+        self.run_core()
+
+        if self.new_vm:
+            self._destroy_vm()
+        if self.new_floating:
+            self._destroy_floating_ip()
+        if self.new_sec_grp:
+            self._destroy_sec_grp()
+
+    def tearDown(self):
+        if not self.new_vm:
+            self._destroy_vm()
+        if not self.new_floating:
+            self._destroy_floating_ip()
+        if not self.new_sec_grp:
+            self._destroy_sec_grp()
diff --git a/tempest/stress/actions/unit_test.py b/tempest/stress/actions/unit_test.py
index 95cc1bc..5ab5573 100644
--- a/tempest/stress/actions/unit_test.py
+++ b/tempest/stress/actions/unit_test.py
@@ -13,6 +13,7 @@
 #    under the License.
 
 from tempest.openstack.common import importutils
+from tempest.openstack.common import log as logging
 import tempest.stress.stressaction as stressaction
 
 
@@ -46,6 +47,7 @@
         method = kwargs['test_method'].split('.')
         self.test_method = method.pop()
         self.klass = importutils.import_class('.'.join(method))
+        self.logger = logging.getLogger('.'.join(method))
         # valid options are 'process', 'application' , 'action'
         self.class_setup_per = kwargs.get('class_setup_per',
                                           SetUpClassRunTime.process)
@@ -55,6 +57,12 @@
             self.klass.setUpClass()
         self.setupclass_called = False
 
+    @property
+    def action(self):
+        if self.test_method:
+            return self.test_method
+        return super(UnitTest, self).action
+
     def run_core(self):
         res = self.klass(self.test_method).run()
         if res.errors:
diff --git a/tempest/stress/driver.py b/tempest/stress/driver.py
index 5171da2..e518d28 100644
--- a/tempest/stress/driver.py
+++ b/tempest/stress/driver.py
@@ -148,7 +148,7 @@
 
             process = {'process': p,
                        'p_number': p_number,
-                       'action': test['action'],
+                       'action': test_run.action,
                        'statistic': shared_statistic}
 
             processes.append(process)
diff --git a/tempest/stress/etc/ssh_floating.json b/tempest/stress/etc/ssh_floating.json
new file mode 100644
index 0000000..0cb6776
--- /dev/null
+++ b/tempest/stress/etc/ssh_floating.json
@@ -0,0 +1,16 @@
+[{"action": "tempest.stress.actions.ssh_floating.FloatingStress",
+  "threads": 8,
+  "use_admin": false,
+  "use_isolated_tenants": false,
+  "kwargs": {"vm_extra_args": {},
+             "new_vm": true,
+             "new_sec_group": true,
+             "new_floating": true,
+             "verify": ["check_icmp_echo", "check_port_ssh"],
+             "check_timeout": 120,
+             "check_inerval": 1,
+             "wait_after_vm_create": true,
+             "wait_for_disassociate": true,
+             "reboot": false}
+}
+]
diff --git a/tempest/stress/run_stress.py b/tempest/stress/run_stress.py
index aab2afd..886d94b 100755
--- a/tempest/stress/run_stress.py
+++ b/tempest/stress/run_stress.py
@@ -17,16 +17,16 @@
 #    limitations under the License.
 
 import argparse
+import inspect
 import json
 import sys
 from testtools.testsuite import iterate_tests
 from unittest import loader
 
 
-def discover_stress_tests(path="./", filter_attr=None):
+def discover_stress_tests(path="./", filter_attr=None, call_inherited=False):
     """Discovers all tempest tests and create action out of them
     """
-
     tests = []
     testloader = loader.TestLoader()
     list = testloader.discover(path)
@@ -52,6 +52,11 @@
                                  "class_setup_per": class_setup_per
                                  }
                       }
+            if (not call_inherited and
+                getattr(test_func, "st_allow_inheritance") is not True):
+                class_structure = inspect.getmro(test_func.im_class)
+                if test_func.__name__ not in class_structure[0].__dict__:
+                    continue
             tests.append(action)
     return tests
 
@@ -63,7 +68,8 @@
     if not ns.all:
         tests = json.load(open(ns.tests, 'r'))
     else:
-        tests = discover_stress_tests(filter_attr=ns.type)
+        tests = discover_stress_tests(filter_attr=ns.type,
+                                      call_inherited=ns.call_inherited)
 
     if ns.serial:
         for test in tests:
@@ -79,22 +85,25 @@
     return result
 
 
-parser = argparse.ArgumentParser(description='Run stress tests. ')
+parser = argparse.ArgumentParser(description='Run stress tests')
 parser.add_argument('-d', '--duration', default=300, type=int,
-                    help="Duration of test in secs.")
+                    help="Duration of test in secs")
 parser.add_argument('-s', '--serial', action='store_true',
-                    help="Trigger running tests serially.")
+                    help="Trigger running tests serially")
 parser.add_argument('-S', '--stop', action='store_true',
-                    default=False, help="Stop on first error.")
+                    default=False, help="Stop on first error")
 parser.add_argument('-n', '--number', type=int,
-                    help="How often an action is executed for each process.")
+                    help="How often an action is executed for each process")
 group = parser.add_mutually_exclusive_group(required=True)
 group.add_argument('-a', '--all', action='store_true',
                    help="Execute all stress tests")
 parser.add_argument('-T', '--type',
                     help="Filters tests of a certain type (e.g. gate)")
+parser.add_argument('-i', '--call-inherited', action='store_true',
+                    default=False,
+                    help="Call also inherited function with stress attribute")
 group.add_argument('-t', "--tests", nargs='?',
-                   help="Name of the file with test description.")
+                   help="Name of the file with test description")
 
 if __name__ == "__main__":
     sys.exit(main(parser.parse_args()))
diff --git a/tempest/stress/stressaction.py b/tempest/stress/stressaction.py
index 6284cef..28251af 100644
--- a/tempest/stress/stressaction.py
+++ b/tempest/stress/stressaction.py
@@ -33,6 +33,13 @@
         self.tearDown()
         sys.exit(0)
 
+    @property
+    def action(self):
+        """This methods returns the action. Overload this if you
+        create a stress test wrapper.
+        """
+        return self.__class__.__name__
+
     def setUp(self, **kwargs):
         """This method is called before the run method
         to help the test initiatlize any structures.
diff --git a/tempest/test.py b/tempest/test.py
index 8b3cfa6..decae94 100644
--- a/tempest/test.py
+++ b/tempest/test.py
@@ -67,12 +67,17 @@
            ``application``: once in the stress job lifetime
            ``process``: once in the worker process lifetime
            ``action``: on each action
+    @param allow_inheritance: allows inheritance of this attribute
     """
     def decorator(f):
         if 'class_setup_per' in kwargs:
             setattr(f, "st_class_setup_per", kwargs['class_setup_per'])
         else:
             setattr(f, "st_class_setup_per", 'process')
+        if 'allow_inheritance' in kwargs:
+            setattr(f, "st_allow_inheritance", kwargs['allow_inheritance'])
+        else:
+            setattr(f, "st_allow_inheritance", False)
         attr(type='stress')(f)
         return f
     return decorator
@@ -141,7 +146,7 @@
 
     @classmethod
     def tearDownClass(cls):
-        at_exit_set.remove(cls)
+        at_exit_set.discard(cls)
         if hasattr(super(BaseTestCase, cls), 'tearDownClass'):
             super(BaseTestCase, cls).tearDownClass()
 
@@ -168,6 +173,11 @@
                 os.environ.get('OS_STDERR_CAPTURE') == '1'):
             stderr = self.useFixture(fixtures.StringStream('stderr')).stream
             self.useFixture(fixtures.MonkeyPatch('sys.stderr', stderr))
+        if (os.environ.get('OS_LOG_CAPTURE') != 'False' and
+            os.environ.get('OS_LOG_CAPTURE') != '0'):
+            log_format = '%(asctime)-15s %(message)s'
+            self.useFixture(fixtures.LoggerFixture(nuke_handlers=False,
+                                                   format=log_format))
 
     @classmethod
     def _get_identity_admin_client(cls):
diff --git a/tempest/thirdparty/boto/test_ec2_instance_run.py b/tempest/thirdparty/boto/test_ec2_instance_run.py
index 5007503..a848fc9 100644
--- a/tempest/thirdparty/boto/test_ec2_instance_run.py
+++ b/tempest/thirdparty/boto/test_ec2_instance_run.py
@@ -233,7 +233,7 @@
 
     # NOTE(afazekas): doctored test case,
     # with normal validation it would fail
-    @testtools.skip("Until Bug #1182679 is fixed")
+    @testtools.skip("Skipped until the Bug #1182679 is resolved.")
     @attr(type='smoke')
     def test_integration_1(self):
         # EC2 1. integration test (not strict)