Merge "Add API test for resizing a stopped server"
diff --git a/etc/tempest.conf.sample b/etc/tempest.conf.sample
index 28a4d1c..37d4d53 100644
--- a/etc/tempest.conf.sample
+++ b/etc/tempest.conf.sample
@@ -211,13 +211,14 @@
 # admin credentials are known. (boolean value)
 #allow_tenant_isolation=false
 
-# Valid primary image reference to be used in tests. (string
-# value)
-#image_ref={$IMAGE_ID}
+# Valid primary image reference to be used in tests. This is a
+# required option (string value)
+#image_ref=<None>
 
-# Valid secondary image reference to be used in tests. (string
-# value)
-#image_ref_alt={$IMAGE_ID_ALT}
+# Valid secondary image reference to be used in tests. This is
+# a required option, but if only one image is available
+# duplicate the value of image_ref above (string value)
+#image_ref_alt=<None>
 
 # Valid primary flavor to use in tests. (string value)
 #flavor_ref=1
@@ -241,7 +242,7 @@
 #image_alt_ssh_password=password
 
 # Time in seconds between build status checks. (integer value)
-#build_interval=10
+#build_interval=1
 
 # Timeout in seconds to wait for an instance to build.
 # (integer value)
@@ -332,6 +333,9 @@
 # admin credentials are known. (boolean value)
 #allow_tenant_isolation=false
 
+# Time in seconds between build status checks. (integer value)
+#build_interval=1
+
 
 [compute-admin]
 
@@ -705,7 +709,7 @@
 
 # Time in seconds between network operation status checks.
 # (integer value)
-#build_interval=10
+#build_interval=1
 
 
 [network-feature-enabled]
@@ -788,9 +792,6 @@
 # (string value)
 #endpoint_type=publicURL
 
-# Time in seconds between build status checks. (integer value)
-#build_interval=1
-
 # Timeout in seconds to wait for a stack to build. (integer
 # value)
 #build_timeout=1200
@@ -825,6 +826,10 @@
 # Catalog type of the Queuing service. (string value)
 #catalog_type=queuing
 
+# The maximum number of queue records per page when listing
+# queues (integer value)
+#max_queues_per_page=20
+
 
 [scenario]
 
@@ -980,7 +985,7 @@
 
 # Time in seconds between volume availability checks. (integer
 # value)
-#build_interval=10
+#build_interval=1
 
 # Timeout in seconds to wait for a volume to becomeavailable.
 # (integer value)
diff --git a/requirements.txt b/requirements.txt
index 75a61e7..f907e7d 100644
--- a/requirements.txt
+++ b/requirements.txt
@@ -5,19 +5,18 @@
 testtools>=0.9.34
 lxml>=2.3
 boto>=2.12.0,!=2.13.0
-paramiko>=1.9.0
+paramiko>=1.13.0
 netaddr>=0.7.6
 python-glanceclient>=0.9.0
 python-keystoneclient>=0.8.0
 python-novaclient>=2.17.0
 python-neutronclient>=2.3.4,<3
 python-cinderclient>=1.0.6
-python-heatclient>=0.2.3
+python-heatclient>=0.2.9
 python-ironicclient
 python-saharaclient>=0.6.0
 python-swiftclient>=2.0.2
 testresources>=0.2.4
-keyring>=2.1
 testrepository>=0.0.18
 oslo.config>=1.2.0
 six>=1.6.0
diff --git a/setup.cfg b/setup.cfg
index f4aa3e1..339da12 100644
--- a/setup.cfg
+++ b/setup.cfg
@@ -1,6 +1,6 @@
 [metadata]
 name = tempest
-version = 2014.1
+version = 2
 summary = OpenStack Integration Testing
 description-file =
     README.rst
@@ -20,6 +20,7 @@
 [entry_points]
 console_scripts =
     verify-tempest-config = tempest.cmd.verify_tempest_config:main
+    javelin2 = tempest.cmd.javelin:main
 
 [build_sphinx]
 all_files = 1
diff --git a/tempest/api/compute/base.py b/tempest/api/compute/base.py
index 44340c3..7c70aec 100644
--- a/tempest/api/compute/base.py
+++ b/tempest/api/compute/base.py
@@ -56,6 +56,7 @@
         cls.images = []
         cls.multi_user = cls.get_multi_user()
         cls.security_groups = []
+        cls.server_groups = []
 
         if cls._api_version == 2:
             cls.servers_client = cls.os.servers_client
@@ -191,11 +192,24 @@
                 LOG.exception(exc)
 
     @classmethod
+    def clear_server_groups(cls):
+        for server_group_id in cls.server_groups:
+            try:
+                cls.client.delete_server_group(server_group_id)
+            except exceptions.NotFound:
+                # The server-group may have already been deleted which is OK.
+                pass
+            except Exception:
+                LOG.exception('Exception raised deleting server-group %s',
+                              server_group_id)
+
+    @classmethod
     def tearDownClass(cls):
         cls.clear_images()
         cls.clear_servers()
         cls.clear_security_groups()
         cls.clear_isolated_creds()
+        cls.clear_server_groups()
         super(BaseComputeTest, cls).tearDownClass()
 
     @classmethod
@@ -249,6 +263,16 @@
 
         return resp, body
 
+    @classmethod
+    def create_test_server_group(cls, name="", policy=[]):
+        if not name:
+            name = data_utils.rand_name(cls.__name__ + "-Server-Group")
+        if not policy:
+            policy = ['affinity']
+        resp, body = cls.servers_client.create_server_group(name, policy)
+        cls.server_groups.append(body)
+        return resp, body
+
     def wait_for(self, condition):
         """Repeatedly calls condition() until a timeout."""
         start_time = int(time.time())
diff --git a/tempest/api/compute/security_groups/test_security_group_rules.py b/tempest/api/compute/security_groups/test_security_group_rules.py
index b04ab8a..35f6fc2 100644
--- a/tempest/api/compute/security_groups/test_security_group_rules.py
+++ b/tempest/api/compute/security_groups/test_security_group_rules.py
@@ -75,7 +75,6 @@
                                                    to_port,
                                                    cidr=cidr,
                                                    group_id=group_id)
-        self.addCleanup(self.client.delete_security_group_rule, rule['id'])
         self.assertEqual(200, resp.status)
 
     @test.attr(type='smoke')
@@ -95,8 +94,6 @@
                                                    ip_protocol1,
                                                    from_port1, to_port1)
         rule1_id = rule['id']
-        # Delete the Security Group rule1 at the end of this method
-        self.addCleanup(self.client.delete_security_group_rule, rule1_id)
 
         # Add a second rule to the created Security Group
         ip_protocol2 = 'icmp'
diff --git a/tempest/api/compute/security_groups/test_security_groups.py b/tempest/api/compute/security_groups/test_security_groups.py
index 3736f28..a077943 100644
--- a/tempest/api/compute/security_groups/test_security_groups.py
+++ b/tempest/api/compute/security_groups/test_security_groups.py
@@ -30,29 +30,31 @@
     def test_security_groups_create_list_delete(self):
         # Positive test:Should return the list of Security Groups
         # Create 3 Security Groups
+        security_group_list = []
         for i in range(3):
-            resp, securitygroup = self.create_security_group()
+            resp, body = self.create_security_group()
             self.assertEqual(200, resp.status)
+            security_group_list.append(body)
         # Fetch all Security Groups and verify the list
         # has all created Security Groups
         resp, fetched_list = self.client.list_security_groups()
         self.assertEqual(200, resp.status)
         # Now check if all the created Security Groups are in fetched list
         missing_sgs = \
-            [sg for sg in self.security_groups if sg not in fetched_list]
+            [sg for sg in security_group_list if sg not in fetched_list]
         self.assertFalse(missing_sgs,
                          "Failed to find Security Group %s in fetched "
                          "list" % ', '.join(m_group['name']
                                             for m_group in missing_sgs))
         # Delete all security groups
-        for sg in self.security_groups:
+        for sg in security_group_list:
             resp, _ = self.client.delete_security_group(sg['id'])
             self.assertEqual(202, resp.status)
             self.client.wait_for_resource_deletion(sg['id'])
         # Now check if all the created Security Groups are deleted
         resp, fetched_list = self.client.list_security_groups()
         deleted_sgs = \
-            [sg for sg in self.security_groups if sg in fetched_list]
+            [sg for sg in security_group_list if sg in fetched_list]
         self.assertFalse(deleted_sgs,
                          "Failed to delete Security Group %s "
                          "list" % ', '.join(m_group['name']
@@ -78,6 +80,9 @@
         self.assertEqual(securitygroup, fetched_group,
                          "The fetched Security Group is different "
                          "from the created Group")
+        resp, _ = self.client.delete_security_group(securitygroup['id'])
+        self.assertEqual(202, resp.status)
+        self.client.wait_for_resource_deletion(securitygroup['id'])
 
     @test.attr(type='smoke')
     def test_server_security_groups(self):
@@ -120,9 +125,9 @@
         self.servers_client.delete_server(server_id)
         self.servers_client.wait_for_server_termination(server_id)
 
-        self.client.delete_security_group(sg['id'])
+        resp, _ = self.client.delete_security_group(sg['id'])
         self.assertEqual(202, resp.status)
-        self.client.delete_security_group(sg2['id'])
+        resp, _ = self.client.delete_security_group(sg2['id'])
         self.assertEqual(202, resp.status)
 
     @test.attr(type='smoke')
diff --git a/tempest/api/compute/servers/test_list_servers_negative.py b/tempest/api/compute/servers/test_list_servers_negative.py
index 768cc11..28d64fb 100644
--- a/tempest/api/compute/servers/test_list_servers_negative.py
+++ b/tempest/api/compute/servers/test_list_servers_negative.py
@@ -13,8 +13,6 @@
 #    License for the specific language governing permissions and limitations
 #    under the License.
 
-import datetime
-
 from six import moves
 
 from tempest.api.compute import base
@@ -37,9 +35,8 @@
         # tearDownClass method of the super-class.
         cls.existing_fixtures = []
         cls.deleted_fixtures = []
-        cls.start_time = datetime.datetime.utcnow()
         for x in moves.xrange(2):
-            resp, srv = cls.create_test_server()
+            resp, srv = cls.create_test_server(wait_until='ACTIVE')
             cls.existing_fixtures.append(srv)
 
         resp, srv = cls.create_test_server()
@@ -127,19 +124,6 @@
         self.assertRaises(exceptions.BadRequest, self.client.list_servers,
                           {'limit': -1})
 
-    @test.attr(type='gate')
-    def test_list_servers_by_changes_since(self):
-        # Servers are listed by specifying changes-since date
-        changes_since = {'changes-since': self.start_time.isoformat()}
-        resp, body = self.client.list_servers(changes_since)
-        self.assertEqual('200', resp['status'])
-        # changes-since returns all instances, including deleted.
-        num_expected = (len(self.existing_fixtures) +
-                        len(self.deleted_fixtures))
-        self.assertEqual(num_expected, len(body['servers']),
-                         "Number of servers %d is wrong in %s" %
-                         (num_expected, body['servers']))
-
     @test.attr(type=['negative', 'gate'])
     def test_list_servers_by_changes_since_invalid_date(self):
         # Return an error when invalid date format is passed
diff --git a/tempest/api/compute/servers/test_server_actions.py b/tempest/api/compute/servers/test_server_actions.py
index d0fd876..0e32e60 100644
--- a/tempest/api/compute/servers/test_server_actions.py
+++ b/tempest/api/compute/servers/test_server_actions.py
@@ -32,28 +32,16 @@
     run_ssh = CONF.compute.run_ssh
 
     def setUp(self):
-        # NOTE(afazekas): Normally we use the same server with all test cases,
-        # but if it has an issue, we build a new one
         super(ServerActionsTestJSON, self).setUp()
-        # Check if the server is in a clean state after test
-        try:
-            self.client.wait_for_server_status(self.server_id, 'ACTIVE')
-        except Exception:
-            # Rebuild server if something happened to it during a test
-            self.__class__.server_id = self.rebuild_server(self.server_id)
-
-    def tearDown(self):
-        _, server = self.client.get_server(self.server_id)
-        self.assertEqual(self.image_ref, server['image']['id'])
-        self.server_check_teardown()
-        super(ServerActionsTestJSON, self).tearDown()
+        resp, server = self.create_test_server(wait_until='ACTIVE')
+        self.addCleanup(self.client.delete_server, server['id'])
+        self.server_id = server['id']
 
     @classmethod
     def setUpClass(cls):
         cls.prepare_instance_network()
         super(ServerActionsTestJSON, cls).setUpClass()
         cls.client = cls.servers_client
-        cls.server_id = cls.rebuild_server(None)
 
     @testtools.skipUnless(CONF.compute_feature_enabled.change_password,
                           'Change password not available.')
diff --git a/tempest/api/compute/servers/test_server_group.py b/tempest/api/compute/servers/test_server_group.py
new file mode 100644
index 0000000..0cd23fd
--- /dev/null
+++ b/tempest/api/compute/servers/test_server_group.py
@@ -0,0 +1,112 @@
+# Copyright 2014 NEC Technologies India Ltd.
+# All Rights Reserved.
+#
+#    Licensed under the Apache License, Version 2.0 (the "License"); you may
+#    not use this file except in compliance with the License. You may obtain
+#    a copy of the License at
+#
+#         http://www.apache.org/licenses/LICENSE-2.0
+#
+#    Unless required by applicable law or agreed to in writing, software
+#    distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+#    WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
+#    License for the specific language governing permissions and limitations
+#    under the License.
+
+from tempest.api.compute import base
+from tempest.common.utils import data_utils
+from tempest import test
+
+
+class ServerGroupTestJSON(base.BaseV2ComputeTest):
+    """
+    These tests check for the server-group APIs
+    They create/delete server-groups with different policies.
+    policies = affinity/anti-affinity
+    It also adds the tests for list and get details of server-groups
+    """
+    @classmethod
+    @test.safe_setup
+    def setUpClass(cls):
+        super(ServerGroupTestJSON, cls).setUpClass()
+        if not test.is_extension_enabled('os-server-groups', 'compute'):
+            msg = "os-server-groups extension is not enabled."
+            raise cls.skipException(msg)
+        cls.client = cls.servers_client
+        server_group_name = data_utils.rand_name('server-group')
+        cls.policy = ['affinity']
+
+        _, cls.created_server_group = cls.create_test_server_group(
+            server_group_name,
+            cls.policy)
+
+    def _create_server_group(self, name, policy):
+        # create the test server-group with given policy
+        server_group = {'name': name, 'policies': policy}
+        resp, body = self.create_test_server_group(name, policy)
+        self.assertEqual(200, resp.status)
+        for key in ['name', 'policies']:
+            self.assertEqual(server_group[key], body[key])
+        return body
+
+    def _delete_server_group(self, server_group):
+        # delete the test server-group
+        resp, _ = self.client.delete_server_group(server_group['id'])
+        self.assertEqual(204, resp.status)
+        # validation of server-group deletion
+        resp, server_group_list = self.client.list_server_groups()
+        self.assertEqual(200, resp.status)
+        self.assertNotIn(server_group, server_group_list)
+
+    def _create_delete_server_group(self, policy):
+        # Create and Delete the server-group with given policy
+        name = data_utils.rand_name('server-group')
+        server_group = self._create_server_group(name, policy)
+        self._delete_server_group(server_group)
+
+    @test.attr(type='gate')
+    def test_create_delete_server_group_with_affinity_policy(self):
+        # Create and Delete the server-group with affinity policy
+        self._create_delete_server_group(self.policy)
+
+    @test.attr(type='gate')
+    def test_create_delete_server_group_with_anti_affinity_policy(self):
+        # Create and Delete the server-group with anti-affinity policy
+        policy = ['anti-affinity']
+        self._create_delete_server_group(policy)
+
+    @test.attr(type='gate')
+    def test_create_delete_server_group_with_multiple_policies(self):
+        # Create and Delete the server-group with multiple policies
+        policies = ['affinity', 'affinity']
+        self._create_delete_server_group(policies)
+
+    @test.attr(type='gate')
+    def test_create_delete_multiple_server_groups_with_same_name_policy(self):
+        # Create and Delete the server-groups with same name and same policy
+        server_groups = []
+        server_group_name = data_utils.rand_name('server-group')
+        for i in range(0, 2):
+            server_groups.append(self._create_server_group(server_group_name,
+                                                           self.policy))
+        for key in ['name', 'policies']:
+            self.assertEqual(server_groups[0][key], server_groups[1][key])
+        self.assertNotEqual(server_groups[0]['id'], server_groups[1]['id'])
+
+        for i in range(0, 2):
+            self._delete_server_group(server_groups[i])
+
+    @test.attr(type='gate')
+    def test_get_server_group(self):
+        # Get the server-group
+        resp, body = self.client.get_server_group(
+            self.created_server_group['id'])
+        self.assertEqual(200, resp.status)
+        self.assertEqual(self.created_server_group, body)
+
+    @test.attr(type='gate')
+    def test_list_server_groups(self):
+        # List the server-group
+        resp, body = self.client.list_server_groups()
+        self.assertEqual(200, resp.status)
+        self.assertIn(self.created_server_group, body)
diff --git a/tempest/api/compute/v3/admin/test_availability_zone_negative.py b/tempest/api/compute/v3/admin/test_availability_zone_negative.py
index f3af6df..b012e65 100644
--- a/tempest/api/compute/v3/admin/test_availability_zone_negative.py
+++ b/tempest/api/compute/v3/admin/test_availability_zone_negative.py
@@ -15,7 +15,7 @@
 
 from tempest.api.compute import base
 from tempest import exceptions
-from tempest.test import attr
+from tempest import test
 
 
 class AZAdminNegativeV3Test(base.BaseV3ComputeAdminTest):
@@ -30,7 +30,7 @@
         cls.client = cls.availability_zone_admin_client
         cls.non_adm_client = cls.availability_zone_client
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_get_availability_zone_list_detail_with_non_admin_user(self):
         # List of availability zones and available services with
         # non-administrator user
diff --git a/tempest/api/compute/v3/admin/test_hypervisor.py b/tempest/api/compute/v3/admin/test_hypervisor.py
index 93d4441..f3397a8 100644
--- a/tempest/api/compute/v3/admin/test_hypervisor.py
+++ b/tempest/api/compute/v3/admin/test_hypervisor.py
@@ -14,7 +14,7 @@
 #    under the License.
 
 from tempest.api.compute import base
-from tempest.test import attr
+from tempest import test
 
 
 class HypervisorAdminV3Test(base.BaseV3ComputeAdminTest):
@@ -34,20 +34,20 @@
         self.assertEqual(200, resp.status)
         return hypers
 
-    @attr(type='gate')
+    @test.attr(type='gate')
     def test_get_hypervisor_list(self):
         # List of hypervisor and available hypervisors hostname
         hypers = self._list_hypervisors()
         self.assertTrue(len(hypers) > 0)
 
-    @attr(type='gate')
+    @test.attr(type='gate')
     def test_get_hypervisor_list_details(self):
         # Display the details of the all hypervisor
         resp, hypers = self.client.get_hypervisor_list_details()
         self.assertEqual(200, resp.status)
         self.assertTrue(len(hypers) > 0)
 
-    @attr(type='gate')
+    @test.attr(type='gate')
     def test_get_hypervisor_show_details(self):
         # Display the details of the specified hypervisor
         hypers = self._list_hypervisors()
@@ -60,7 +60,7 @@
         self.assertEqual(details['hypervisor_hostname'],
                          hypers[0]['hypervisor_hostname'])
 
-    @attr(type='gate')
+    @test.attr(type='gate')
     def test_get_hypervisor_show_servers(self):
         # Show instances about the specific hypervisors
         hypers = self._list_hypervisors()
@@ -71,14 +71,14 @@
         self.assertEqual(200, resp.status)
         self.assertTrue(len(hypervisors) > 0)
 
-    @attr(type='gate')
+    @test.attr(type='gate')
     def test_get_hypervisor_stats(self):
         # Verify the stats of the all hypervisor
         resp, stats = self.client.get_hypervisor_stats()
         self.assertEqual(200, resp.status)
         self.assertTrue(len(stats) > 0)
 
-    @attr(type='gate')
+    @test.attr(type='gate')
     def test_get_hypervisor_uptime(self):
         # Verify that GET shows the specified hypervisor uptime
         hypers = self._list_hypervisors()
@@ -87,7 +87,7 @@
         self.assertEqual(200, resp.status)
         self.assertTrue(len(uptime) > 0)
 
-    @attr(type='gate')
+    @test.attr(type='gate')
     def test_search_hypervisor(self):
         hypers = self._list_hypervisors()
         self.assertTrue(len(hypers) > 0)
diff --git a/tempest/api/compute/v3/admin/test_hypervisor_negative.py b/tempest/api/compute/v3/admin/test_hypervisor_negative.py
index 45642b7..ae4df15 100644
--- a/tempest/api/compute/v3/admin/test_hypervisor_negative.py
+++ b/tempest/api/compute/v3/admin/test_hypervisor_negative.py
@@ -18,7 +18,7 @@
 from tempest.api.compute import base
 from tempest.common.utils import data_utils
 from tempest import exceptions
-from tempest.test import attr
+from tempest import test
 
 
 class HypervisorAdminNegativeV3Test(base.BaseV3ComputeAdminTest):
@@ -39,7 +39,7 @@
         self.assertEqual(200, resp.status)
         return hypers
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_show_nonexistent_hypervisor(self):
         nonexistent_hypervisor_id = str(uuid.uuid4())
 
@@ -48,7 +48,7 @@
             self.client.get_hypervisor_show_details,
             nonexistent_hypervisor_id)
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_show_hypervisor_with_non_admin_user(self):
         hypers = self._list_hypervisors()
         self.assertTrue(len(hypers) > 0)
@@ -58,7 +58,7 @@
             self.non_adm_client.get_hypervisor_show_details,
             hypers[0]['id'])
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_show_servers_with_non_admin_user(self):
         hypers = self._list_hypervisors()
         self.assertTrue(len(hypers) > 0)
@@ -68,7 +68,7 @@
             self.non_adm_client.get_hypervisor_servers,
             hypers[0]['id'])
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_show_servers_with_nonexistent_hypervisor(self):
         nonexistent_hypervisor_id = str(uuid.uuid4())
 
@@ -77,13 +77,13 @@
             self.client.get_hypervisor_servers,
             nonexistent_hypervisor_id)
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_get_hypervisor_stats_with_non_admin_user(self):
         self.assertRaises(
             exceptions.Unauthorized,
             self.non_adm_client.get_hypervisor_stats)
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_get_nonexistent_hypervisor_uptime(self):
         nonexistent_hypervisor_id = str(uuid.uuid4())
 
@@ -92,7 +92,7 @@
             self.client.get_hypervisor_uptime,
             nonexistent_hypervisor_id)
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_get_hypervisor_uptime_with_non_admin_user(self):
         hypers = self._list_hypervisors()
         self.assertTrue(len(hypers) > 0)
@@ -102,21 +102,21 @@
             self.non_adm_client.get_hypervisor_uptime,
             hypers[0]['id'])
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_get_hypervisor_list_with_non_admin_user(self):
         # List of hypervisor and available services with non admin user
         self.assertRaises(
             exceptions.Unauthorized,
             self.non_adm_client.get_hypervisor_list)
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_get_hypervisor_list_details_with_non_admin_user(self):
         # List of hypervisor details and available services with non admin user
         self.assertRaises(
             exceptions.Unauthorized,
             self.non_adm_client.get_hypervisor_list_details)
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_search_nonexistent_hypervisor(self):
         nonexistent_hypervisor_name = data_utils.rand_name('test_hypervisor')
 
@@ -125,7 +125,7 @@
         self.assertEqual(200, resp.status)
         self.assertEqual(0, len(hypers))
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_search_hypervisor_with_non_admin_user(self):
         hypers = self._list_hypervisors()
         self.assertTrue(len(hypers) > 0)
diff --git a/tempest/api/compute/v3/admin/test_servers_negative.py b/tempest/api/compute/v3/admin/test_servers_negative.py
index a46da47..a971463 100644
--- a/tempest/api/compute/v3/admin/test_servers_negative.py
+++ b/tempest/api/compute/v3/admin/test_servers_negative.py
@@ -20,7 +20,7 @@
 from tempest.common.utils import data_utils
 from tempest import config
 from tempest import exceptions
-from tempest.test import attr
+from tempest import test
 
 CONF = config.CONF
 
@@ -54,7 +54,7 @@
             flavor_id = data_utils.rand_int_id(start=1000)
         return flavor_id
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_resize_server_using_overlimit_ram(self):
         flavor_name = data_utils.rand_name("flavor-")
         flavor_id = self._get_unused_flavor_id()
@@ -72,7 +72,7 @@
                           self.servers[0]['id'],
                           flavor_ref['id'])
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_resize_server_using_overlimit_vcpus(self):
         flavor_name = data_utils.rand_name("flavor-")
         flavor_id = self._get_unused_flavor_id()
@@ -90,31 +90,31 @@
                           self.servers[0]['id'],
                           flavor_ref['id'])
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_reset_state_server_invalid_state(self):
         self.assertRaises(exceptions.BadRequest,
                           self.client.reset_state, self.s1_id,
                           state='invalid')
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_reset_state_server_invalid_type(self):
         self.assertRaises(exceptions.BadRequest,
                           self.client.reset_state, self.s1_id,
                           state=1)
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_reset_state_server_nonexistent_server(self):
         self.assertRaises(exceptions.NotFound,
                           self.client.reset_state, '999')
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_get_server_diagnostics_by_non_admin(self):
         # Non-admin user can not view server diagnostics according to policy
         self.assertRaises(exceptions.Unauthorized,
                           self.non_adm_client.get_server_diagnostics,
                           self.s1_id)
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_migrate_non_existent_server(self):
         # migrate a non existent server
         self.assertRaises(exceptions.NotFound,
@@ -123,7 +123,7 @@
 
     @testtools.skipUnless(CONF.compute_feature_enabled.suspend,
                           'Suspend is not available.')
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_migrate_server_invalid_state(self):
         # create server.
         resp, server = self.create_test_server(wait_until='ACTIVE')
diff --git a/tempest/api/compute/v3/admin/test_services.py b/tempest/api/compute/v3/admin/test_services.py
index b367dad..e6efb70 100644
--- a/tempest/api/compute/v3/admin/test_services.py
+++ b/tempest/api/compute/v3/admin/test_services.py
@@ -15,7 +15,7 @@
 #    under the License.
 
 from tempest.api.compute import base
-from tempest.test import attr
+from tempest import test
 
 
 class ServicesAdminV3Test(base.BaseV3ComputeAdminTest):
@@ -29,13 +29,13 @@
         super(ServicesAdminV3Test, cls).setUpClass()
         cls.client = cls.services_admin_client
 
-    @attr(type='gate')
+    @test.attr(type='gate')
     def test_list_services(self):
         resp, services = self.client.list_services()
         self.assertEqual(200, resp.status)
         self.assertNotEqual(0, len(services))
 
-    @attr(type='gate')
+    @test.attr(type='gate')
     def test_get_service_by_service_binary_name(self):
         binary_name = 'nova-compute'
         params = {'binary': binary_name}
@@ -45,7 +45,7 @@
         for service in services:
             self.assertEqual(binary_name, service['binary'])
 
-    @attr(type='gate')
+    @test.attr(type='gate')
     def test_get_service_by_host_name(self):
         resp, services = self.client.list_services()
         self.assertEqual(200, resp.status)
@@ -65,7 +65,7 @@
         # on order.
         self.assertEqual(sorted(s1), sorted(s2))
 
-    @attr(type='gate')
+    @test.attr(type='gate')
     def test_get_service_by_service_and_host_name(self):
         resp, services = self.client.list_services()
         host_name = services[0]['host']
diff --git a/tempest/api/compute/v3/admin/test_services_negative.py b/tempest/api/compute/v3/admin/test_services_negative.py
index 3168af2..6ac78d4 100644
--- a/tempest/api/compute/v3/admin/test_services_negative.py
+++ b/tempest/api/compute/v3/admin/test_services_negative.py
@@ -16,7 +16,7 @@
 
 from tempest.api.compute import base
 from tempest import exceptions
-from tempest.test import attr
+from tempest import test
 
 
 class ServicesAdminNegativeV3Test(base.BaseV3ComputeAdminTest):
@@ -31,12 +31,12 @@
         cls.client = cls.services_admin_client
         cls.non_admin_client = cls.services_client
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_list_services_with_non_admin_user(self):
         self.assertRaises(exceptions.Unauthorized,
                           self.non_admin_client.list_services)
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_get_service_by_invalid_params(self):
         # return all services if send the request with invalid parameter
         resp, services = self.client.list_services()
@@ -45,7 +45,7 @@
         self.assertEqual(200, resp.status)
         self.assertEqual(len(services), len(services_xxx))
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_get_service_by_invalid_service_and_valid_host(self):
         resp, services = self.client.list_services()
         host_name = services[0]['host']
@@ -54,7 +54,7 @@
         self.assertEqual(200, resp.status)
         self.assertEqual(0, len(services))
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_get_service_with_valid_service_and_invalid_host(self):
         resp, services = self.client.list_services()
         binary_name = services[0]['binary']
diff --git a/tempest/api/compute/v3/servers/test_attach_interfaces.py b/tempest/api/compute/v3/servers/test_attach_interfaces.py
index c848f8c..43440c1 100644
--- a/tempest/api/compute/v3/servers/test_attach_interfaces.py
+++ b/tempest/api/compute/v3/servers/test_attach_interfaces.py
@@ -16,7 +16,7 @@
 from tempest.api.compute import base
 from tempest import config
 from tempest import exceptions
-from tempest.test import attr
+from tempest import test
 
 import time
 
@@ -106,7 +106,7 @@
 
         self.assertEqual(sorted(list1), sorted(list2))
 
-    @attr(type='smoke')
+    @test.attr(type='smoke')
     def test_create_list_show_delete_interfaces(self):
         server, ifs = self._create_server_get_interfaces()
         interface_count = len(ifs)
@@ -127,7 +127,7 @@
         _ifs = self._test_delete_interface(server, ifs)
         self.assertEqual(len(ifs) - 1, len(_ifs))
 
-    @attr(type='smoke')
+    @test.attr(type='smoke')
     def test_add_remove_fixed_ip(self):
         # Add and Remove the fixed IP to server.
         server, ifs = self._create_server_get_interfaces()
diff --git a/tempest/api/compute/v3/servers/test_list_servers_negative.py b/tempest/api/compute/v3/servers/test_list_servers_negative.py
index 9cbc4e0..18e5c67 100644
--- a/tempest/api/compute/v3/servers/test_list_servers_negative.py
+++ b/tempest/api/compute/v3/servers/test_list_servers_negative.py
@@ -39,7 +39,7 @@
         cls.deleted_fixtures = []
         cls.start_time = datetime.datetime.utcnow()
         for x in moves.xrange(2):
-            resp, srv = cls.create_test_server()
+            resp, srv = cls.create_test_server(wait_until='ACTIVE')
             cls.existing_fixtures.append(srv)
 
         resp, srv = cls.create_test_server()
diff --git a/tempest/api/compute/v3/servers/test_server_actions.py b/tempest/api/compute/v3/servers/test_server_actions.py
index e098311..f7c3411 100644
--- a/tempest/api/compute/v3/servers/test_server_actions.py
+++ b/tempest/api/compute/v3/servers/test_server_actions.py
@@ -30,15 +30,10 @@
     run_ssh = CONF.compute.run_ssh
 
     def setUp(self):
-        # NOTE(afazekas): Normally we use the same server with all test cases,
-        # but if it has an issue, we build a new one
         super(ServerActionsV3Test, self).setUp()
-        # Check if the server is in a clean state after test
-        try:
-            self.client.wait_for_server_status(self.server_id, 'ACTIVE')
-        except Exception:
-            # Rebuild server if something happened to it during a test
-            self.__class__.server_id = self.rebuild_server(self.server_id)
+        resp, server = self.create_test_server(wait_until='ACTIVE')
+        self.addCleanup(self.client.delete_server, server['id'])
+        self.server_id = server['id']
 
     def tearDown(self):
         _, server = self.client.get_server(self.server_id)
@@ -51,7 +46,6 @@
         cls.prepare_instance_network()
         super(ServerActionsV3Test, cls).setUpClass()
         cls.client = cls.servers_client
-        cls.server_id = cls.rebuild_server(None)
 
     @testtools.skipUnless(CONF.compute_feature_enabled.change_password,
                           'Change password not available.')
diff --git a/tempest/api/compute/v3/test_live_block_migration.py b/tempest/api/compute/v3/test_live_block_migration.py
index 33d2bd9..6ca37e6 100644
--- a/tempest/api/compute/v3/test_live_block_migration.py
+++ b/tempest/api/compute/v3/test_live_block_migration.py
@@ -17,7 +17,7 @@
 
 from tempest.api.compute import base
 from tempest import config
-from tempest.test import attr
+from tempest import test
 
 CONF = config.CONF
 
@@ -85,7 +85,7 @@
 
     @testtools.skipIf(not CONF.compute_feature_enabled.live_migration,
                       'Live migration not available')
-    @attr(type='gate')
+    @test.attr(type='gate')
     def test_live_block_migration(self):
         # Live block migrate an instance to another host
         if len(self._get_compute_hostnames()) < 2:
@@ -105,7 +105,7 @@
     @testtools.skipIf(not CONF.compute_feature_enabled.
                       block_migrate_cinder_iscsi,
                       'Block Live migration not configured for iSCSI')
-    @attr(type='gate')
+    @test.attr(type='gate')
     def test_iscsi_volume(self):
         # Live block migrate an instance to another host
         if len(self._get_compute_hostnames()) < 2:
diff --git a/tempest/api/compute/volumes/test_volumes_list.py b/tempest/api/compute/volumes/test_volumes_list.py
index 9867c64..25a8547 100644
--- a/tempest/api/compute/volumes/test_volumes_list.py
+++ b/tempest/api/compute/volumes/test_volumes_list.py
@@ -16,7 +16,7 @@
 from tempest.api.compute import base
 from tempest.common.utils import data_utils
 from tempest import config
-from tempest.test import attr
+from tempest import test
 
 CONF = config.CONF
 
@@ -75,7 +75,7 @@
             cls.delete_volume(volume['id'])
         super(VolumesTestJSON, cls).tearDownClass()
 
-    @attr(type='gate')
+    @test.attr(type='gate')
     def test_volume_list(self):
         # Should return the list of Volumes
         # Fetch all Volumes
@@ -91,7 +91,7 @@
                          ', '.join(m_vol['displayName']
                                    for m_vol in missing_volumes))
 
-    @attr(type='gate')
+    @test.attr(type='gate')
     def test_volume_list_with_details(self):
         # Should return the list of Volumes with details
         # Fetch all Volumes
@@ -107,7 +107,7 @@
                          ', '.join(m_vol['displayName']
                                    for m_vol in missing_volumes))
 
-    @attr(type='gate')
+    @test.attr(type='gate')
     def test_volume_list_param_limit(self):
         # Return the list of volumes based on limit set
         params = {'limit': 2}
@@ -117,7 +117,7 @@
         self.assertEqual(len(fetched_vol_list), params['limit'],
                          "Failed to list volumes by limit set")
 
-    @attr(type='gate')
+    @test.attr(type='gate')
     def test_volume_list_with_detail_param_limit(self):
         # Return the list of volumes with details based on limit set.
         params = {'limit': 2}
@@ -128,7 +128,7 @@
         self.assertEqual(len(fetched_vol_list), params['limit'],
                          "Failed to list volume details by limit set")
 
-    @attr(type='gate')
+    @test.attr(type='gate')
     def test_volume_list_param_offset_and_limit(self):
         # Return the list of volumes based on offset and limit set.
         # get all volumes list
@@ -146,7 +146,7 @@
                              all_vol_list[index + params['offset']]['id'],
                              "Failed to list volumes by offset and limit")
 
-    @attr(type='gate')
+    @test.attr(type='gate')
     def test_volume_list_with_detail_param_offset_and_limit(self):
         # Return the list of volumes details based on offset and limit set.
         # get all volumes list
diff --git a/tempest/api/compute/volumes/test_volumes_negative.py b/tempest/api/compute/volumes/test_volumes_negative.py
index cecaf62..5dfbad7 100644
--- a/tempest/api/compute/volumes/test_volumes_negative.py
+++ b/tempest/api/compute/volumes/test_volumes_negative.py
@@ -19,7 +19,7 @@
 from tempest.common.utils import data_utils
 from tempest import config
 from tempest import exceptions
-from tempest.test import attr
+from tempest import test
 
 CONF = config.CONF
 
@@ -34,7 +34,7 @@
             skip_msg = ("%s skipped as Cinder is not available" % cls.__name__)
             raise cls.skipException(skip_msg)
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_volume_get_nonexistent_volume_id(self):
         # Negative: Should not be able to get details of nonexistent volume
         # Creating a nonexistent volume id
@@ -42,7 +42,7 @@
         self.assertRaises(exceptions.NotFound, self.client.get_volume,
                           str(uuid.uuid4()))
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_volume_delete_nonexistent_volume_id(self):
         # Negative: Should not be able to delete nonexistent Volume
         # Creating nonexistent volume id
@@ -50,7 +50,7 @@
         self.assertRaises(exceptions.NotFound, self.client.delete_volume,
                           str(uuid.uuid4()))
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_create_volume_with_invalid_size(self):
         # Negative: Should not be able to create volume with invalid size
         # in request
@@ -59,7 +59,7 @@
         self.assertRaises(exceptions.BadRequest, self.client.create_volume,
                           size='#$%', display_name=v_name, metadata=metadata)
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_create_volume_with_out_passing_size(self):
         # Negative: Should not be able to create volume without passing size
         # in request
@@ -68,7 +68,7 @@
         self.assertRaises(exceptions.BadRequest, self.client.create_volume,
                           size='', display_name=v_name, metadata=metadata)
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_create_volume_with_size_zero(self):
         # Negative: Should not be able to create volume with size zero
         v_name = data_utils.rand_name('Volume-')
@@ -76,25 +76,25 @@
         self.assertRaises(exceptions.BadRequest, self.client.create_volume,
                           size='0', display_name=v_name, metadata=metadata)
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_get_invalid_volume_id(self):
         # Negative: Should not be able to get volume with invalid id
         self.assertRaises(exceptions.NotFound,
                           self.client.get_volume, '#$%%&^&^')
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_get_volume_without_passing_volume_id(self):
         # Negative: Should not be able to get volume when empty ID is passed
         self.assertRaises(exceptions.NotFound, self.client.get_volume, '')
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_delete_invalid_volume_id(self):
         # Negative: Should not be able to delete volume when invalid ID is
         # passed
         self.assertRaises(exceptions.NotFound,
                           self.client.delete_volume, '!@#$%^&*()')
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_delete_volume_without_passing_volume_id(self):
         # Negative: Should not be able to delete volume when empty ID is passed
         self.assertRaises(exceptions.NotFound, self.client.delete_volume, '')
diff --git a/tempest/api/data_processing/base.py b/tempest/api/data_processing/base.py
index 74444d7..cc76880 100644
--- a/tempest/api/data_processing/base.py
+++ b/tempest/api/data_processing/base.py
@@ -1,17 +1,16 @@
-# Copyright (c) 2013 Mirantis Inc.
+# Copyright (c) 2014 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
+#    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
+#         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.
+#    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 import exceptions
@@ -39,6 +38,7 @@
         cls._node_group_templates = []
         cls._cluster_templates = []
         cls._data_sources = []
+        cls._job_binary_internals = []
 
     @classmethod
     def tearDownClass(cls):
@@ -48,6 +48,8 @@
                               cls.client.delete_node_group_template)
         cls.cleanup_resources(getattr(cls, '_data_sources', []),
                               cls.client.delete_data_source)
+        cls.cleanup_resources(getattr(cls, '_job_binary_internals', []),
+                              cls.client.delete_job_binary_internal)
         cls.clear_isolated_creds()
         super(BaseDataProcessingTest, cls).tearDownClass()
 
@@ -113,3 +115,16 @@
         cls._data_sources.append(body['id'])
 
         return resp, body
+
+    @classmethod
+    def create_job_binary_internal(cls, name, data):
+        """Creates watched job binary internal with specified params.
+
+        It returns created object. All resources created in this method will
+        be automatically removed in tearDownClass method.
+        """
+        resp, body = cls.client.create_job_binary_internal(name, data)
+        # store id of created job binary internal
+        cls._job_binary_internals.append(body['id'])
+
+        return resp, body
diff --git a/tempest/api/data_processing/test_data_sources.py b/tempest/api/data_processing/test_data_sources.py
new file mode 100644
index 0000000..c72e828
--- /dev/null
+++ b/tempest/api/data_processing/test_data_sources.py
@@ -0,0 +1,154 @@
+# Copyright (c) 2014 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.
+
+from tempest.api.data_processing import base as dp_base
+from tempest.common.utils import data_utils
+from tempest import config
+from tempest import test
+
+CONF = config.CONF
+
+
+class DataSourceTest(dp_base.BaseDataProcessingTest):
+    @classmethod
+    def setUpClass(cls):
+        super(DataSourceTest, cls).setUpClass()
+        cls.swift_data_source_with_creds = {
+            'url': 'swift://sahara-container.sahara/input-source',
+            'description': 'Test data source',
+            'credentials': {
+                'user': CONF.identity.username,
+                'password': CONF.identity.password
+            },
+            'type': 'swift'
+        }
+        cls.swift_data_source = cls.swift_data_source_with_creds.copy()
+        del cls.swift_data_source['credentials']
+
+        cls.local_hdfs_data_source = {
+            'url': 'input-source',
+            'description': 'Test data source',
+            'type': 'hdfs'
+        }
+
+        cls.external_hdfs_data_source = {
+            'url': 'hdfs://172.18.168.2:8020/usr/hadoop/input-source',
+            'description': 'Test data source',
+            'type': 'hdfs'
+        }
+
+    def _create_data_source(self, source_body, source_name=None):
+        """Creates Data Source with optional name specified.
+
+        It creates a link to input-source file (it may not exist) and ensures
+        response status and source name. Returns id and name of created source.
+        """
+        if not source_name:
+            # generate random name if it's not specified
+            source_name = data_utils.rand_name('sahara-data-source')
+
+        # create data source
+        resp, body = self.create_data_source(source_name, **source_body)
+
+        # ensure that source created successfully
+        self.assertEqual(202, resp.status)
+        self.assertEqual(source_name, body['name'])
+        if source_body['type'] == 'swift':
+            source_body = self.swift_data_source
+        self.assertDictContainsSubset(source_body, body)
+
+        return body['id'], source_name
+
+    def _list_data_sources(self, source_info):
+        # check for data source in list
+        resp, sources = self.client.list_data_sources()
+        self.assertEqual(200, resp.status)
+        sources_info = [(source['id'], source['name']) for source in sources]
+        self.assertIn(source_info, sources_info)
+
+    def _get_data_source(self, source_id, source_name, source_body):
+        # check data source fetch by id
+        resp, source = self.client.get_data_source(source_id)
+        self.assertEqual(200, resp.status)
+        self.assertEqual(source_name, source['name'])
+        self.assertDictContainsSubset(source_body, source)
+
+    def _delete_data_source(self, source_id):
+        # delete the data source by id
+        resp = self.client.delete_data_source(source_id)[0]
+        self.assertEqual(204, resp.status)
+
+    @test.attr(type='smoke')
+    def test_swift_data_source_create(self):
+        self._create_data_source(self.swift_data_source_with_creds)
+
+    @test.attr(type='smoke')
+    def test_swift_data_source_list(self):
+        source_info = self._create_data_source(
+            self.swift_data_source_with_creds)
+        self._list_data_sources(source_info)
+
+    @test.attr(type='smoke')
+    def test_swift_data_source_get(self):
+        source_id, source_name = self._create_data_source(
+            self.swift_data_source_with_creds)
+        self._get_data_source(source_id, source_name, self.swift_data_source)
+
+    @test.attr(type='smoke')
+    def test_swift_data_source_delete(self):
+        source_id = self._create_data_source(
+            self.swift_data_source_with_creds)[0]
+        self._delete_data_source(source_id)
+
+    @test.attr(type='smoke')
+    def test_local_hdfs_data_source_create(self):
+        self._create_data_source(self.local_hdfs_data_source)
+
+    @test.attr(type='smoke')
+    def test_local_hdfs_data_source_list(self):
+        source_info = self._create_data_source(self.local_hdfs_data_source)
+        self._list_data_sources(source_info)
+
+    @test.attr(type='smoke')
+    def test_local_hdfs_data_source_get(self):
+        source_id, source_name = self._create_data_source(
+            self.local_hdfs_data_source)
+        self._get_data_source(
+            source_id, source_name, self.local_hdfs_data_source)
+
+    @test.attr(type='smoke')
+    def test_local_hdfs_data_source_delete(self):
+        source_id = self._create_data_source(self.local_hdfs_data_source)[0]
+        self._delete_data_source(source_id)
+
+    @test.attr(type='smoke')
+    def test_external_hdfs_data_source_create(self):
+        self._create_data_source(self.external_hdfs_data_source)
+
+    @test.attr(type='smoke')
+    def test_external_hdfs_data_source_list(self):
+        source_info = self._create_data_source(self.external_hdfs_data_source)
+        self._list_data_sources(source_info)
+
+    @test.attr(type='smoke')
+    def test_external_hdfs_data_source_get(self):
+        source_id, source_name = self._create_data_source(
+            self.external_hdfs_data_source)
+        self._get_data_source(
+            source_id, source_name, self.external_hdfs_data_source)
+
+    @test.attr(type='smoke')
+    def test_external_hdfs_data_source_delete(self):
+        source_id = self._create_data_source(self.external_hdfs_data_source)[0]
+        self._delete_data_source(source_id)
diff --git a/tempest/api/data_processing/test_node_group_templates.py b/tempest/api/data_processing/test_node_group_templates.py
index ed4cf1f..04f98b4 100644
--- a/tempest/api/data_processing/test_node_group_templates.py
+++ b/tempest/api/data_processing/test_node_group_templates.py
@@ -1,21 +1,20 @@
-# Copyright (c) 2013 Mirantis Inc.
+# Copyright (c) 2014 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
+#    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
+#         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.
+#    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.data_processing import base as dp_base
 from tempest.common.utils import data_utils
-from tempest.test import attr
+from tempest import test
 
 
 class NodeGroupTemplateTest(dp_base.BaseDataProcessingTest):
@@ -47,7 +46,7 @@
         It creates template and ensures response status and template name.
         Returns id and name of created template.
         """
-        if template_name is None:
+        if not template_name:
             # generate random name if it's not specified
             template_name = data_utils.rand_name('sahara-ng-template')
 
@@ -58,48 +57,39 @@
         # ensure that template created successfully
         self.assertEqual(202, resp.status)
         self.assertEqual(template_name, body['name'])
+        self.assertDictContainsSubset(self.node_group_template, body)
 
         return body['id'], template_name
 
-    @attr(type='smoke')
+    @test.attr(type='smoke')
     def test_node_group_template_create(self):
-        template_name = data_utils.rand_name('sahara-ng-template')
-        resp, body = self.create_node_group_template(
-            template_name, **self.node_group_template)
+        self._create_node_group_template()
 
-        # check that template created successfully
-        self.assertEqual(resp.status, 202)
-        self.assertEqual(template_name, body['name'])
-        self.assertDictContainsSubset(self.node_group_template, body)
-
-    @attr(type='smoke')
+    @test.attr(type='smoke')
     def test_node_group_template_list(self):
         template_info = self._create_node_group_template()
 
         # check for node group template in list
         resp, templates = self.client.list_node_group_templates()
-
         self.assertEqual(200, resp.status)
         templates_info = [(template['id'], template['name'])
                           for template in templates]
         self.assertIn(template_info, templates_info)
 
-    @attr(type='smoke')
+    @test.attr(type='smoke')
     def test_node_group_template_get(self):
         template_id, template_name = self._create_node_group_template()
 
         # check node group template fetch by id
         resp, template = self.client.get_node_group_template(template_id)
-
         self.assertEqual(200, resp.status)
         self.assertEqual(template_name, template['name'])
         self.assertDictContainsSubset(self.node_group_template, template)
 
-    @attr(type='smoke')
+    @test.attr(type='smoke')
     def test_node_group_template_delete(self):
         template_id = self._create_node_group_template()[0]
 
         # delete the node group template by id
         resp = self.client.delete_node_group_template(template_id)[0]
-
         self.assertEqual(204, resp.status)
diff --git a/tempest/api/data_processing/test_plugins.py b/tempest/api/data_processing/test_plugins.py
index 3b941d8..d643f23 100644
--- a/tempest/api/data_processing/test_plugins.py
+++ b/tempest/api/data_processing/test_plugins.py
@@ -1,20 +1,19 @@
-# Copyright (c) 2013 Mirantis Inc.
+# Copyright (c) 2014 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
+#    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
+#         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.
+#    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.data_processing import base as dp_base
-from tempest.test import attr
+from tempest import test
 
 
 class PluginsTest(dp_base.BaseDataProcessingTest):
@@ -24,31 +23,27 @@
         It ensures response status and main plugins availability.
         """
         resp, plugins = self.client.list_plugins()
-
         self.assertEqual(200, resp.status)
-
-        plugins_names = list([plugin['name'] for plugin in plugins])
+        plugins_names = [plugin['name'] for plugin in plugins]
         self.assertIn('vanilla', plugins_names)
         self.assertIn('hdp', plugins_names)
 
         return plugins_names
 
-    @attr(type='smoke')
+    @test.attr(type='smoke')
     def test_plugin_list(self):
         self._list_all_plugin_names()
 
-    @attr(type='smoke')
+    @test.attr(type='smoke')
     def test_plugin_get(self):
         for plugin_name in self._list_all_plugin_names():
             resp, plugin = self.client.get_plugin(plugin_name)
-
             self.assertEqual(200, resp.status)
             self.assertEqual(plugin_name, plugin['name'])
 
             for plugin_version in plugin['versions']:
                 resp, detailed_plugin = self.client.get_plugin(plugin_name,
                                                                plugin_version)
-
                 self.assertEqual(200, resp.status)
                 self.assertEqual(plugin_name, detailed_plugin['name'])
 
diff --git a/tempest/api/identity/admin/test_roles_negative.py b/tempest/api/identity/admin/test_roles_negative.py
index d311143..6f8f9b5 100644
--- a/tempest/api/identity/admin/test_roles_negative.py
+++ b/tempest/api/identity/admin/test_roles_negative.py
@@ -18,7 +18,7 @@
 from tempest.api.identity import base
 from tempest.common.utils import data_utils
 from tempest import exceptions
-from tempest.test import attr
+from tempest import test
 
 
 class RolesNegativeTestJSON(base.BaseIdentityV2AdminTest):
@@ -32,13 +32,13 @@
         role = self.get_role_by_name(self.data.test_role)
         return (user, tenant, role)
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_list_roles_by_unauthorized_user(self):
         # Non-administrator user should not be able to list roles
         self.assertRaises(exceptions.Unauthorized,
                           self.non_admin_client.list_roles)
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_list_roles_request_without_token(self):
         # Request to list roles without a valid token should fail
         token = self.client.auth_provider.get_token()
@@ -46,19 +46,19 @@
         self.assertRaises(exceptions.Unauthorized, self.client.list_roles)
         self.client.auth_provider.clear_auth()
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_role_create_blank_name(self):
         # Should not be able to create a role with a blank name
         self.assertRaises(exceptions.BadRequest, self.client.create_role, '')
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_create_role_by_unauthorized_user(self):
         # Non-administrator user should not be able to create role
         role_name = data_utils.rand_name(name='role-')
         self.assertRaises(exceptions.Unauthorized,
                           self.non_admin_client.create_role, role_name)
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_create_role_request_without_token(self):
         # Request to create role without a valid token should fail
         token = self.client.auth_provider.get_token()
@@ -68,7 +68,7 @@
                           self.client.create_role, role_name)
         self.client.auth_provider.clear_auth()
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_role_create_duplicate(self):
         # Role names should be unique
         role_name = data_utils.rand_name(name='role-dup-')
@@ -79,7 +79,7 @@
         self.assertRaises(exceptions.Conflict, self.client.create_role,
                           role_name)
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_delete_role_by_unauthorized_user(self):
         # Non-administrator user should not be able to delete role
         role_name = data_utils.rand_name(name='role-')
@@ -90,7 +90,7 @@
         self.assertRaises(exceptions.Unauthorized,
                           self.non_admin_client.delete_role, role_id)
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_delete_role_request_without_token(self):
         # Request to delete role without a valid token should fail
         role_name = data_utils.rand_name(name='role-')
@@ -105,14 +105,14 @@
                           role_id)
         self.client.auth_provider.clear_auth()
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_delete_role_non_existent(self):
         # Attempt to delete a non existent role should fail
         non_existent_role = str(uuid.uuid4().hex)
         self.assertRaises(exceptions.NotFound, self.client.delete_role,
                           non_existent_role)
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_assign_user_role_by_unauthorized_user(self):
         # Non-administrator user should not be authorized to
         # assign a role to user
@@ -121,7 +121,7 @@
                           self.non_admin_client.assign_user_role,
                           tenant['id'], user['id'], role['id'])
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_assign_user_role_request_without_token(self):
         # Request to assign a role to a user without a valid token
         (user, tenant, role) = self._get_role_params()
@@ -132,7 +132,7 @@
                           user['id'], role['id'])
         self.client.auth_provider.clear_auth()
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_assign_user_role_for_non_existent_role(self):
         # Attempt to assign a non existent role to user should fail
         (user, tenant, role) = self._get_role_params()
@@ -140,7 +140,7 @@
         self.assertRaises(exceptions.NotFound, self.client.assign_user_role,
                           tenant['id'], user['id'], non_existent_role)
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_assign_user_role_for_non_existent_tenant(self):
         # Attempt to assign a role on a non existent tenant should fail
         (user, tenant, role) = self._get_role_params()
@@ -148,7 +148,7 @@
         self.assertRaises(exceptions.NotFound, self.client.assign_user_role,
                           non_existent_tenant, user['id'], role['id'])
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_assign_duplicate_user_role(self):
         # Duplicate user role should not get assigned
         (user, tenant, role) = self._get_role_params()
@@ -156,7 +156,7 @@
         self.assertRaises(exceptions.Conflict, self.client.assign_user_role,
                           tenant['id'], user['id'], role['id'])
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_remove_user_role_by_unauthorized_user(self):
         # Non-administrator user should not be authorized to
         # remove a user's role
@@ -168,7 +168,7 @@
                           self.non_admin_client.remove_user_role,
                           tenant['id'], user['id'], role['id'])
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_remove_user_role_request_without_token(self):
         # Request to remove a user's role without a valid token
         (user, tenant, role) = self._get_role_params()
@@ -182,7 +182,7 @@
                           user['id'], role['id'])
         self.client.auth_provider.clear_auth()
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_remove_user_role_non_existent_role(self):
         # Attempt to delete a non existent role from a user should fail
         (user, tenant, role) = self._get_role_params()
@@ -193,7 +193,7 @@
         self.assertRaises(exceptions.NotFound, self.client.remove_user_role,
                           tenant['id'], user['id'], non_existent_role)
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_remove_user_role_non_existent_tenant(self):
         # Attempt to remove a role from a non existent tenant should fail
         (user, tenant, role) = self._get_role_params()
@@ -204,7 +204,7 @@
         self.assertRaises(exceptions.NotFound, self.client.remove_user_role,
                           non_existent_tenant, user['id'], role['id'])
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_list_user_roles_by_unauthorized_user(self):
         # Non-administrator user should not be authorized to list
         # a user's roles
@@ -214,7 +214,7 @@
                           self.non_admin_client.list_user_roles, tenant['id'],
                           user['id'])
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_list_user_roles_request_without_token(self):
         # Request to list user's roles without a valid token should fail
         (user, tenant, role) = self._get_role_params()
diff --git a/tempest/api/identity/admin/test_services.py b/tempest/api/identity/admin/test_services.py
index e5cb348..0472e07 100644
--- a/tempest/api/identity/admin/test_services.py
+++ b/tempest/api/identity/admin/test_services.py
@@ -18,7 +18,7 @@
 from tempest.api.identity import base
 from tempest.common.utils import data_utils
 from tempest import exceptions
-from tempest.test import attr
+from tempest import test
 
 
 class ServicesTestJSON(base.BaseIdentityV2AdminTest):
@@ -32,7 +32,7 @@
         self.assertRaises(exceptions.NotFound, self.client.get_service,
                           service_id)
 
-    @attr(type='smoke')
+    @test.attr(type='smoke')
     def test_create_get_delete_service(self):
         # GET Service
         # Creating a Service
@@ -66,7 +66,7 @@
         self.assertEqual(fetched_service['description'],
                          service_data['description'])
 
-    @attr(type='gate')
+    @test.attr(type='gate')
     def test_create_service_without_description(self):
         # Create a service only with name and type
         name = data_utils.rand_name('service-')
@@ -80,7 +80,7 @@
         self.assertIn('type', service)
         self.assertEqual(type, service['type'])
 
-    @attr(type='smoke')
+    @test.attr(type='smoke')
     def test_list_services(self):
         # Create, List, Verify and Delete Services
         services = []
diff --git a/tempest/api/identity/admin/test_tenant_negative.py b/tempest/api/identity/admin/test_tenant_negative.py
index 44b54b8..622ad81 100644
--- a/tempest/api/identity/admin/test_tenant_negative.py
+++ b/tempest/api/identity/admin/test_tenant_negative.py
@@ -18,19 +18,19 @@
 from tempest.api.identity import base
 from tempest.common.utils import data_utils
 from tempest import exceptions
-from tempest.test import attr
+from tempest import test
 
 
 class TenantsNegativeTestJSON(base.BaseIdentityV2AdminTest):
     _interface = 'json'
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_list_tenants_by_unauthorized_user(self):
         # Non-administrator user should not be able to list tenants
         self.assertRaises(exceptions.Unauthorized,
                           self.non_admin_client.list_tenants)
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_list_tenant_request_without_token(self):
         # Request to list tenants without a valid token should fail
         token = self.client.auth_provider.get_token()
@@ -38,7 +38,7 @@
         self.assertRaises(exceptions.Unauthorized, self.client.list_tenants)
         self.client.auth_provider.clear_auth()
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_tenant_delete_by_unauthorized_user(self):
         # Non-administrator user should not be able to delete a tenant
         tenant_name = data_utils.rand_name(name='tenant-')
@@ -48,7 +48,7 @@
         self.assertRaises(exceptions.Unauthorized,
                           self.non_admin_client.delete_tenant, tenant['id'])
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_tenant_delete_request_without_token(self):
         # Request to delete a tenant without a valid token should fail
         tenant_name = data_utils.rand_name(name='tenant-')
@@ -61,13 +61,13 @@
                           tenant['id'])
         self.client.auth_provider.clear_auth()
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_delete_non_existent_tenant(self):
         # Attempt to delete a non existent tenant should fail
         self.assertRaises(exceptions.NotFound, self.client.delete_tenant,
                           str(uuid.uuid4().hex))
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_tenant_create_duplicate(self):
         # Tenant names should be unique
         tenant_name = data_utils.rand_name(name='tenant-')
@@ -82,14 +82,14 @@
         self.assertRaises(exceptions.Conflict, self.client.create_tenant,
                           tenant_name)
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_create_tenant_by_unauthorized_user(self):
         # Non-administrator user should not be authorized to create a tenant
         tenant_name = data_utils.rand_name(name='tenant-')
         self.assertRaises(exceptions.Unauthorized,
                           self.non_admin_client.create_tenant, tenant_name)
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_create_tenant_request_without_token(self):
         # Create tenant request without a token should not be authorized
         tenant_name = data_utils.rand_name(name='tenant-')
@@ -99,26 +99,26 @@
                           tenant_name)
         self.client.auth_provider.clear_auth()
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_create_tenant_with_empty_name(self):
         # Tenant name should not be empty
         self.assertRaises(exceptions.BadRequest, self.client.create_tenant,
                           name='')
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_create_tenants_name_length_over_64(self):
         # Tenant name length should not be greater than 64 characters
         tenant_name = 'a' * 65
         self.assertRaises(exceptions.BadRequest, self.client.create_tenant,
                           tenant_name)
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_update_non_existent_tenant(self):
         # Attempt to update a non existent tenant should fail
         self.assertRaises(exceptions.NotFound, self.client.update_tenant,
                           str(uuid.uuid4().hex))
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_tenant_update_by_unauthorized_user(self):
         # Non-administrator user should not be able to update a tenant
         tenant_name = data_utils.rand_name(name='tenant-')
@@ -128,7 +128,7 @@
         self.assertRaises(exceptions.Unauthorized,
                           self.non_admin_client.update_tenant, tenant['id'])
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_tenant_update_request_without_token(self):
         # Request to update a tenant without a valid token should fail
         tenant_name = data_utils.rand_name(name='tenant-')
diff --git a/tempest/api/identity/admin/test_tenants.py b/tempest/api/identity/admin/test_tenants.py
index 7ba46bb..b989664 100644
--- a/tempest/api/identity/admin/test_tenants.py
+++ b/tempest/api/identity/admin/test_tenants.py
@@ -17,13 +17,13 @@
 
 from tempest.api.identity import base
 from tempest.common.utils import data_utils
-from tempest.test import attr
+from tempest import test
 
 
 class TenantsTestJSON(base.BaseIdentityV2AdminTest):
     _interface = 'json'
 
-    @attr(type='gate')
+    @test.attr(type='gate')
     def test_tenant_list_delete(self):
         # Create several tenants and delete them
         tenants = []
@@ -48,7 +48,7 @@
         found = [tenant for tenant in body if tenant['id'] in tenant_ids]
         self.assertFalse(any(found), 'Tenants failed to delete')
 
-    @attr(type='gate')
+    @test.attr(type='gate')
     def test_tenant_create_with_description(self):
         # Create tenant with a description
         tenant_name = data_utils.rand_name(name='tenant-')
@@ -69,7 +69,7 @@
         self.client.delete_tenant(tenant_id)
         self.data.tenants.remove(tenant)
 
-    @attr(type='gate')
+    @test.attr(type='gate')
     def test_tenant_create_enabled(self):
         # Create a tenant that is enabled
         tenant_name = data_utils.rand_name(name='tenant-')
@@ -86,7 +86,7 @@
         self.client.delete_tenant(tenant_id)
         self.data.tenants.remove(tenant)
 
-    @attr(type='gate')
+    @test.attr(type='gate')
     def test_tenant_create_not_enabled(self):
         # Create a tenant that is not enabled
         tenant_name = data_utils.rand_name(name='tenant-')
@@ -105,7 +105,7 @@
         self.client.delete_tenant(tenant_id)
         self.data.tenants.remove(tenant)
 
-    @attr(type='gate')
+    @test.attr(type='gate')
     def test_tenant_update_name(self):
         # Update name attribute of a tenant
         t_name1 = data_utils.rand_name(name='tenant-')
@@ -133,7 +133,7 @@
         self.client.delete_tenant(t_id)
         self.data.tenants.remove(tenant)
 
-    @attr(type='gate')
+    @test.attr(type='gate')
     def test_tenant_update_desc(self):
         # Update description attribute of a tenant
         t_name = data_utils.rand_name(name='tenant-')
@@ -162,7 +162,7 @@
         self.client.delete_tenant(t_id)
         self.data.tenants.remove(tenant)
 
-    @attr(type='gate')
+    @test.attr(type='gate')
     def test_tenant_update_enable(self):
         # Update the enabled attribute of a tenant
         t_name = data_utils.rand_name(name='tenant-')
diff --git a/tempest/api/identity/admin/test_tokens.py b/tempest/api/identity/admin/test_tokens.py
index 7fec28d..08e12f0 100644
--- a/tempest/api/identity/admin/test_tokens.py
+++ b/tempest/api/identity/admin/test_tokens.py
@@ -15,13 +15,13 @@
 
 from tempest.api.identity import base
 from tempest.common.utils import data_utils
-from tempest.test import attr
+from tempest import test
 
 
 class TokensTestJSON(base.BaseIdentityV2AdminTest):
     _interface = 'json'
 
-    @attr(type='gate')
+    @test.attr(type='gate')
     def test_create_get_delete_token(self):
         # get a token by username and password
         user_name = data_utils.rand_name(name='user-')
@@ -56,7 +56,7 @@
         resp, body = self.client.delete_token(token_id)
         self.assertEqual(resp['status'], '204')
 
-    @attr(type='gate')
+    @test.attr(type='gate')
     def test_rescope_token(self):
         """An unscoped token can be requested, that token can be used to
            request a scoped token.
diff --git a/tempest/api/identity/admin/test_users.py b/tempest/api/identity/admin/test_users.py
index a4e6c17..e2c1066 100644
--- a/tempest/api/identity/admin/test_users.py
+++ b/tempest/api/identity/admin/test_users.py
@@ -206,6 +206,25 @@
                          "Failed to find user %s in fetched list" %
                          ', '.join(m_user for m_user in missing_users))
 
+    @test.attr(type='smoke')
+    def test_update_user_password(self):
+        # Test case to check if updating of user password is successful.
+        self.data.setup_test_user()
+        # Updating the user with new password
+        new_pass = data_utils.rand_name('pass-')
+        resp, update_user = self.client.update_user_password(
+            self.data.user['id'], new_pass)
+        # Assert response body of update user.
+        self.assertEqual(200, resp.status)
+        self.assertEqual(update_user['id'], self.data.user['id'])
+
+        # Validate the updated password
+        # Get a token
+        resp, body = self.token_client.auth(self.data.test_user, new_pass,
+                                            self.data.test_tenant)
+        self.assertEqual('200', resp['status'])
+        self.assertTrue('id' in body['token'])
+
 
 class UsersTestXML(UsersTestJSON):
     _interface = 'xml'
diff --git a/tempest/api/identity/admin/test_users_negative.py b/tempest/api/identity/admin/test_users_negative.py
index 4e8ebe5..a584a7b 100644
--- a/tempest/api/identity/admin/test_users_negative.py
+++ b/tempest/api/identity/admin/test_users_negative.py
@@ -18,7 +18,7 @@
 from tempest.api.identity import base
 from tempest.common.utils import data_utils
 from tempest import exceptions
-from tempest.test import attr
+from tempest import test
 
 
 class UsersNegativeTestJSON(base.BaseIdentityV2AdminTest):
@@ -31,7 +31,7 @@
         cls.alt_password = data_utils.rand_name('pass_')
         cls.alt_email = cls.alt_user + '@testmail.tm'
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_create_user_by_unauthorized_user(self):
         # Non-administrator should not be authorized to create a user
         self.data.setup_test_tenant()
@@ -40,7 +40,7 @@
                           self.alt_password, self.data.tenant['id'],
                           self.alt_email)
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_create_user_with_empty_name(self):
         # User with an empty name should not be created
         self.data.setup_test_tenant()
@@ -48,7 +48,7 @@
                           self.alt_password, self.data.tenant['id'],
                           self.alt_email)
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_create_user_with_name_length_over_255(self):
         # Length of user name filed should be restricted to 255 characters
         self.data.setup_test_tenant()
@@ -56,7 +56,7 @@
                           'a' * 256, self.alt_password,
                           self.data.tenant['id'], self.alt_email)
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_create_user_with_duplicate_name(self):
         # Duplicate user should not be created
         self.data.setup_test_user()
@@ -64,14 +64,14 @@
                           self.data.test_user, self.data.test_password,
                           self.data.tenant['id'], self.data.test_email)
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_create_user_for_non_existent_tenant(self):
         # Attempt to create a user in a non-existent tenant should fail
         self.assertRaises(exceptions.NotFound, self.client.create_user,
                           self.alt_user, self.alt_password, '49ffgg99999',
                           self.alt_email)
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_create_user_request_without_a_token(self):
         # Request to create a user without a valid token should fail
         self.data.setup_test_tenant()
@@ -86,7 +86,7 @@
         # Unset the token to allow further tests to generate a new token
         self.client.auth_provider.clear_auth()
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_create_user_with_enabled_non_bool(self):
         # Attempt to create a user with valid enabled para should fail
         self.data.setup_test_tenant()
@@ -96,7 +96,7 @@
                           self.data.tenant['id'],
                           self.alt_email, enabled=3)
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_update_user_for_non_existent_user(self):
         # Attempt to update a user non-existent user should fail
         user_name = data_utils.rand_name('user-')
@@ -104,7 +104,7 @@
         self.assertRaises(exceptions.NotFound, self.client.update_user,
                           non_existent_id, name=user_name)
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_update_user_request_without_a_token(self):
         # Request to update a user without a valid token should fail
 
@@ -118,14 +118,14 @@
         # Unset the token to allow further tests to generate a new token
         self.client.auth_provider.clear_auth()
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_update_user_by_unauthorized_user(self):
         # Non-administrator should not be authorized to update user
         self.data.setup_test_tenant()
         self.assertRaises(exceptions.Unauthorized,
                           self.non_admin_client.update_user, self.alt_user)
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_delete_users_by_unauthorized_user(self):
         # Non-administrator user should not be authorized to delete a user
         self.data.setup_test_user()
@@ -133,13 +133,13 @@
                           self.non_admin_client.delete_user,
                           self.data.user['id'])
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_delete_non_existent_user(self):
         # Attempt to delete a non-existent user should fail
         self.assertRaises(exceptions.NotFound, self.client.delete_user,
                           'junk12345123')
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_delete_user_request_without_a_token(self):
         # Request to delete a user without a valid token should fail
 
@@ -153,7 +153,7 @@
         # Unset the token to allow further tests to generate a new token
         self.client.auth_provider.clear_auth()
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_authentication_for_disabled_user(self):
         # Disabled user's token should not get authenticated
         self.data.setup_test_user()
@@ -163,7 +163,7 @@
                           self.data.test_password,
                           self.data.test_tenant)
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_authentication_when_tenant_is_disabled(self):
         # User's token for a disabled tenant should not be authenticated
         self.data.setup_test_user()
@@ -173,7 +173,7 @@
                           self.data.test_password,
                           self.data.test_tenant)
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_authentication_with_invalid_tenant(self):
         # User's token for an invalid tenant should not be authenticated
         self.data.setup_test_user()
@@ -182,7 +182,7 @@
                           self.data.test_password,
                           'junktenant1234')
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_authentication_with_invalid_username(self):
         # Non-existent user's token should not get authenticated
         self.data.setup_test_user()
@@ -190,7 +190,7 @@
                           'junkuser123', self.data.test_password,
                           self.data.test_tenant)
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_authentication_with_invalid_password(self):
         # User's token with invalid password should not be authenticated
         self.data.setup_test_user()
@@ -198,14 +198,14 @@
                           self.data.test_user, 'junkpass1234',
                           self.data.test_tenant)
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_get_users_by_unauthorized_user(self):
         # Non-administrator user should not be authorized to get user list
         self.data.setup_test_user()
         self.assertRaises(exceptions.Unauthorized,
                           self.non_admin_client.get_users)
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_get_users_request_without_token(self):
         # Request to get list of users without a valid token should fail
         token = self.client.auth_provider.get_token()
@@ -213,7 +213,7 @@
         self.assertRaises(exceptions.Unauthorized, self.client.get_users)
         self.client.auth_provider.clear_auth()
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_list_users_with_invalid_tenant(self):
         # Should not be able to return a list of all
         # users for a non-existent tenant
diff --git a/tempest/api/identity/admin/v3/test_domains.py b/tempest/api/identity/admin/v3/test_domains.py
index 086d235..a1e6cde 100644
--- a/tempest/api/identity/admin/v3/test_domains.py
+++ b/tempest/api/identity/admin/v3/test_domains.py
@@ -16,7 +16,7 @@
 
 from tempest.api.identity import base
 from tempest.common.utils import data_utils
-from tempest.test import attr
+from tempest import test
 
 
 class DomainsTestJSON(base.BaseIdentityV3AdminTest):
@@ -29,7 +29,7 @@
         resp, _ = self.client.delete_domain(domain_id)
         self.assertEqual(204, resp.status)
 
-    @attr(type='smoke')
+    @test.attr(type='smoke')
     def test_list_domains(self):
         # Test to list domains
         domain_ids = list()
@@ -49,7 +49,7 @@
         missing_doms = [d for d in domain_ids if d not in fetched_ids]
         self.assertEqual(0, len(missing_doms))
 
-    @attr(type='smoke')
+    @test.attr(type='smoke')
     def test_create_update_delete_domain(self):
         d_name = data_utils.rand_name('domain-')
         d_desc = data_utils.rand_name('domain-desc-')
diff --git a/tempest/api/identity/admin/v3/test_endpoints_negative.py b/tempest/api/identity/admin/v3/test_endpoints_negative.py
index 28615a4..5b46f89 100644
--- a/tempest/api/identity/admin/v3/test_endpoints_negative.py
+++ b/tempest/api/identity/admin/v3/test_endpoints_negative.py
@@ -18,7 +18,7 @@
 from tempest.api.identity import base
 from tempest.common.utils import data_utils
 from tempest import exceptions
-from tempest.test import attr
+from tempest import test
 
 
 class EndpointsNegativeTestJSON(base.BaseIdentityV3AdminTest):
@@ -45,7 +45,7 @@
             cls.service_client.delete_service(s)
         super(EndpointsNegativeTestJSON, cls).tearDownClass()
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_create_with_enabled_False(self):
         # Enabled should be a boolean, not a string like 'False'
         interface = 'public'
@@ -55,7 +55,7 @@
                           self.service_id, interface, url, region=region,
                           force_enabled='False')
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_create_with_enabled_True(self):
         # Enabled should be a boolean, not a string like 'True'
         interface = 'public'
@@ -79,12 +79,12 @@
         self.assertRaises(exceptions.BadRequest, self.client.update_endpoint,
                           endpoint_for_update['id'], force_enabled=enabled)
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_update_with_enabled_False(self):
         # Enabled should be a boolean, not a string like 'False'
         self._assert_update_raises_bad_request('False')
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_update_with_enabled_True(self):
         # Enabled should be a boolean, not a string like 'True'
         self._assert_update_raises_bad_request('True')
diff --git a/tempest/api/identity/admin/v3/test_policies.py b/tempest/api/identity/admin/v3/test_policies.py
index 3e04b5f..0e79440 100644
--- a/tempest/api/identity/admin/v3/test_policies.py
+++ b/tempest/api/identity/admin/v3/test_policies.py
@@ -15,7 +15,7 @@
 
 from tempest.api.identity import base
 from tempest.common.utils import data_utils
-from tempest.test import attr
+from tempest import test
 
 
 class PoliciesTestJSON(base.BaseIdentityV3AdminTest):
@@ -25,7 +25,7 @@
         resp, _ = self.policy_client.delete_policy(policy_id)
         self.assertEqual(204, resp.status)
 
-    @attr(type='smoke')
+    @test.attr(type='smoke')
     def test_list_policies(self):
         # Test to list policies
         policy_ids = list()
@@ -46,7 +46,7 @@
         missing_pols = [p for p in policy_ids if p not in fetched_ids]
         self.assertEqual(0, len(missing_pols))
 
-    @attr(type='smoke')
+    @test.attr(type='smoke')
     def test_create_update_delete_policy(self):
         # Test to update policy
         blob = data_utils.rand_name('BlobName-')
diff --git a/tempest/api/identity/admin/v3/test_services.py b/tempest/api/identity/admin/v3/test_services.py
index c5d4ddf..36e5327 100644
--- a/tempest/api/identity/admin/v3/test_services.py
+++ b/tempest/api/identity/admin/v3/test_services.py
@@ -16,13 +16,13 @@
 
 from tempest.api.identity import base
 from tempest.common.utils import data_utils
-from tempest.test import attr
+from tempest import test
 
 
 class ServicesTestJSON(base.BaseIdentityV3AdminTest):
     _interface = 'json'
 
-    @attr(type='gate')
+    @test.attr(type='gate')
     def test_update_service(self):
         # Update description attribute of service
         name = data_utils.rand_name('service-')
diff --git a/tempest/api/identity/admin/v3/test_tokens.py b/tempest/api/identity/admin/v3/test_tokens.py
index ebc1cac..fe3eb03 100644
--- a/tempest/api/identity/admin/v3/test_tokens.py
+++ b/tempest/api/identity/admin/v3/test_tokens.py
@@ -16,13 +16,13 @@
 from tempest.api.identity import base
 from tempest.common.utils import data_utils
 from tempest import exceptions
-from tempest.test import attr
+from tempest import test
 
 
 class TokensV3TestJSON(base.BaseIdentityV3AdminTest):
     _interface = 'json'
 
-    @attr(type='smoke')
+    @test.attr(type='smoke')
     def test_tokens(self):
         # Valid user's token is authenticated
         # Create a User
@@ -50,7 +50,7 @@
         self.assertRaises(exceptions.NotFound, self.client.get_token,
                           subject_token)
 
-    @attr(type='gate')
+    @test.attr(type='gate')
     def test_rescope_token(self):
         """Rescope a token.
 
diff --git a/tempest/api/identity/admin/v3/test_users.py b/tempest/api/identity/admin/v3/test_users.py
index e1d1543..7316c7f 100644
--- a/tempest/api/identity/admin/v3/test_users.py
+++ b/tempest/api/identity/admin/v3/test_users.py
@@ -15,13 +15,13 @@
 
 from tempest.api.identity import base
 from tempest.common.utils import data_utils
-from tempest.test import attr
+from tempest import test
 
 
 class UsersV3TestJSON(base.BaseIdentityV3AdminTest):
     _interface = 'json'
 
-    @attr(type='gate')
+    @test.attr(type='gate')
     def test_user_update(self):
         # Test case to check if updating of user attributes is successful.
         # Creating first user
@@ -66,7 +66,7 @@
         self.assertEqual(u_email2, new_user_get['email'])
         self.assertEqual('false', str(new_user_get['enabled']).lower())
 
-    @attr(type='gate')
+    @test.attr(type='gate')
     def test_list_user_projects(self):
         # List the projects that a user has access upon
         assigned_project_ids = list()
@@ -120,7 +120,7 @@
                          ', '.join(m_project for m_project
                                    in missing_projects))
 
-    @attr(type='gate')
+    @test.attr(type='gate')
     def test_get_user(self):
         # Get a user detail
         self.data.setup_test_v3_user()
diff --git a/tempest/api/image/base.py b/tempest/api/image/base.py
index e31e635..9981292 100644
--- a/tempest/api/image/base.py
+++ b/tempest/api/image/base.py
@@ -129,15 +129,11 @@
         if CONF.compute.allow_tenant_isolation:
             creds = cls.isolated_creds.get_alt_creds()
             cls.os_alt = clients.Manager(creds)
-            cls.alt_tenant_id = cls.isolated_creds.get_alt_creds().tenant_id
         else:
             cls.os_alt = clients.AltManager()
-            alt_tenant_name = cls.os_alt.credentials['tenant_name']
-            identity_client = cls._get_identity_admin_client()
-            cls.alt_tenant_id = identity_client.get_tenant_by_name(
-                alt_tenant_name)['id']
         cls.os_img_client = cls.os.image_client_v2
         cls.alt_img_client = cls.os_alt.image_client_v2
+        cls.alt_tenant_id = cls.alt_img_client.tenant_id
 
     def _list_image_ids_as_alt(self):
         _, image_list = self.alt_img_client.image_list()
diff --git a/tempest/api/image/v1/test_images.py b/tempest/api/image/v1/test_images.py
index b90891b..c8726a2 100644
--- a/tempest/api/image/v1/test_images.py
+++ b/tempest/api/image/v1/test_images.py
@@ -33,12 +33,12 @@
         resp, body = self.create_image(name='New Name',
                                        container_format='bare',
                                        disk_format='raw',
-                                       is_public=True,
+                                       is_public=False,
                                        properties=properties)
         self.assertIn('id', body)
         image_id = body.get('id')
         self.assertEqual('New Name', body.get('name'))
-        self.assertTrue(body.get('is_public'))
+        self.assertFalse(body.get('is_public'))
         self.assertEqual('queued', body.get('status'))
         for key, val in properties.items():
             self.assertEqual(val, body.get('properties')[key])
@@ -54,14 +54,14 @@
         # Register a new remote image
         resp, body = self.create_image(name='New Remote Image',
                                        container_format='bare',
-                                       disk_format='raw', is_public=True,
+                                       disk_format='raw', is_public=False,
                                        location='http://example.com'
                                                 '/someimage.iso',
                                        properties={'key1': 'value1',
                                                    'key2': 'value2'})
         self.assertIn('id', body)
         self.assertEqual('New Remote Image', body.get('name'))
-        self.assertTrue(body.get('is_public'))
+        self.assertFalse(body.get('is_public'))
         self.assertEqual('active', body.get('status'))
         properties = body.get('properties')
         self.assertEqual(properties['key1'], 'value1')
@@ -71,12 +71,12 @@
     def test_register_http_image(self):
         resp, body = self.create_image(name='New Http Image',
                                        container_format='bare',
-                                       disk_format='raw', is_public=True,
+                                       disk_format='raw', is_public=False,
                                        copy_from=CONF.image.http_image)
         self.assertIn('id', body)
         image_id = body.get('id')
         self.assertEqual('New Http Image', body.get('name'))
-        self.assertTrue(body.get('is_public'))
+        self.assertFalse(body.get('is_public'))
         self.client.wait_for_image_status(image_id, 'active')
         resp, body = self.client.get_image(image_id)
         self.assertEqual(resp['status'], '200')
@@ -88,12 +88,12 @@
         resp, body = self.create_image(name='New_image_with_min_ram',
                                        container_format='bare',
                                        disk_format='raw',
-                                       is_public=True,
+                                       is_public=False,
                                        min_ram=40,
                                        properties=properties)
         self.assertIn('id', body)
         self.assertEqual('New_image_with_min_ram', body.get('name'))
-        self.assertTrue(body.get('is_public'))
+        self.assertFalse(body.get('is_public'))
         self.assertEqual('queued', body.get('status'))
         self.assertEqual(40, body.get('min_ram'))
         for key, val in properties.items():
@@ -147,7 +147,7 @@
         resp, image = cls.create_image(name=name,
                                        container_format=container_format,
                                        disk_format=disk_format,
-                                       is_public=True,
+                                       is_public=False,
                                        location=location)
         image_id = image['id']
         return image_id
@@ -165,7 +165,7 @@
         resp, image = cls.create_image(name=name,
                                        container_format=container_format,
                                        disk_format=disk_format,
-                                       is_public=True, data=image_file)
+                                       is_public=False, data=image_file)
         image_id = image['id']
         return image_id
 
@@ -264,7 +264,7 @@
         resp, image = cls.create_image(name="Standard Image",
                                        container_format='ami',
                                        disk_format='ami',
-                                       is_public=True, data=image_file)
+                                       is_public=False, data=image_file)
         cls.image_id = image['id']
         cls.client.wait_for_image_status(image['id'], 'active')
 
@@ -356,7 +356,7 @@
         resp, image = cls.create_image(name=name,
                                        container_format=container_format,
                                        disk_format=disk_format,
-                                       is_public=True, data=image_file,
+                                       is_public=False, data=image_file,
                                        properties={'key1': 'value1'})
         image_id = image['id']
         return image_id
diff --git a/tempest/api/image/v2/test_images.py b/tempest/api/image/v2/test_images.py
index 2592409..37dc163 100644
--- a/tempest/api/image/v2/test_images.py
+++ b/tempest/api/image/v2/test_images.py
@@ -35,17 +35,19 @@
         upload the image file, get image and get image file api's
         """
 
+        uuid = '00000000-1111-2222-3333-444455556666'
         image_name = data_utils.rand_name('image')
         resp, body = self.create_image(name=image_name,
                                        container_format='bare',
                                        disk_format='raw',
-                                       visibility='public')
+                                       visibility='private',
+                                       ramdisk_id=uuid)
         self.assertIn('id', body)
         image_id = body.get('id')
         self.assertIn('name', body)
         self.assertEqual(image_name, body['name'])
         self.assertIn('visibility', body)
-        self.assertEqual('public', body['visibility'])
+        self.assertEqual('private', body['visibility'])
         self.assertIn('status', body)
         self.assertEqual('queued', body['status'])
 
@@ -60,6 +62,7 @@
         self.assertEqual(200, resp.status)
         self.assertEqual(image_id, body['id'])
         self.assertEqual(image_name, body['name'])
+        self.assertEqual(uuid, body['ramdisk_id'])
         self.assertIn('size', body)
         self.assertEqual(1024, body.get('size'))
 
@@ -77,7 +80,7 @@
         resp, body = self.client.create_image(name=image_name,
                                               container_format='bare',
                                               disk_format='raw',
-                                              visibility='public')
+                                              visibility='private')
         self.assertEqual(201, resp.status)
         image_id = body['id']
 
@@ -99,7 +102,7 @@
         resp, body = self.client.create_image(name=image_name,
                                               container_format='bare',
                                               disk_format='iso',
-                                              visibility='public')
+                                              visibility='private')
         self.assertEqual(201, resp.status)
         self.addCleanup(self.client.delete_image, body['id'])
         self.assertEqual('queued', body['status'])
@@ -113,10 +116,8 @@
 
         # Update Image
         new_image_name = data_utils.rand_name('new-image')
-        new_visibility = 'private'
         resp, body = self.client.update_image(image_id, [
-            dict(replace='/name', value=new_image_name),
-            dict(replace='/visibility', value=new_visibility)])
+            dict(replace='/name', value=new_image_name)])
 
         self.assertEqual(200, resp.status)
 
@@ -126,7 +127,6 @@
         self.assertEqual(200, resp.status)
         self.assertEqual(image_id, body['id'])
         self.assertEqual(new_image_name, body['name'])
-        self.assertEqual(new_visibility, body['visibility'])
 
 
 class ListImagesTest(base.BaseV2ImageTest):
@@ -160,7 +160,7 @@
         resp, body = cls.create_image(name=name,
                                       container_format=container_format,
                                       disk_format=disk_format,
-                                      visibility='public')
+                                      visibility='private')
         image_id = body['id']
         resp, body = cls.client.store_image(image_id, data=image_file)
 
@@ -202,8 +202,8 @@
 
     @test.attr(type='gate')
     def test_list_images_param_visibility(self):
-        # Test to get all images with visibility = public
-        params = {"visibility": "public"}
+        # Test to get all images with visibility = private
+        params = {"visibility": "private"}
         self._list_by_param_value_and_assert(params)
 
     @test.attr(type='gate')
diff --git a/tempest/api/image/v2/test_images_tags.py b/tempest/api/image/v2/test_images_tags.py
index 504c0e8..dec3353 100644
--- a/tempest/api/image/v2/test_images_tags.py
+++ b/tempest/api/image/v2/test_images_tags.py
@@ -23,7 +23,7 @@
     def test_update_delete_tags_for_image(self):
         resp, body = self.create_image(container_format='bare',
                                        disk_format='raw',
-                                       visibility='public')
+                                       visibility='private')
         image_id = body['id']
         tag = data_utils.rand_name('tag-')
         self.addCleanup(self.client.delete_image, image_id)
diff --git a/tempest/api/image/v2/test_images_tags_negative.py b/tempest/api/image/v2/test_images_tags_negative.py
index 3233db7..13cfa0a 100644
--- a/tempest/api/image/v2/test_images_tags_negative.py
+++ b/tempest/api/image/v2/test_images_tags_negative.py
@@ -35,7 +35,7 @@
         # Delete non existing tag.
         resp, body = self.create_image(container_format='bare',
                                        disk_format='raw',
-                                       is_public=True,
+                                       visibility='private'
                                        )
         image_id = body['id']
         tag = data_utils.rand_name('non-exist-tag-')
diff --git a/tempest/api/network/admin/test_l3_agent_scheduler.py b/tempest/api/network/admin/test_l3_agent_scheduler.py
index f4050c5..3b05f42 100644
--- a/tempest/api/network/admin/test_l3_agent_scheduler.py
+++ b/tempest/api/network/admin/test_l3_agent_scheduler.py
@@ -28,8 +28,9 @@
         List L3 agents hosting the given router.
         Add and Remove Router to L3 agent
 
-    v2.0 of the Neutron API is assumed. It is also assumed that the following
-    options are defined in the [network] section of etc/tempest.conf:
+    v2.0 of the Neutron API is assumed.
+
+    The l3_agent_scheduler extension is required for these tests.
     """
 
     @classmethod
diff --git a/tempest/api/network/test_allowed_address_pair.py b/tempest/api/network/test_allowed_address_pair.py
new file mode 100644
index 0000000..e0e26da
--- /dev/null
+++ b/tempest/api/network/test_allowed_address_pair.py
@@ -0,0 +1,83 @@
+# Copyright 2014 OpenStack Foundation
+# All Rights Reserved.
+#
+#    Licensed under the Apache License, Version 2.0 (the "License"); you may
+#    not use this file except in compliance with the License. You may obtain
+#    a copy of the License at
+#
+#         http://www.apache.org/licenses/LICENSE-2.0
+#
+#    Unless required by applicable law or agreed to in writing, software
+#    distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+#    WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
+#    License for the specific language governing permissions and limitations
+#    under the License.
+
+from tempest.api.network import base
+from tempest import test
+
+
+class AllowedAddressPairTestJSON(base.BaseNetworkTest):
+    _interface = 'json'
+
+    """
+    Tests the Neutron Allowed Address Pair API extension using the Tempest
+    ReST client. The following API operations are tested with this extension:
+
+        create port
+        list ports
+        update port
+        show port
+
+    v2.0 of the Neutron API is assumed. It is also assumed that the following
+    options are defined in the [network-feature-enabled] section of
+    etc/tempest.conf
+
+        api_extensions
+    """
+
+    @classmethod
+    @test.safe_setup
+    def setUpClass(cls):
+        super(AllowedAddressPairTestJSON, cls).setUpClass()
+        if not test.is_extension_enabled('allowed-address-pairs', 'network'):
+            msg = "Allowed Address Pairs extension not enabled."
+            raise cls.skipException(msg)
+        cls.network = cls.create_network()
+        cls.create_subnet(cls.network)
+        port = cls.create_port(cls.network)
+        cls.ip_address = port['fixed_ips'][0]['ip_address']
+        cls.mac_address = port['mac_address']
+
+    @test.attr(type='smoke')
+    def test_create_list_port_with_address_pair(self):
+        # Create port with allowed address pair attribute
+        allowed_address_pairs = [{'ip_address': self.ip_address,
+                                  'mac_address': self.mac_address}]
+        resp, body = self.client.create_port(
+            network_id=self.network['id'],
+            allowed_address_pairs=allowed_address_pairs)
+        self.assertEqual('201', resp['status'])
+        port_id = body['port']['id']
+        self.addCleanup(self.client.delete_port, port_id)
+
+        # Confirm port was created with allowed address pair attribute
+        resp, body = self.client.list_ports()
+        self.assertEqual('200', resp['status'])
+        ports = body['ports']
+        port = [p for p in ports if p['id'] == port_id]
+        msg = 'Created port not found in list of ports returned by Neutron'
+        self.assertTrue(port, msg)
+        self._confirm_allowed_address_pair(port[0], self.ip_address)
+
+    def _confirm_allowed_address_pair(self, port, ip):
+        msg = 'Port allowed address pairs should not be empty'
+        self.assertTrue(port['allowed_address_pairs'], msg)
+        ip_address = port['allowed_address_pairs'][0]['ip_address']
+        mac_address = port['allowed_address_pairs'][0]['mac_address']
+        self.assertEqual(ip_address, ip)
+        self.assertEqual(mac_address, self.mac_address)
+
+
+class AllowedAddressPairTestXML(AllowedAddressPairTestJSON):
+    _interface = 'xml'
diff --git a/tempest/api/network/test_floating_ips.py b/tempest/api/network/test_floating_ips.py
index d0d25ec..2463654 100644
--- a/tempest/api/network/test_floating_ips.py
+++ b/tempest/api/network/test_floating_ips.py
@@ -13,6 +13,8 @@
 #    License for the specific language governing permissions and limitations
 #    under the License.
 
+import netaddr
+
 from tempest.api.network import base
 from tempest.common.utils import data_utils
 from tempest import config
@@ -192,6 +194,36 @@
         self.assertEqual('200', resp['status'])
         self.assertIsNone(floating_ip['floatingip']['port_id'])
 
+    @test.attr(type='smoke')
+    def test_create_update_floatingip_with_port_multiple_ip_address(self):
+        # Find out ips that can be used for tests
+        ips = list(netaddr.IPNetwork(self.subnet['cidr']))
+        list_ips = [str(ip) for ip in ips[-3:-1]]
+        fixed_ips = [{'ip_address': list_ips[0]}, {'ip_address': list_ips[1]}]
+        # Create port
+        resp, body = self.client.create_port(network_id=self.network['id'],
+                                             fixed_ips=fixed_ips)
+        self.assertEqual('201', resp['status'])
+        port = body['port']
+        self.addCleanup(self.client.delete_port, port['id'])
+        # Create floating ip
+        resp, body = self.client.create_floatingip(
+            floating_network_id=self.ext_net_id, port_id=port['id'],
+            fixed_ip_address=list_ips[0])
+        self.assertEqual('201', resp['status'])
+        floating_ip = body['floatingip']
+        self.addCleanup(self.client.delete_floatingip, floating_ip['id'])
+        self.assertIsNotNone(floating_ip['id'])
+        self.assertEqual(floating_ip['fixed_ip_address'], list_ips[0])
+        # Update floating ip
+        resp, body = self.client.update_floatingip(
+            floating_ip['id'], port_id=port['id'],
+            fixed_ip_address=list_ips[1])
+        self.assertEqual('200', resp['status'])
+        update_floating_ip = body['floatingip']
+        self.assertEqual(update_floating_ip['fixed_ip_address'],
+                         list_ips[1])
+
 
 class FloatingIPTestXML(FloatingIPTestJSON):
     _interface = 'xml'
diff --git a/tempest/api/network/test_networks.py b/tempest/api/network/test_networks.py
index 660b376..ac0fd11 100644
--- a/tempest/api/network/test_networks.py
+++ b/tempest/api/network/test_networks.py
@@ -234,6 +234,8 @@
 
     @test.attr(type='smoke')
     def test_create_delete_subnet_without_gw(self):
+        net = netaddr.IPNetwork(CONF.network.tenant_network_cidr)
+        gateway_ip = str(netaddr.IPAddress(net.first + 1))
         name = data_utils.rand_name('network-')
         resp, body = self.client.create_network(name=name)
         self.assertEqual('201', resp['status'])
@@ -241,7 +243,7 @@
         net_id = network['id']
         subnet = self.create_subnet(network)
         # Verifies Subnet GW in IPv4
-        self.assertEqual(subnet['gateway_ip'], '10.100.0.1')
+        self.assertEqual(subnet['gateway_ip'], gateway_ip)
         # Delete network and subnet
         resp, body = self.client.delete_network(net_id)
         self.assertEqual('204', resp['status'])
diff --git a/tempest/api/network/test_networks_negative.py b/tempest/api/network/test_networks_negative.py
index 89c8a9f..53dfc52 100644
--- a/tempest/api/network/test_networks_negative.py
+++ b/tempest/api/network/test_networks_negative.py
@@ -17,37 +17,37 @@
 from tempest.api.network import base
 from tempest.common.utils import data_utils
 from tempest import exceptions
-from tempest.test import attr
+from tempest import test
 
 
 class NetworksNegativeTestJSON(base.BaseNetworkTest):
     _interface = 'json'
 
-    @attr(type=['negative', 'smoke'])
+    @test.attr(type=['negative', 'smoke'])
     def test_show_non_existent_network(self):
         non_exist_id = data_utils.rand_name('network')
         self.assertRaises(exceptions.NotFound, self.client.show_network,
                           non_exist_id)
 
-    @attr(type=['negative', 'smoke'])
+    @test.attr(type=['negative', 'smoke'])
     def test_show_non_existent_subnet(self):
         non_exist_id = data_utils.rand_name('subnet')
         self.assertRaises(exceptions.NotFound, self.client.show_subnet,
                           non_exist_id)
 
-    @attr(type=['negative', 'smoke'])
+    @test.attr(type=['negative', 'smoke'])
     def test_show_non_existent_port(self):
         non_exist_id = data_utils.rand_name('port')
         self.assertRaises(exceptions.NotFound, self.client.show_port,
                           non_exist_id)
 
-    @attr(type=['negative', 'smoke'])
+    @test.attr(type=['negative', 'smoke'])
     def test_update_non_existent_network(self):
         non_exist_id = data_utils.rand_name('network')
         self.assertRaises(exceptions.NotFound, self.client.update_network,
                           non_exist_id, name="new_name")
 
-    @attr(type=['negative', 'smoke'])
+    @test.attr(type=['negative', 'smoke'])
     def test_delete_non_existent_network(self):
         non_exist_id = data_utils.rand_name('network')
         self.assertRaises(exceptions.NotFound, self.client.delete_network,
diff --git a/tempest/api/network/test_security_groups.py b/tempest/api/network/test_security_groups.py
index 3e26f46..b98cea1 100644
--- a/tempest/api/network/test_security_groups.py
+++ b/tempest/api/network/test_security_groups.py
@@ -13,6 +13,8 @@
 #    License for the specific language governing permissions and limitations
 #    under the License.
 
+import six
+
 from tempest.api.network import base_security_groups as base
 from tempest.common.utils import data_utils
 from tempest import test
@@ -84,22 +86,25 @@
                 direction='ingress'
             )
             self.assertEqual('201', resp['status'])
-            self.addCleanup(self._delete_security_group_rule,
-                            rule_create_body['security_group_rule']['id']
-                            )
 
-        # Show details of the created security rule
-        resp, show_rule_body = self.client.show_security_group_rule(
-            rule_create_body['security_group_rule']['id']
-        )
-        self.assertEqual('200', resp['status'])
+            # Show details of the created security rule
+            resp, show_rule_body = self.client.show_security_group_rule(
+                rule_create_body['security_group_rule']['id']
+            )
+            self.assertEqual('200', resp['status'])
+            create_dict = rule_create_body['security_group_rule']
+            for key, value in six.iteritems(create_dict):
+                self.assertEqual(value,
+                                 show_rule_body['security_group_rule'][key],
+                                 "%s does not match." % key)
 
-        # List rules and verify created rule is in response
-        resp, rule_list_body = self.client.list_security_group_rules()
-        self.assertEqual('200', resp['status'])
-        rule_list = [rule['id']
-                     for rule in rule_list_body['security_group_rules']]
-        self.assertIn(rule_create_body['security_group_rule']['id'], rule_list)
+            # List rules and verify created rule is in response
+            resp, rule_list_body = self.client.list_security_group_rules()
+            self.assertEqual('200', resp['status'])
+            rule_list = [rule['id']
+                         for rule in rule_list_body['security_group_rules']]
+            self.assertIn(rule_create_body['security_group_rule']['id'],
+                          rule_list)
 
     @test.attr(type='smoke')
     def test_create_security_group_rule_with_additional_args(self):
@@ -122,9 +127,6 @@
 
         self.assertEqual('201', resp['status'])
         sec_group_rule = rule_create_body['security_group_rule']
-        self.addCleanup(self._delete_security_group_rule,
-                        sec_group_rule['id']
-                        )
 
         self.assertEqual(sec_group_rule['direction'], direction)
         self.assertEqual(sec_group_rule['protocol'], protocol)
diff --git a/tempest/api/object_storage/test_account_services_negative.py b/tempest/api/object_storage/test_account_services_negative.py
index d5f8649..490672d 100644
--- a/tempest/api/object_storage/test_account_services_negative.py
+++ b/tempest/api/object_storage/test_account_services_negative.py
@@ -17,12 +17,12 @@
 from tempest.api.object_storage import base
 from tempest import clients
 from tempest import exceptions
-from tempest.test import attr
+from tempest import test
 
 
 class AccountNegativeTest(base.BaseObjectTest):
 
-    @attr(type=['negative', 'gate'])
+    @test.attr(type=['negative', 'gate'])
     def test_list_containers_with_non_authorized_user(self):
         # list containers using non-authorized user
 
diff --git a/tempest/api/orchestration/base.py b/tempest/api/orchestration/base.py
index 4e40de9..446f4ab 100644
--- a/tempest/api/orchestration/base.py
+++ b/tempest/api/orchestration/base.py
@@ -42,12 +42,14 @@
         cls.keypairs_client = cls.os.keypairs_client
         cls.network_client = cls.os.network_client
         cls.volumes_client = cls.os.volumes_client
+        cls.images_v2_client = cls.os.image_client_v2
         cls.stacks = []
         cls.keypairs = []
+        cls.images = []
 
     @classmethod
     def _get_default_network(cls):
-        resp, networks = cls.network_client.list_networks()
+        __, networks = cls.network_client.list_networks()
         for net in networks['networks']:
             if net['name'] == CONF.compute.fixed_network_name:
                 return net
@@ -60,11 +62,14 @@
         return admin_client
 
     @classmethod
-    def create_stack(cls, stack_name, template_data, parameters={}):
+    def create_stack(cls, stack_name, template_data, parameters={},
+                     environment=None, files=None):
         resp, body = cls.client.create_stack(
             stack_name,
             template=template_data,
-            parameters=parameters)
+            parameters=parameters,
+            environment=environment,
+            files=files)
         stack_id = resp['location'].split('/')[-1]
         stack_identifier = '%s/%s' % (stack_name, stack_id)
         cls.stacks.append(stack_identifier)
@@ -88,7 +93,7 @@
     @classmethod
     def _create_keypair(cls, name_start='keypair-heat-'):
         kp_name = data_utils.rand_name(name_start)
-        resp, body = cls.keypairs_client.create_keypair(kp_name)
+        __, body = cls.keypairs_client.create_keypair(kp_name)
         cls.keypairs.append(kp_name)
         return body
 
@@ -101,6 +106,25 @@
                 pass
 
     @classmethod
+    def _create_image(cls, name_start='image-heat-', container_format='bare',
+                      disk_format='iso'):
+        image_name = data_utils.rand_name(name_start)
+        __, body = cls.images_v2_client.create_image(image_name,
+                                                     container_format,
+                                                     disk_format)
+        image_id = body['id']
+        cls.images.append(image_id)
+        return body
+
+    @classmethod
+    def _clear_images(cls):
+        for image_id in cls.images:
+            try:
+                cls.images_v2_client.delete_image(image_id)
+            except exceptions.NotFound:
+                pass
+
+    @classmethod
     def load_template(cls, name, ext='yaml'):
         loc = ["stacks", "templates", "%s.%s" % (name, ext)]
         fullpath = os.path.join(os.path.dirname(__file__), *loc)
@@ -113,6 +137,7 @@
     def tearDownClass(cls):
         cls._clear_stacks()
         cls._clear_keypairs()
+        cls._clear_images()
         super(BaseOrchestrationTest, cls).tearDownClass()
 
     @staticmethod
diff --git a/tempest/api/orchestration/stacks/templates/non_empty_stack.yaml b/tempest/api/orchestration/stacks/templates/non_empty_stack.yaml
index 58a934e..8690941 100644
--- a/tempest/api/orchestration/stacks/templates/non_empty_stack.yaml
+++ b/tempest/api/orchestration/stacks/templates/non_empty_stack.yaml
@@ -5,6 +5,8 @@
   trigger:
     Type: String
     Default: not_yet
+  image:
+    Type: String
 Resources:
   fluffy:
     Type: AWS::AutoScaling::LaunchConfiguration
@@ -13,7 +15,7 @@
       - Tom
       - Stinky
     Properties:
-      ImageId: not_used
+      ImageId: {Ref: image}
       InstanceType: not_used
       UserData:
         Fn::Replace:
diff --git a/tempest/api/orchestration/stacks/templates/random_string.yaml b/tempest/api/orchestration/stacks/templates/random_string.yaml
new file mode 100644
index 0000000..dfd2342
--- /dev/null
+++ b/tempest/api/orchestration/stacks/templates/random_string.yaml
@@ -0,0 +1,18 @@
+heat_template_version: 2013-05-23
+
+parameters:
+  random_length:
+    type: number
+    default: 10
+
+resources:
+  random:
+    type: OS::Heat::RandomString
+    properties:
+        length: {get_param: random_length}
+
+outputs:
+  random_length:
+    value: {get_param: random_length}
+  random_value:
+    value: {get_attr: [random, value]}
diff --git a/tempest/api/orchestration/stacks/test_environment.py b/tempest/api/orchestration/stacks/test_environment.py
new file mode 100644
index 0000000..3911e72
--- /dev/null
+++ b/tempest/api/orchestration/stacks/test_environment.py
@@ -0,0 +1,93 @@
+#    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 import data_utils
+from tempest import config
+from tempest import test
+
+
+CONF = config.CONF
+LOG = logging.getLogger(__name__)
+
+
+class StackEnvironmentTest(base.BaseOrchestrationTest):
+
+    @test.attr(type='gate')
+    def test_environment_parameter(self):
+        """Test passing a stack parameter via the environment."""
+        stack_name = data_utils.rand_name('heat')
+        template = self.load_template('random_string')
+        environment = {'parameters': {'random_length': 20}}
+
+        stack_identifier = self.create_stack(stack_name, template,
+                                             environment=environment)
+        self.client.wait_for_stack_status(stack_identifier, 'CREATE_COMPLETE')
+
+        random_len = self.get_stack_output(stack_identifier, 'random_length')
+        self.assertEqual(20, random_len)
+
+        random_value = self.get_stack_output(stack_identifier, 'random_value')
+        self.assertEqual(20, len(random_value))
+
+    @test.attr(type='gate')
+    def test_environment_provider_resource(self):
+        """Test passing resource_registry defining a provider resource."""
+        stack_name = data_utils.rand_name('heat')
+        template = '''
+heat_template_version: 2013-05-23
+resources:
+  random:
+    type: My:Random::String
+outputs:
+    random_value:
+        value: {get_attr: [random, random_value]}
+'''
+        environment = {'resource_registry':
+                       {'My:Random::String': 'my_random.yaml'}}
+        files = {'my_random.yaml': self.load_template('random_string')}
+
+        stack_identifier = self.create_stack(stack_name, template,
+                                             environment=environment,
+                                             files=files)
+        self.client.wait_for_stack_status(stack_identifier, 'CREATE_COMPLETE')
+
+        # random_string.yaml specifies a length of 10
+        random_value = self.get_stack_output(stack_identifier, 'random_value')
+        self.assertEqual(10, len(random_value))
+
+    @test.attr(type='gate')
+    def test_files_provider_resource(self):
+        """Test untyped defining of a provider resource via "files"."""
+        # It's also possible to specify the filename directly in the template.
+        # without adding the type alias to resource_registry
+        stack_name = data_utils.rand_name('heat')
+        template = '''
+heat_template_version: 2013-05-23
+resources:
+  random:
+    type: my_random.yaml
+outputs:
+    random_value:
+        value: {get_attr: [random, random_value]}
+'''
+        files = {'my_random.yaml': self.load_template('random_string')}
+
+        stack_identifier = self.create_stack(stack_name, template,
+                                             files=files)
+        self.client.wait_for_stack_status(stack_identifier, 'CREATE_COMPLETE')
+
+        # random_string.yaml specifies a length of 10
+        random_value = self.get_stack_output(stack_identifier, 'random_value')
+        self.assertEqual(10, len(random_value))
diff --git a/tempest/api/orchestration/stacks/test_limits.py b/tempest/api/orchestration/stacks/test_limits.py
index 283ab2b..8ee62ab 100644
--- a/tempest/api/orchestration/stacks/test_limits.py
+++ b/tempest/api/orchestration/stacks/test_limits.py
@@ -16,7 +16,7 @@
 from tempest.common.utils import data_utils
 from tempest import config
 from tempest import exceptions
-from tempest.test import attr
+from tempest import test
 
 CONF = config.CONF
 
@@ -25,7 +25,7 @@
 
 class TestServerStackLimits(base.BaseOrchestrationTest):
 
-    @attr(type='gate')
+    @test.attr(type='gate')
     def test_exceed_max_template_size_fails(self):
         stack_name = data_utils.rand_name('heat')
         fill = 'A' * CONF.orchestration.max_template_size
@@ -38,7 +38,7 @@
                                stack_name, template)
         self.assertIn('Template exceeds maximum allowed size', str(ex))
 
-    @attr(type='gate')
+    @test.attr(type='gate')
     def test_exceed_max_resources_per_stack(self):
         stack_name = data_utils.rand_name('heat')
         # Create a big template, one resource more than the limit
diff --git a/tempest/api/orchestration/stacks/test_non_empty_stack.py b/tempest/api/orchestration/stacks/test_non_empty_stack.py
index 9ef95a1..585c90b 100644
--- a/tempest/api/orchestration/stacks/test_non_empty_stack.py
+++ b/tempest/api/orchestration/stacks/test_non_empty_stack.py
@@ -14,8 +14,10 @@
 
 from tempest.api.orchestration import base
 from tempest.common.utils import data_utils
-from tempest.test import attr
+from tempest import config
+from tempest import test
 
+CONF = config.CONF
 
 LOG = logging.getLogger(__name__)
 
@@ -27,13 +29,15 @@
         super(StacksTestJSON, cls).setUpClass()
         cls.stack_name = data_utils.rand_name('heat')
         template = cls.load_template('non_empty_stack')
-
+        image_id = (CONF.orchestration.image_ref or
+                    cls._create_image()['id'])
         # create the stack
         cls.stack_identifier = cls.create_stack(
             cls.stack_name,
             template,
             parameters={
-                'trigger': 'start'
+                'trigger': 'start',
+                'image': image_id
             })
         cls.stack_id = cls.stack_identifier.split('/')[1]
         cls.resource_name = 'fluffy'
@@ -48,14 +52,14 @@
             self.assertEqual(expected_num, len(stacks))
         return stacks
 
-    @attr(type='gate')
+    @test.attr(type='gate')
     def test_stack_list(self):
         """Created stack should be in the list of existing stacks."""
         stacks = self._list_stacks()
         stacks_names = map(lambda stack: stack['stack_name'], stacks)
         self.assertIn(self.stack_name, stacks_names)
 
-    @attr(type='gate')
+    @test.attr(type='gate')
     def test_stack_show(self):
         """Getting details about created stack should be possible."""
         resp, stack = self.client.get_stack(self.stack_name)
@@ -75,7 +79,7 @@
         self.assertEqual(self.stack_id, stack['id'])
         self.assertEqual('fluffy', stack['outputs'][0]['output_key'])
 
-    @attr(type='gate')
+    @test.attr(type='gate')
     def test_suspend_resume_stack(self):
         """Suspend and resume a stack."""
         resp, suspend_stack = self.client.suspend_stack(self.stack_identifier)
@@ -87,14 +91,14 @@
         self.client.wait_for_stack_status(self.stack_identifier,
                                           'RESUME_COMPLETE')
 
-    @attr(type='gate')
+    @test.attr(type='gate')
     def test_list_resources(self):
         """Getting list of created resources for the stack should be possible.
         """
         resources = self.list_resources(self.stack_identifier)
         self.assertEqual({self.resource_name: self.resource_type}, resources)
 
-    @attr(type='gate')
+    @test.attr(type='gate')
     def test_show_resource(self):
         """Getting details about created resource should be possible."""
         resp, resource = self.client.get_resource(self.stack_identifier,
@@ -108,7 +112,7 @@
         self.assertEqual(self.resource_name, resource['logical_resource_id'])
         self.assertEqual(self.resource_type, resource['resource_type'])
 
-    @attr(type='gate')
+    @test.attr(type='gate')
     def test_resource_metadata(self):
         """Getting metadata for created resources should be possible."""
         resp, metadata = self.client.show_resource_metadata(
@@ -118,7 +122,7 @@
         self.assertIsInstance(metadata, dict)
         self.assertEqual(['Tom', 'Stinky'], metadata.get('kittens', None))
 
-    @attr(type='gate')
+    @test.attr(type='gate')
     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)
@@ -134,7 +138,7 @@
         self.assertIn('CREATE_IN_PROGRESS', resource_statuses)
         self.assertIn('CREATE_COMPLETE', resource_statuses)
 
-    @attr(type='gate')
+    @test.attr(type='gate')
     def test_show_event(self):
         """Getting details about an event should be possible."""
         resp, events = self.client.list_resource_events(self.stack_identifier,
diff --git a/tempest/api/orchestration/stacks/test_nova_keypair_resources.py b/tempest/api/orchestration/stacks/test_nova_keypair_resources.py
index 7f088de..cb70d07 100644
--- a/tempest/api/orchestration/stacks/test_nova_keypair_resources.py
+++ b/tempest/api/orchestration/stacks/test_nova_keypair_resources.py
@@ -15,7 +15,7 @@
 
 from tempest.api.orchestration import base
 from tempest.common.utils import data_utils
-from tempest.test import attr
+from tempest import test
 
 
 LOG = logging.getLogger(__name__)
@@ -46,7 +46,7 @@
         for resource in resources:
             cls.test_resources[resource['logical_resource_id']] = resource
 
-    @attr(type='slow')
+    @test.attr(type='slow')
     def test_created_resources(self):
         """Verifies created keypair resource."""
         resources = [('KeyPairSavePrivate', 'OS::Nova::KeyPair'),
@@ -59,7 +59,7 @@
             self.assertEqual(resource_type, resource['resource_type'])
             self.assertEqual('CREATE_COMPLETE', resource['resource_status'])
 
-    @attr(type='slow')
+    @test.attr(type='slow')
     def test_stack_keypairs_output(self):
         resp, stack = self.client.get_stack(self.stack_name)
         self.assertEqual('200', resp['status'])
diff --git a/tempest/api/orchestration/stacks/test_server_cfn_init.py b/tempest/api/orchestration/stacks/test_server_cfn_init.py
deleted file mode 100644
index 4b845b1..0000000
--- a/tempest/api/orchestration/stacks/test_server_cfn_init.py
+++ /dev/null
@@ -1,121 +0,0 @@
-#    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 json
-import testtools
-
-from tempest.api.orchestration import base
-from tempest.common.utils import data_utils
-from tempest.common.utils.linux import remote_client
-from tempest import config
-from tempest import exceptions
-from tempest.openstack.common import log as logging
-from tempest import test
-
-CONF = config.CONF
-LOG = logging.getLogger(__name__)
-
-
-class ServerCfnInitTestJSON(base.BaseOrchestrationTest):
-    existing_keypair = CONF.orchestration.keypair_name is not None
-
-    @classmethod
-    @test.safe_setup
-    def setUpClass(cls):
-        super(ServerCfnInitTestJSON, cls).setUpClass()
-        if not CONF.orchestration.image_ref:
-            raise cls.skipException("No image available to test")
-        template = cls.load_template('cfn_init_signal')
-        stack_name = data_utils.rand_name('heat')
-        if CONF.orchestration.keypair_name:
-            keypair_name = CONF.orchestration.keypair_name
-        else:
-            cls.keypair = cls._create_keypair()
-            keypair_name = cls.keypair['name']
-
-        # create the stack
-        cls.stack_identifier = cls.create_stack(
-            stack_name,
-            template,
-            parameters={
-                'key_name': keypair_name,
-                'flavor': CONF.orchestration.instance_type,
-                'image': CONF.orchestration.image_ref,
-                'network': cls._get_default_network()['id'],
-                'timeout': CONF.orchestration.build_timeout
-            })
-
-    @test.attr(type='slow')
-    @testtools.skipIf(existing_keypair, 'Server ssh tests are disabled.')
-    def test_can_log_into_created_server(self):
-
-        sid = self.stack_identifier
-        rid = 'SmokeServer'
-
-        # wait for create to complete.
-        self.client.wait_for_stack_status(sid, 'CREATE_COMPLETE')
-
-        resp, body = self.client.get_resource(sid, rid)
-        self.assertEqual('CREATE_COMPLETE', body['resource_status'])
-
-        # fetch the IP address from servers client, since we can't get it
-        # from the stack until stack create is complete
-        resp, server = self.servers_client.get_server(
-            body['physical_resource_id'])
-
-        # Check that the user can authenticate with the generated password
-        linux_client = remote_client.RemoteClient(server, 'ec2-user',
-                                                  pkey=self.keypair[
-                                                      'private_key'])
-        linux_client.validate_authentication()
-
-    @test.attr(type='slow')
-    def test_all_resources_created(self):
-        sid = self.stack_identifier
-        self.client.wait_for_resource_status(
-            sid, 'WaitHandle', 'CREATE_COMPLETE')
-        self.client.wait_for_resource_status(
-            sid, 'SmokeSecurityGroup', 'CREATE_COMPLETE')
-        self.client.wait_for_resource_status(
-            sid, 'SmokeKeys', 'CREATE_COMPLETE')
-        self.client.wait_for_resource_status(
-            sid, 'CfnUser', 'CREATE_COMPLETE')
-        self.client.wait_for_resource_status(
-            sid, 'SmokeServer', 'CREATE_COMPLETE')
-        try:
-            self.client.wait_for_resource_status(
-                sid, 'WaitCondition', 'CREATE_COMPLETE')
-        except (exceptions.StackResourceBuildErrorException,
-                exceptions.TimeoutException) as e:
-            # attempt to log the server console to help with debugging
-            # the cause of the server not signalling the waitcondition
-            # to heat.
-            resp, body = self.client.get_resource(sid, 'SmokeServer')
-            server_id = body['physical_resource_id']
-            LOG.debug('Console output for %s', server_id)
-            resp, output = self.servers_client.get_console_output(
-                server_id, None)
-            LOG.debug(output)
-            raise e
-
-        # wait for create to complete.
-        self.client.wait_for_stack_status(sid, 'CREATE_COMPLETE')
-
-        # 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 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(
-            self.get_stack_output(sid, 'WaitConditionStatus'))
-        self.assertEqual('smoke test complete', wait_status['00000'])
diff --git a/tempest/api/orchestration/stacks/test_stacks.py b/tempest/api/orchestration/stacks/test_stacks.py
index 867995c..5b45d82 100644
--- a/tempest/api/orchestration/stacks/test_stacks.py
+++ b/tempest/api/orchestration/stacks/test_stacks.py
@@ -13,7 +13,7 @@
 from tempest.api.orchestration import base
 from tempest.common.utils import data_utils
 from tempest.openstack.common import log as logging
-from tempest.test import attr
+from tempest import test
 
 
 LOG = logging.getLogger(__name__)
@@ -26,13 +26,13 @@
     def setUpClass(cls):
         super(StacksTestJSON, cls).setUpClass()
 
-    @attr(type='smoke')
+    @test.attr(type='smoke')
     def test_stack_list_responds(self):
         resp, stacks = self.client.list_stacks()
         self.assertEqual('200', resp['status'])
         self.assertIsInstance(stacks, list)
 
-    @attr(type='smoke')
+    @test.attr(type='smoke')
     def test_stack_crud_no_resources(self):
         stack_name = data_utils.rand_name('heat')
 
diff --git a/tempest/api/queuing/base.py b/tempest/api/queuing/base.py
index 6c22719..5649619 100644
--- a/tempest/api/queuing/base.py
+++ b/tempest/api/queuing/base.py
@@ -50,6 +50,42 @@
 
     @classmethod
     def delete_queue(cls, queue_name):
-        """Wrapper utility that returns a test queue."""
+        """Wrapper utility that deletes a test queue."""
         resp, body = cls.client.delete_queue(queue_name)
         return resp, body
+
+    @classmethod
+    def check_queue_exists(cls, queue_name):
+        """Wrapper utility that checks the existence of a test queue."""
+        resp, body = cls.client.get_queue(queue_name)
+        return resp, body
+
+    @classmethod
+    def check_queue_exists_head(cls, queue_name):
+        """Wrapper utility checks the head of a queue via http HEAD."""
+        resp, body = cls.client.head_queue(queue_name)
+        return resp, body
+
+    @classmethod
+    def list_queues(cls):
+        """Wrapper utility that lists queues."""
+        resp, body = cls.client.list_queues()
+        return resp, body
+
+    @classmethod
+    def get_queue_stats(cls, queue_name):
+        """Wrapper utility that returns the queue stats."""
+        resp, body = cls.client.get_queue_stats(queue_name)
+        return resp, body
+
+    @classmethod
+    def get_queue_metadata(cls, queue_name):
+        """Wrapper utility that gets a queue metadata."""
+        resp, body = cls.client.get_queue_metadata(queue_name)
+        return resp, body
+
+    @classmethod
+    def set_queue_metadata(cls, queue_name, rbody):
+        """Wrapper utility that sets the metadata of a queue."""
+        resp, body = cls.client.set_queue_metadata(queue_name, rbody)
+        return resp, body
diff --git a/tempest/api/queuing/test_queues.py b/tempest/api/queuing/test_queues.py
index 4d03f7e..e43178a 100644
--- a/tempest/api/queuing/test_queues.py
+++ b/tempest/api/queuing/test_queues.py
@@ -14,6 +14,8 @@
 # limitations under the License.
 
 import logging
+from six import moves
+from testtools import matchers
 
 from tempest.api.queuing import base
 from tempest.common.utils import data_utils
@@ -43,18 +45,86 @@
     @classmethod
     def setUpClass(cls):
         super(TestManageQueue, cls).setUpClass()
-        cls.queue_name = data_utils.rand_name('Queues-Test')
-        # Create Queue
-        cls.client.create_queue(cls.queue_name)
+        cls.queues = list()
+        for _ in moves.xrange(5):
+            queue_name = data_utils.rand_name('Queues-Test')
+            cls.queues.append(queue_name)
+            # Create Queue
+            cls.client.create_queue(queue_name)
 
     @test.attr(type='smoke')
     def test_delete_queue(self):
         # Delete Queue
-        resp, body = self.delete_queue(self.queue_name)
+        queue_name = self.queues.pop()
+        resp, body = self.delete_queue(queue_name)
         self.assertEqual('204', resp['status'])
         self.assertEqual('', body)
 
+    @test.attr(type='smoke')
+    def test_check_queue_existence(self):
+        # Checking Queue Existence
+        for queue_name in self.queues:
+            resp, body = self.check_queue_exists(queue_name)
+            self.assertEqual('204', resp['status'])
+            self.assertEqual('', body)
+
+    @test.attr(type='smoke')
+    def test_check_queue_head(self):
+        # Checking Queue Existence by calling HEAD
+        for queue_name in self.queues:
+            resp, body = self.check_queue_exists_head(queue_name)
+            self.assertEqual('204', resp['status'])
+            self.assertEqual('', body)
+
+    @test.attr(type='smoke')
+    def test_list_queues(self):
+        # Listing queues
+        resp, body = self.list_queues()
+        self.assertEqual(len(body['queues']), len(self.queues))
+        for item in body['queues']:
+            self.assertIn(item['name'], self.queues)
+
+    @test.attr(type='smoke')
+    def test_get_queue_stats(self):
+        # Retrieve random queue
+        queue_name = self.queues[data_utils.rand_int_id(0,
+                                                        len(self.queues) - 1)]
+        # Get Queue Stats for a newly created Queue
+        resp, body = self.get_queue_stats(queue_name)
+        msgs = body['messages']
+        for element in ('free', 'claimed', 'total'):
+            self.assertEqual(0, msgs[element])
+        for element in ('oldest', 'newest'):
+            self.assertNotIn(element, msgs)
+
+    @test.attr(type='smoke')
+    def test_set_and_get_queue_metadata(self):
+        # Retrieve random queue
+        queue_name = self.queues[data_utils.rand_int_id(0,
+                                                        len(self.queues) - 1)]
+        # Check the Queue has no metadata
+        resp, body = self.get_queue_metadata(queue_name)
+        self.assertEqual('200', resp['status'])
+        self.assertThat(body, matchers.HasLength(0))
+        # Create metadata
+        key3 = [0, 1, 2, 3, 4]
+        key2 = data_utils.rand_name('value')
+        req_body1 = dict()
+        req_body1[data_utils.rand_name('key3')] = key3
+        req_body1[data_utils.rand_name('key2')] = key2
+        req_body = dict()
+        req_body[data_utils.rand_name('key1')] = req_body1
+        # Set Queue Metadata
+        resp, body = self.set_queue_metadata(queue_name, req_body)
+        self.assertEqual('204', resp['status'])
+        self.assertEqual('', body)
+        # Get Queue Metadata
+        resp, body = self.get_queue_metadata(queue_name)
+        self.assertEqual('200', resp['status'])
+        self.assertThat(body, matchers.Equals(req_body))
+
     @classmethod
     def tearDownClass(cls):
-        cls.client.delete_queue(cls.queue_name)
+        for queue_name in cls.queues:
+            cls.client.delete_queue(queue_name)
         super(TestManageQueue, cls).tearDownClass()
diff --git a/tempest/api/telemetry/test_telemetry_alarming_api.py b/tempest/api/telemetry/test_telemetry_alarming_api.py
index 3472b31..95758e8 100644
--- a/tempest/api/telemetry/test_telemetry_alarming_api.py
+++ b/tempest/api/telemetry/test_telemetry_alarming_api.py
@@ -13,7 +13,7 @@
 from tempest.api.telemetry import base
 from tempest.common.utils import data_utils
 from tempest import exceptions
-from tempest.test import attr
+from tempest import test
 
 
 class TelemetryAlarmingAPITestJSON(base.BaseTelemetryTest):
@@ -29,7 +29,7 @@
         for i in range(2):
             cls.create_alarm(threshold_rule=cls.rule)
 
-    @attr(type="gate")
+    @test.attr(type="gate")
     def test_alarm_list(self):
         # List alarms
         resp, alarm_list = self.telemetry_client.list_alarms()
@@ -43,7 +43,7 @@
                          " in a fetched list: %s" %
                          ', '.join(str(a) for a in missing_alarms))
 
-    @attr(type="gate")
+    @test.attr(type="gate")
     def test_create_update_get_delete_alarm(self):
         # Create an alarm
         alarm_name = data_utils.rand_name('telemetry_alarm')
@@ -78,7 +78,7 @@
         self.assertRaises(exceptions.NotFound,
                           self.telemetry_client.get_alarm, alarm_id)
 
-    @attr(type="gate")
+    @test.attr(type="gate")
     def test_set_get_alarm_state(self):
         alarm_states = ['ok', 'alarm', 'insufficient data']
         _, alarm = self.create_alarm(threshold_rule=self.rule)
@@ -94,7 +94,7 @@
         self.assertEqual(200, resp.status)
         self.assertEqual(new_state, state)
 
-    @attr(type="gate")
+    @test.attr(type="gate")
     def test_create_delete_alarm_with_combination_rule(self):
         rule = {"alarm_ids": self.alarm_ids,
                 "operator": "or"}
diff --git a/tempest/api/volume/admin/test_volume_quotas.py b/tempest/api/volume/admin/test_volume_quotas.py
index 531e145..ecd8836 100644
--- a/tempest/api/volume/admin/test_volume_quotas.py
+++ b/tempest/api/volume/admin/test_volume_quotas.py
@@ -15,6 +15,7 @@
 #    under the License.
 
 from tempest.api.volume import base
+from tempest.common.utils import data_utils
 from tempest import test
 
 QUOTA_KEYS = ['gigabytes', 'snapshots', 'volumes']
@@ -99,6 +100,27 @@
         self.assertEqual(quota_usage['gigabytes']['in_use'] + 1,
                          new_quota_usage['gigabytes']['in_use'])
 
+    @test.attr(type='gate')
+    def test_delete_quota(self):
+        # Admin can delete the resource quota set for a tenant
+        tenant_name = data_utils.rand_name('quota_tenant_')
+        identity_client = self.os_adm.identity_client
+        tenant = identity_client.create_tenant(tenant_name)[1]
+        tenant_id = tenant['id']
+        self.addCleanup(identity_client.delete_tenant, tenant_id)
+        _, quota_set_default = self.quotas_client.get_default_quota_set(
+            tenant_id)
+        volume_default = quota_set_default['volumes']
+
+        self.quotas_client.update_quota_set(tenant_id,
+                                            volumes=(int(volume_default) + 5))
+
+        resp, _ = self.quotas_client.delete_quota_set(tenant_id)
+        self.assertEqual(200, resp.status)
+
+        _, quota_set_new = self.quotas_client.get_quota_set(tenant_id)
+        self.assertEqual(volume_default, quota_set_new['volumes'])
+
 
 class VolumeQuotasAdminTestXML(VolumeQuotasAdminTestJSON):
     _interface = "xml"
diff --git a/tempest/api/volume/admin/test_volume_types.py b/tempest/api/volume/admin/test_volume_types.py
index ee1d09a..3b8c214 100644
--- a/tempest/api/volume/admin/test_volume_types.py
+++ b/tempest/api/volume/admin/test_volume_types.py
@@ -118,14 +118,16 @@
                          'from the created Volume_type')
 
     @test.attr(type='smoke')
-    def test_volume_type_encryption_create_get(self):
-        # Create/get encryption type.
+    def test_volume_type_encryption_create_get_delete(self):
+        # Create/get/delete encryption type.
         provider = "LuksEncryptor"
         control_location = "front-end"
         name = data_utils.rand_name("volume-type-")
         resp, body = self.client.create_volume_type(name)
         self.assertEqual(200, resp.status)
         self.addCleanup(self._delete_volume_type, body['id'])
+
+        # Create encryption type
         resp, encryption_type = self.client.create_encryption_type(
             body['id'], provider=provider,
             control_location=control_location)
@@ -137,6 +139,8 @@
         self.assertEqual(control_location, encryption_type['control_location'],
                          "The created encryption_type control_location is not "
                          "equal to the requested control_location")
+
+        # Get encryption type
         resp, fetched_encryption_type = self.client.get_encryption_type(
             encryption_type['volume_type_id'])
         self.assertEqual(200, resp.status)
@@ -148,3 +152,15 @@
                          fetched_encryption_type['control_location'],
                          'The fetched encryption_type control_location is '
                          'different from the created encryption_type')
+
+        # Delete encryption type
+        resp, _ = self.client.delete_encryption_type(
+            encryption_type['volume_type_id'])
+        self.assertEqual(202, resp.status)
+        resource = {"id": encryption_type['volume_type_id'],
+                    "type": "encryption-type"}
+        self.client.wait_for_resource_deletion(resource)
+        resp, deleted_encryption_type = self.client.get_encryption_type(
+            encryption_type['volume_type_id'])
+        self.assertEqual(200, resp.status)
+        self.assertEmpty(deleted_encryption_type)
diff --git a/tempest/api/volume/base.py b/tempest/api/volume/base.py
index 4d11d24..67d0203 100644
--- a/tempest/api/volume/base.py
+++ b/tempest/api/volume/base.py
@@ -109,6 +109,7 @@
         cls.backups_client = cls.os.backups_client
         cls.volume_services_client = cls.os.volume_services_client
         cls.volumes_extension_client = cls.os.volumes_extension_client
+        cls.availability_zone_client = cls.os.volume_availability_zone_client
 
     @classmethod
     def create_volume(cls, size=1, **kwargs):
diff --git a/tempest/api/volume/test_availability_zone.py b/tempest/api/volume/test_availability_zone.py
new file mode 100644
index 0000000..1db7b7b
--- /dev/null
+++ b/tempest/api/volume/test_availability_zone.py
@@ -0,0 +1,40 @@
+# Copyright 2014 NEC Corporation
+# All Rights Reserved.
+#
+#    Licensed under the Apache License, Version 2.0 (the "License"); you may
+#    not use this file except in compliance with the License. You may obtain
+#    a copy of the License at
+#
+#         http://www.apache.org/licenses/LICENSE-2.0
+#
+#    Unless required by applicable law or agreed to in writing, software
+#    distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+#    WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
+#    License for the specific language governing permissions and limitations
+#    under the License.
+
+from tempest.api.volume import base
+from tempest import test
+
+
+class AvailabilityZoneTestJSON(base.BaseVolumeV1Test):
+
+    """
+    Tests Availability Zone API List
+    """
+
+    @classmethod
+    def setUpClass(cls):
+        super(AvailabilityZoneTestJSON, cls).setUpClass()
+        cls.client = cls.availability_zone_client
+
+    @test.attr(type='gate')
+    def test_get_availability_zone_list(self):
+        # List of availability zone
+        resp, availability_zone = self.client.get_availability_zone_list()
+        self.assertEqual(200, resp.status)
+        self.assertTrue(len(availability_zone) > 0)
+
+
+class AvailabilityZoneTestXML(AvailabilityZoneTestJSON):
+    _interface = 'xml'
diff --git a/tempest/api/volume/v2/test_volumes_list.py b/tempest/api/volume/v2/test_volumes_list.py
index 41445d7..e90c957 100644
--- a/tempest/api/volume/v2/test_volumes_list.py
+++ b/tempest/api/volume/v2/test_volumes_list.py
@@ -203,7 +203,7 @@
         def _list_details_with_multiple_params(limit=2,
                                                status='available',
                                                sort_dir='asc',
-                                               sort_key='created_at'):
+                                               sort_key='id'):
             params = {'limit': limit,
                       'status': status,
                       'sort_dir': sort_dir,
diff --git a/tempest/api_schema/compute/servers.py b/tempest/api_schema/compute/servers.py
index e11f047..2002927 100644
--- a/tempest/api_schema/compute/servers.py
+++ b/tempest/api_schema/compute/servers.py
@@ -139,3 +139,22 @@
         'required': ['servers']
     }
 }
+
+server_actions_common_schema = {
+    'status_code': [202]
+}
+
+server_actions_delete_password = {
+    'status_code': [204]
+}
+
+get_console_output = {
+    'status_code': [200],
+    'response_body': {
+        'type': 'object',
+        'properties': {
+            'output': {'type': 'string'}
+        },
+        'required': ['output']
+    }
+}
diff --git a/tempest/api_schema/compute/v2/security_groups.py b/tempest/api_schema/compute/v2/security_groups.py
index 8b4bead..9a852e5 100644
--- a/tempest/api_schema/compute/v2/security_groups.py
+++ b/tempest/api_schema/compute/v2/security_groups.py
@@ -80,6 +80,10 @@
     }
 }
 
+delete_security_group = {
+    'status_code': [202]
+}
+
 create_security_group_rule = {
     'status_code': [200],
     'response_body': {
diff --git a/tempest/api_schema/compute/v2/servers.py b/tempest/api_schema/compute/v2/servers.py
index e90f436..981d8f7 100644
--- a/tempest/api_schema/compute/v2/servers.py
+++ b/tempest/api_schema/compute/v2/servers.py
@@ -128,3 +128,17 @@
     'status_code': [200],
     'response_body': parameter_types.addresses
 }
+
+server_actions_confirm_resize = copy.deepcopy(
+    servers.server_actions_delete_password)
+
+list_addresses = {
+    'status_code': [200],
+    'response_body': {
+        'type': 'object',
+        'properties': {
+            'addresses': parameter_types.addresses
+        },
+        'required': ['addresses']
+    }
+}
diff --git a/tempest/api_schema/compute/v3/servers.py b/tempest/api_schema/compute/v3/servers.py
index 956b5ad..682021f 100644
--- a/tempest/api_schema/compute/v3/servers.py
+++ b/tempest/api_schema/compute/v3/servers.py
@@ -81,3 +81,17 @@
     'status_code': [200],
     'response_body': addresses_v3
 }
+
+server_actions_change_password = copy.deepcopy(
+    servers.server_actions_delete_password)
+
+list_addresses = {
+    'status_code': [200],
+    'response_body': {
+        'type': 'object',
+        'properties': {
+            'addresses': addresses_v3
+        },
+        'required': ['addresses']
+    }
+}
diff --git a/tempest/api_schema/queuing/__init__.py b/tempest/api_schema/queuing/__init__.py
new file mode 100644
index 0000000..e69de29
--- /dev/null
+++ b/tempest/api_schema/queuing/__init__.py
diff --git a/tempest/api_schema/queuing/v1/__init__.py b/tempest/api_schema/queuing/v1/__init__.py
new file mode 100644
index 0000000..e69de29
--- /dev/null
+++ b/tempest/api_schema/queuing/v1/__init__.py
diff --git a/tempest/api_schema/queuing/v1/queues.py b/tempest/api_schema/queuing/v1/queues.py
new file mode 100644
index 0000000..4630e1c
--- /dev/null
+++ b/tempest/api_schema/queuing/v1/queues.py
@@ -0,0 +1,98 @@
+
+# Copyright (c) 2014 Rackspace, 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.
+
+list_link = {
+    'type': 'object',
+    'properties': {
+        'rel': {'type': 'string'},
+        'href': {
+            'type': 'string',
+            'format': 'uri'
+        }
+    },
+    'required': ['href', 'rel']
+}
+
+list_queue = {
+    'type': 'object',
+    'properties': {
+        'name': {'type': 'string'},
+        'href': {
+            'type': 'string',
+            'format': 'uri'
+        },
+        'metadata': {'type': 'object'}
+    },
+    'required': ['name', 'href']
+}
+
+list_queues = {
+    'status_code': [200, 204],
+    'response_body': {
+        'type': 'object',
+        'properties': {
+            'links': {
+                'type': 'array',
+                'items': list_link,
+                'maxItems': 1
+            },
+            'queues': {
+                'type': 'array',
+                'items': list_queue
+            }
+        },
+        'required': ['links', 'queues']
+    }
+}
+
+message_link = {
+    'type': 'object',
+    'properties': {
+        'href': {
+            'type': 'string',
+            'format': 'uri'
+        },
+        'age': {'type': 'number'},
+        'created': {
+            'type': 'string',
+            'format': 'date-time'
+        }
+    },
+    'required': ['href', 'age', 'created']
+}
+
+messages = {
+    'type': 'object',
+    'properties': {
+        'free': {'type': 'number'},
+        'claimed': {'type': 'number'},
+        'total': {'type': 'number'},
+        'oldest': message_link,
+        'newest': message_link
+    },
+    'required': ['free', 'claimed', 'total']
+}
+
+queue_stats = {
+    'status_code': [200],
+    'response_body': {
+        'type': 'object',
+        'properties': {
+            'messages': messages
+        },
+        'required': ['messages']
+    }
+}
diff --git a/tempest/cli/simple_read_only/test_heat.py b/tempest/cli/simple_read_only/test_heat.py
index cf4580c..7a952fc 100644
--- a/tempest/cli/simple_read_only/test_heat.py
+++ b/tempest/cli/simple_read_only/test_heat.py
@@ -85,6 +85,9 @@
     def test_heat_help(self):
         self.heat('help')
 
+    def test_heat_bash_completion(self):
+        self.heat('bash-completion')
+
     def test_heat_help_cmd(self):
         # Check requesting help for a specific command works
         help_text = self.heat('help resource-template')
diff --git a/tempest/clients.py b/tempest/clients.py
index e50a0c3..7745d54 100644
--- a/tempest/clients.py
+++ b/tempest/clients.py
@@ -17,7 +17,7 @@
 import keystoneclient.v2_0.client
 
 from tempest import auth
-from tempest.common.rest_client import NegativeRestClient
+from tempest.common import rest_client
 from tempest import config
 from tempest import exceptions
 from tempest import manager
@@ -168,6 +168,8 @@
     VolumesServicesClientJSON
 from tempest.services.volume.json.admin.volume_types_client import \
     VolumeTypesClientJSON
+from tempest.services.volume.json.availability_zone_client import \
+    VolumeAvailabilityZoneClientJSON
 from tempest.services.volume.json.backups_client import BackupsClientJSON
 from tempest.services.volume.json.extensions_client import \
     ExtensionsClientJSON as VolumeExtensionClientJSON
@@ -183,6 +185,8 @@
     VolumesServicesClientXML
 from tempest.services.volume.xml.admin.volume_types_client import \
     VolumeTypesClientXML
+from tempest.services.volume.xml.availability_zone_client import \
+    VolumeAvailabilityZoneClientXML
 from tempest.services.volume.xml.backups_client import BackupsClientXML
 from tempest.services.volume.xml.extensions_client import \
     ExtensionsClientXML as VolumeExtensionClientXML
@@ -262,6 +266,8 @@
                     self.auth_provider)
             self.token_client = TokenClientXML()
             self.token_v3_client = V3TokenClientXML()
+            self.volume_availability_zone_client = \
+                VolumeAvailabilityZoneClientXML(self.auth_provider)
 
         elif self.interface == 'json':
             self.certificates_client = CertificatesClientJSON(
@@ -355,8 +361,11 @@
                     self.auth_provider)
             self.token_client = TokenClientJSON()
             self.token_v3_client = V3TokenClientJSON()
-            self.negative_client = NegativeRestClient(self.auth_provider)
+            self.negative_client = rest_client.NegativeRestClient(
+                self.auth_provider)
             self.negative_client.service = service
+            self.volume_availability_zone_client = \
+                VolumeAvailabilityZoneClientJSON(self.auth_provider)
 
         else:
             msg = "Unsupported interface type `%s'" % interface
diff --git a/tempest/cmd/javelin.py b/tempest/cmd/javelin.py
new file mode 100755
index 0000000..20ee63e
--- /dev/null
+++ b/tempest/cmd/javelin.py
@@ -0,0 +1,430 @@
+#!/usr/bin/env python
+#
+# 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.
+
+"""Javelin makes resources that should survive an upgrade.
+
+Javelin is a tool for creating, verifying, and deleting a small set of
+resources in a declarative way.
+
+"""
+
+import logging
+import os
+import sys
+import unittest
+import yaml
+
+import argparse
+
+import tempest.auth
+from tempest import exceptions
+from tempest.services.compute.json import flavors_client
+from tempest.services.compute.json import servers_client
+from tempest.services.identity.json import identity_client
+from tempest.services.image.v2.json import image_client
+from tempest.services.object_storage import container_client
+from tempest.services.object_storage import object_client
+
+OPTS = {}
+USERS = {}
+RES = {}
+
+LOG = None
+
+
+class OSClient(object):
+    _creds = None
+    identity = None
+    servers = None
+
+    def __init__(self, user, pw, tenant):
+        _creds = tempest.auth.KeystoneV2Credentials(
+            username=user,
+            password=pw,
+            tenant_name=tenant)
+        _auth = tempest.auth.KeystoneV2AuthProvider(_creds)
+        self.identity = identity_client.IdentityClientJSON(_auth)
+        self.servers = servers_client.ServersClientJSON(_auth)
+        self.objects = object_client.ObjectClient(_auth)
+        self.containers = container_client.ContainerClient(_auth)
+        self.images = image_client.ImageClientV2JSON(_auth)
+        self.flavors = flavors_client.FlavorsClientJSON(_auth)
+
+
+def load_resources(fname):
+    """Load the expected resources from a yaml flie."""
+    return yaml.load(open(fname, 'r'))
+
+
+def keystone_admin():
+    return OSClient(OPTS.os_username, OPTS.os_password, OPTS.os_tenant_name)
+
+
+def client_for_user(name):
+    LOG.debug("Entering client_for_user")
+    if name in USERS:
+        user = USERS[name]
+        LOG.debug("Created client for user %s" % user)
+        return OSClient(user['name'], user['pass'], user['tenant'])
+    else:
+        LOG.error("%s not found in USERS: %s" % (name, USERS))
+
+###################
+#
+# TENANTS
+#
+###################
+
+
+def create_tenants(tenants):
+    """Create tenants from resource definition.
+
+    Don't create the tenants if they already exist.
+    """
+    admin = keystone_admin()
+    _, body = admin.identity.list_tenants()
+    existing = [x['name'] for x in body]
+    for tenant in tenants:
+        if tenant not in existing:
+            admin.identity.create_tenant(tenant)
+        else:
+            LOG.warn("Tenant '%s' already exists in this environment" % tenant)
+
+##############
+#
+# USERS
+#
+##############
+
+
+def _users_for_tenant(users, tenant):
+    u_for_t = []
+    for user in users:
+        for n in user:
+            if user[n]['tenant'] == tenant:
+                u_for_t.append(user[n])
+    return u_for_t
+
+
+def _tenants_from_users(users):
+    tenants = set()
+    for user in users:
+        for n in user:
+            tenants.add(user[n]['tenant'])
+    return tenants
+
+
+def _assign_swift_role(user):
+    admin = keystone_admin()
+    resp, roles = admin.identity.list_roles()
+    role = next(r for r in roles if r['name'] == 'Member')
+    LOG.debug(USERS[user])
+    try:
+        admin.identity.assign_user_role(
+            USERS[user]['tenant_id'],
+            USERS[user]['id'],
+            role['id'])
+    except exceptions.Conflict:
+        # don't care if it's already assigned
+        pass
+
+
+def create_users(users):
+    """Create tenants from resource definition.
+
+    Don't create the tenants if they already exist.
+    """
+    global USERS
+    LOG.info("Creating users")
+    admin = keystone_admin()
+    for u in users:
+        try:
+            tenant = admin.identity.get_tenant_by_name(u['tenant'])
+        except exceptions.NotFound:
+            LOG.error("Tenant: %s - not found" % u['tenant'])
+            continue
+        try:
+            admin.identity.get_user_by_username(tenant['id'], u['name'])
+            LOG.warn("User '%s' already exists in this environment"
+                     % u['name'])
+        except exceptions.NotFound:
+            admin.identity.create_user(
+                u['name'], u['pass'], tenant['id'],
+                "%s@%s" % (u['name'], tenant['id']),
+                enabled=True)
+
+
+def collect_users(users):
+    global USERS
+    LOG.info("Creating users")
+    admin = keystone_admin()
+    for u in users:
+        tenant = admin.identity.get_tenant_by_name(u['tenant'])
+        u['tenant_id'] = tenant['id']
+        USERS[u['name']] = u
+        body = admin.identity.get_user_by_username(tenant['id'], u['name'])
+        USERS[u['name']]['id'] = body['id']
+
+
+class JavelinCheck(unittest.TestCase):
+    def __init__(self, users, resources):
+        super(JavelinCheck, self).__init__()
+        self.users = users
+        self.res = resources
+
+    def runTest(self, *args):
+        pass
+
+    def check(self):
+        self.check_users()
+        self.check_objects()
+        self.check_servers()
+
+    def check_users(self):
+        """Check that the users we expect to exist, do.
+
+        We don't use the resource list for this because we need to validate
+        that things like tenantId didn't drift across versions.
+        """
+        for name, user in self.users.iteritems():
+            client = keystone_admin()
+            _, found = client.identity.get_user(user['id'])
+            self.assertEqual(found['name'], user['name'])
+            self.assertEqual(found['tenantId'], user['tenant_id'])
+
+            # also ensure we can auth with that user, and do something
+            # on the cloud. We don't care about the results except that it
+            # remains authorized.
+            client = client_for_user(user['name'])
+            resp, body = client.servers.list_servers()
+            self.assertEqual(resp['status'], '200')
+
+    def check_objects(self):
+        """Check that the objects created are still there."""
+        for obj in self.res['objects']:
+            client = client_for_user(obj['owner'])
+            r, contents = client.objects.get_object(
+                obj['container'], obj['name'])
+            source = _file_contents(obj['file'])
+            self.assertEqual(contents, source)
+
+    def check_servers(self):
+        """Check that the servers are still up and running."""
+        for server in self.res['servers']:
+            client = client_for_user(server['owner'])
+            found = _get_server_by_name(client, server['name'])
+            self.assertIsNotNone(
+                found,
+                "Couldn't find expected server %s" % server['name'])
+
+            r, found = client.servers.get_server(found['id'])
+            # get the ipv4 address
+            addr = found['addresses']['private'][0]['addr']
+            self.assertEqual(os.system("ping -c 1 " + addr), 0,
+                             "Server %s is not pingable at %s" % (
+                                 server['name'], addr))
+
+
+#######################
+#
+# OBJECTS
+#
+#######################
+
+
+def _file_contents(fname):
+    with open(fname, 'r') as f:
+        return f.read()
+
+
+def create_objects(objects):
+    LOG.info("Creating objects")
+    for obj in objects:
+        LOG.debug("Object %s" % obj)
+        _assign_swift_role(obj['owner'])
+        client = client_for_user(obj['owner'])
+        client.containers.create_container(obj['container'])
+        client.objects.create_object(
+            obj['container'], obj['name'],
+            _file_contents(obj['file']))
+
+#######################
+#
+# IMAGES
+#
+#######################
+
+
+def create_images(images):
+    for image in images:
+        client = client_for_user(image['owner'])
+
+        # only upload a new image if the name isn't there
+        r, body = client.images.image_list()
+        names = [x['name'] for x in body]
+        if image['name'] in names:
+            continue
+
+        # special handling for 3 part image
+        extras = {}
+        if image['format'] == 'ami':
+            r, aki = client.images.create_image(
+                'javelin_' + image['aki'], 'aki', 'aki')
+            client.images.store_image(aki.get('id'), open(image['aki'], 'r'))
+            extras['kernel_id'] = aki.get('id')
+
+            r, ari = client.images.create_image(
+                'javelin_' + image['ari'], 'ari', 'ari')
+            client.images.store_image(ari.get('id'), open(image['ari'], 'r'))
+            extras['ramdisk_id'] = ari.get('id')
+
+        r, body = client.images.create_image(
+            image['name'], image['format'], image['format'], **extras)
+        image_id = body.get('id')
+        client.images.store_image(image_id, open(image['file'], 'r'))
+
+
+#######################
+#
+# SERVERS
+#
+#######################
+
+def _get_server_by_name(client, name):
+    r, body = client.servers.list_servers()
+    for server in body['servers']:
+        if name == server['name']:
+            return server
+    return None
+
+
+def _get_image_by_name(client, name):
+    r, body = client.images.image_list()
+    for image in body:
+        if name == image['name']:
+            return image
+    return None
+
+
+def _get_flavor_by_name(client, name):
+    r, body = client.flavors.list_flavors()
+    for flavor in body:
+        if name == flavor['name']:
+            return flavor
+    return None
+
+
+def create_servers(servers):
+    for server in servers:
+        client = client_for_user(server['owner'])
+
+        if _get_server_by_name(client, server['name']):
+            continue
+
+        image_id = _get_image_by_name(client, server['image'])['id']
+        flavor_id = _get_flavor_by_name(client, server['flavor'])['id']
+        client.servers.create_server(server['name'], image_id, flavor_id)
+
+
+#######################
+#
+# MAIN LOGIC
+#
+#######################
+
+def create_resources():
+    LOG.info("Creating Resources")
+    # first create keystone level resources, and we need to be admin
+    # for those.
+    create_tenants(RES['tenants'])
+    create_users(RES['users'])
+    collect_users(RES['users'])
+
+    # next create resources in a well known order
+    create_objects(RES['objects'])
+    create_images(RES['images'])
+    create_servers(RES['servers'])
+
+
+def get_options():
+    global OPTS
+    parser = argparse.ArgumentParser(
+        description='Create and validate a fixed set of OpenStack resources')
+    parser.add_argument('-m', '--mode',
+                        metavar='<create|check|destroy>',
+                        required=True,
+                        help=('One of (create, check, destroy)'))
+    parser.add_argument('-r', '--resources',
+                        required=True,
+                        metavar='resourcefile.yaml',
+                        help='Resources definition yaml file')
+    # auth bits, letting us also just source the devstack openrc
+    parser.add_argument('--os-username',
+                        metavar='<auth-user-name>',
+                        default=os.environ.get('OS_USERNAME'),
+                        help=('Defaults to env[OS_USERNAME].'))
+    parser.add_argument('--os-password',
+                        metavar='<auth-password>',
+                        default=os.environ.get('OS_PASSWORD'),
+                        help=('Defaults to env[OS_PASSWORD].'))
+    parser.add_argument('--os-tenant-name',
+                        metavar='<auth-tenant-name>',
+                        default=os.environ.get('OS_TENANT_NAME'),
+                        help=('Defaults to env[OS_TENANT_NAME].'))
+
+    OPTS = parser.parse_args()
+    if OPTS.mode not in ('create', 'check', 'destroy'):
+        print("ERROR: Unknown mode -m %s\n" % OPTS.mode)
+        parser.print_help()
+        sys.exit(1)
+
+
+def setup_logging(debug=True):
+    global LOG
+    LOG = logging.getLogger(__name__)
+    if debug:
+        LOG.setLevel(logging.DEBUG)
+    else:
+        LOG.setLevel(logging.INFO)
+
+    ch = logging.StreamHandler(sys.stdout)
+    ch.setLevel(logging.DEBUG)
+    formatter = logging.Formatter(
+        datefmt='%Y-%m-%d %H:%M:%S',
+        fmt='%(asctime)s.%(msecs).03d - %(levelname)s - %(message)s')
+    ch.setFormatter(formatter)
+    LOG.addHandler(ch)
+
+
+def main():
+    global RES
+    get_options()
+    setup_logging()
+    RES = load_resources(OPTS.resources)
+
+    if OPTS.mode == 'create':
+        create_resources()
+    elif OPTS.mode == 'check':
+        collect_users(RES['users'])
+        checker = JavelinCheck(USERS, RES)
+        checker.check()
+    elif OPTS.mode == 'destroy':
+        LOG.warn("Destroy mode not yet implemented")
+    else:
+        LOG.error('Unknown mode %s' % OPTS.mode)
+        return 1
+    return 0
+
+if __name__ == "__main__":
+    sys.exit(main())
diff --git a/tempest/cmd/resources.yaml b/tempest/cmd/resources.yaml
new file mode 100644
index 0000000..f7cb8a9
--- /dev/null
+++ b/tempest/cmd/resources.yaml
@@ -0,0 +1,51 @@
+# This is a yaml description for the most basic definitions
+# of what should exist across the resource boundary. Perhaps
+# one day this will grow into a Heat resource template, but as
+# Heat isn't a known working element in the upgrades, we do
+# this much simpler thing for now.
+
+tenants:
+  - javelin
+  - discuss
+
+users:
+  - name: javelin
+    pass: gungnir
+    tenant: javelin
+  - name: javelin2
+    pass: gungnir2
+    tenant: discuss
+
+secgroups:
+  - angon:
+    owner: javelin
+    rules:
+      - 'icmp -1 -1 0.0.0.0/0'
+      - 'tcp 22 22 0.0.0.0/0'
+
+# resources that we want to create
+images:
+  - name: javelin_cirros
+    owner: javelin
+    file: cirros-0.3.2-x86_64-blank.img
+    format: ami
+    aki: cirros-0.3.2-x86_64-vmlinuz
+    ari: cirros-0.3.2-x86_64-initrd
+volumes:
+  - assegai:
+    - owner: javelin
+    - gb: 1
+servers:
+  - name: peltast
+    owner: javelin
+    flavor: m1.small
+    image: javelin_cirros
+  - name: hoplite
+    owner: javelin
+    flavor: m1.medium
+    image: javelin_cirros
+objects:
+  - container: jc1
+    name: javelin1
+    owner: javelin
+    file: /etc/hosts
diff --git a/tempest/common/commands.py b/tempest/common/commands.py
index c31a038..6720847 100644
--- a/tempest/common/commands.py
+++ b/tempest/common/commands.py
@@ -28,15 +28,13 @@
     args = shlex.split(cmd)
     subprocess_args = {'stdout': subprocess.PIPE,
                        'stderr': subprocess.STDOUT}
-    try:
-        proc = subprocess.Popen(['/usr/bin/sudo', '-n'] + args,
-                                **subprocess_args)
-        return proc.communicate()[0]
-        if proc.returncode != 0:
-            LOG.error(cmd + "returned with: " +
-                      proc.returncode + "exit status")
-    except subprocess.CalledProcessError as e:
-        LOG.error("command output:\n%s" % e.output)
+    proc = subprocess.Popen(['/usr/bin/sudo', '-n'] + args,
+                            **subprocess_args)
+    stdout = proc.communicate()[0]
+    if proc.returncode != 0:
+        LOG.error(("Command {0} returned with exit status {1},"
+                   "output {2}").format(cmd, proc.returncode, stdout))
+    return stdout
 
 
 def ip_addr_raw():
@@ -77,3 +75,22 @@
 
 def ovs_db_dump():
     return sudo_cmd_call("ovsdb-client dump")
+
+
+def copy_file_to_host(file_from, dest, host, username, pkey):
+    dest = "%s@%s:%s" % (username, host, dest)
+    cmd = "scp -v -o UserKnownHostsFile=/dev/null " \
+          "-o StrictHostKeyChecking=no " \
+          "-i %(pkey)s %(file1)s %(dest)s" % {'pkey': pkey,
+                                              'file1': file_from,
+                                              'dest': dest}
+    args = shlex.split(cmd)
+    subprocess_args = {'stdout': subprocess.PIPE,
+                       'stderr': subprocess.STDOUT}
+    proc = subprocess.Popen(args, **subprocess_args)
+    stdout, stderr = proc.communicate()
+    if proc.returncode != 0:
+        LOG.error(("Command {0} returned with exit status {1},"
+                  "output {2}, error {3}").format(cmd, proc.returncode,
+                                                  stdout, stderr))
+    return stdout
diff --git a/tempest/common/rest_client.py b/tempest/common/rest_client.py
index 10223a0..3c527f5 100644
--- a/tempest/common/rest_client.py
+++ b/tempest/common/rest_client.py
@@ -238,6 +238,14 @@
                 return resp[i]
         return ""
 
+    def _log_request_start(self, method, req_url, req_headers={},
+                           req_body=None):
+        caller_name = misc_utils.find_test_caller()
+        trace_regex = CONF.debug.trace_requests
+        if trace_regex and re.search(trace_regex, caller_name):
+            self.LOG.debug('Starting Request (%s): %s %s' %
+                           (caller_name, method, req_url))
+
     def _log_request(self, method, req_url, resp,
                      secs="", req_headers={},
                      req_body=None, resp_body=None):
@@ -364,6 +372,7 @@
 
         # Do the actual request, and time it
         start = time.time()
+        self._log_request_start(method, req_url)
         resp, resp_body = self.http_obj.request(
             req_url, method, headers=req_headers, body=req_body)
         end = time.time()
diff --git a/tempest/common/utils/misc.py b/tempest/common/utils/misc.py
index b9f411b..0d78273 100644
--- a/tempest/common/utils/misc.py
+++ b/tempest/common/utils/misc.py
@@ -60,6 +60,9 @@
                 break
             elif re.search("^_run_cleanup", name):
                 is_cleanup = True
+            elif name == 'main':
+                caller_name = 'main'
+                break
             else:
                 cname = ""
                 if 'self' in frame.f_locals:
diff --git a/tempest/config.py b/tempest/config.py
index f9be90d..1049f67 100644
--- a/tempest/config.py
+++ b/tempest/config.py
@@ -137,11 +137,12 @@
                      "better parallel execution, but also requires that "
                      "OpenStack Identity API admin credentials are known."),
     cfg.StrOpt('image_ref',
-               default="{$IMAGE_ID}",
-               help="Valid primary image reference to be used in tests."),
+               help="Valid primary image reference to be used in tests. "
+                    "This is a required option"),
     cfg.StrOpt('image_ref_alt',
-               default="{$IMAGE_ID_ALT}",
-               help="Valid secondary image reference to be used in tests."),
+               help="Valid secondary image reference to be used in tests. "
+                    "This is a required option, but if only one image is "
+                    "available duplicate the value of image_ref above"),
     cfg.StrOpt('flavor_ref',
                default="1",
                help="Valid primary flavor to use in tests."),
@@ -163,7 +164,7 @@
                help="Password used to authenticate to an instance using "
                     "the alternate image."),
     cfg.IntOpt('build_interval',
-               default=10,
+               default=1,
                help="Time in seconds between build status checks."),
     cfg.IntOpt('build_timeout',
                default=300,
@@ -411,7 +412,7 @@
                help="Timeout in seconds to wait for network operation to "
                     "complete."),
     cfg.IntOpt('build_interval',
-               default=10,
+               default=1,
                help="Time in seconds between network operation status "
                     "checks."),
 ]
@@ -436,6 +437,10 @@
     cfg.StrOpt('catalog_type',
                default='queuing',
                help='Catalog type of the Queuing service.'),
+    cfg.IntOpt('max_queues_per_page',
+               default=20,
+               help='The maximum number of queue records per page when '
+                    'listing queues'),
 ]
 
 volume_group = cfg.OptGroup(name='volume',
@@ -443,7 +448,7 @@
 
 VolumeGroup = [
     cfg.IntOpt('build_interval',
-               default=10,
+               default=1,
                help='Time in seconds between volume availability checks.'),
     cfg.IntOpt('build_timeout',
                default=300,
diff --git a/tempest/scenario/manager.py b/tempest/scenario/manager.py
index 0ef34c6..f4850bb 100644
--- a/tempest/scenario/manager.py
+++ b/tempest/scenario/manager.py
@@ -16,9 +16,12 @@
 
 import logging
 import os
+import re
 import six
 import subprocess
+import time
 
+from heatclient import exc as heat_exceptions
 import netaddr
 from neutronclient.common import exceptions as exc
 from novaclient import exceptions as nova_exceptions
@@ -32,6 +35,7 @@
 from tempest import config
 from tempest import exceptions
 from tempest.openstack.common import log
+from tempest.openstack.common import timeutils
 import tempest.test
 
 CONF = config.CONF
@@ -114,8 +118,10 @@
             resource.delete()
         except Exception as e:
             # If the resource is already missing, mission accomplished.
-            # add status code as workaround for bug 1247568
-            if (e.__class__.__name__ == 'NotFound' or
+            # - Status code tolerated as a workaround for bug 1247568
+            # - HTTPNotFound tolerated as this is currently raised when
+            # attempting to delete an already-deleted heat stack.
+            if (e.__class__.__name__ in ('NotFound', 'HTTPNotFound') or
                     (hasattr(e, 'status_code') and e.status_code == 404)):
                 return
             raise
@@ -279,7 +285,6 @@
         for ruleset in rulesets:
             sg_rule = client.security_group_rules.create(secgroup_id,
                                                          **ruleset)
-            self.set_resource(sg_rule.id, sg_rule)
             rules.append(sg_rule)
         return rules
 
@@ -405,7 +410,7 @@
             'name': name,
             'container_format': fmt,
             'disk_format': fmt,
-            'is_public': 'True',
+            'is_public': 'False',
         }
         params.update(properties)
         image = self.image_client.images.create(**params)
@@ -917,7 +922,6 @@
             client=client,
             **sg_rule['security_group_rule']
         )
-        self.set_resource(sg_rule.id, sg_rule)
         self.assertEqual(secgroup.tenant_id, sg_rule.tenant_id)
         self.assertEqual(secgroup.id, sg_rule.security_group_id)
 
@@ -1067,3 +1071,98 @@
         for net in networks['networks']:
             if net['name'] == CONF.compute.fixed_network_name:
                 return net
+
+    @staticmethod
+    def _stack_output(stack, output_key):
+        """Return a stack output value for a given key."""
+        return next((o['output_value'] for o in stack.outputs
+                    if o['output_key'] == output_key), None)
+
+    def _ping_ip_address(self, ip_address, should_succeed=True):
+        cmd = ['ping', '-c1', '-w1', ip_address]
+
+        def ping():
+            proc = subprocess.Popen(cmd,
+                                    stdout=subprocess.PIPE,
+                                    stderr=subprocess.PIPE)
+            proc.wait()
+            return (proc.returncode == 0) == should_succeed
+
+        return tempest.test.call_until_true(
+            ping, CONF.orchestration.build_timeout, 1)
+
+    def _wait_for_resource_status(self, stack_identifier, resource_name,
+                                  status, failure_pattern='^.*_FAILED$'):
+        """Waits for a Resource to reach a given status."""
+        fail_regexp = re.compile(failure_pattern)
+        build_timeout = CONF.orchestration.build_timeout
+        build_interval = CONF.orchestration.build_interval
+
+        start = timeutils.utcnow()
+        while timeutils.delta_seconds(start,
+                                      timeutils.utcnow()) < build_timeout:
+            try:
+                res = self.client.resources.get(
+                    stack_identifier, resource_name)
+            except heat_exceptions.HTTPNotFound:
+                # ignore this, as the resource may not have
+                # been created yet
+                pass
+            else:
+                if res.resource_status == status:
+                    return
+                if fail_regexp.search(res.resource_status):
+                    raise exceptions.StackResourceBuildErrorException(
+                        resource_name=res.resource_name,
+                        stack_identifier=stack_identifier,
+                        resource_status=res.resource_status,
+                        resource_status_reason=res.resource_status_reason)
+            time.sleep(build_interval)
+
+        message = ('Resource %s failed to reach %s status within '
+                   'the required time (%s s).' %
+                   (res.resource_name, status, build_timeout))
+        raise exceptions.TimeoutException(message)
+
+    def _wait_for_stack_status(self, stack_identifier, status,
+                               failure_pattern='^.*_FAILED$'):
+        """
+        Waits for a Stack to reach a given status.
+
+        Note this compares the full $action_$status, e.g
+        CREATE_COMPLETE, not just COMPLETE which is exposed
+        via the status property of Stack in heatclient
+        """
+        fail_regexp = re.compile(failure_pattern)
+        build_timeout = CONF.orchestration.build_timeout
+        build_interval = CONF.orchestration.build_interval
+
+        start = timeutils.utcnow()
+        while timeutils.delta_seconds(start,
+                                      timeutils.utcnow()) < build_timeout:
+            try:
+                stack = self.client.stacks.get(stack_identifier)
+            except heat_exceptions.HTTPNotFound:
+                # ignore this, as the stackource may not have
+                # been created yet
+                pass
+            else:
+                if stack.stack_status == status:
+                    return
+                if fail_regexp.search(stack.stack_status):
+                    raise exceptions.StackBuildErrorException(
+                        stack_identifier=stack_identifier,
+                        stack_status=stack.stack_status,
+                        stack_status_reason=stack.stack_status_reason)
+            time.sleep(build_interval)
+
+        message = ('Stack %s failed to reach %s status within '
+                   'the required time (%s s).' %
+                   (stack.stack_name, status, build_timeout))
+        raise exceptions.TimeoutException(message)
+
+    def _stack_delete(self, stack_identifier):
+        try:
+            self.client.stacks.delete(stack_identifier)
+        except heat_exceptions.HTTPNotFound:
+            pass
diff --git a/tempest/api/orchestration/stacks/templates/cfn_init_signal.yaml b/tempest/scenario/orchestration/cfn_init_signal.yaml
similarity index 97%
rename from tempest/api/orchestration/stacks/templates/cfn_init_signal.yaml
rename to tempest/scenario/orchestration/cfn_init_signal.yaml
index fa5345e..c95aabf 100644
--- a/tempest/api/orchestration/stacks/templates/cfn_init_signal.yaml
+++ b/tempest/scenario/orchestration/cfn_init_signal.yaml
@@ -62,7 +62,7 @@
           #!/bin/bash -v
           /opt/aws/bin/cfn-init
           /opt/aws/bin/cfn-signal -e 0 --data "`cat /tmp/smoke-status`" \
-              "WaitHandle"
+              --id smoke_status "WaitHandle"
   WaitHandle:
     Type: AWS::CloudFormation::WaitConditionHandle
   WaitCondition:
diff --git a/tempest/scenario/orchestration/test_server_cfn_init.py b/tempest/scenario/orchestration/test_server_cfn_init.py
new file mode 100644
index 0000000..36e6126
--- /dev/null
+++ b/tempest/scenario/orchestration/test_server_cfn_init.py
@@ -0,0 +1,130 @@
+#    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 json
+
+from tempest import config
+from tempest import exceptions
+from tempest.openstack.common import log as logging
+from tempest.scenario import manager
+from tempest import test
+
+CONF = config.CONF
+LOG = logging.getLogger(__name__)
+
+
+class CfnInitScenarioTest(manager.OrchestrationScenarioTest):
+
+    def setUp(self):
+        super(CfnInitScenarioTest, self).setUp()
+        if not CONF.orchestration.image_ref:
+            raise self.skipException("No image available to test")
+        self.client = self.orchestration_client
+        self.template_name = 'cfn_init_signal.yaml'
+
+    def assign_keypair(self):
+        self.stack_name = self._stack_rand_name()
+        if CONF.orchestration.keypair_name:
+            self.keypair = None
+            self.keypair_name = CONF.orchestration.keypair_name
+        else:
+            self.keypair = self.create_keypair()
+            self.keypair_name = self.keypair.id
+
+    def launch_stack(self):
+        net = self._get_default_network()
+        self.parameters = {
+            'key_name': self.keypair_name,
+            'flavor': CONF.orchestration.instance_type,
+            'image': CONF.orchestration.image_ref,
+            'timeout': CONF.orchestration.build_timeout,
+            'network': net['id'],
+        }
+
+        # create the stack
+        self.template = self._load_template(__file__, self.template_name)
+        self.client.stacks.create(
+            stack_name=self.stack_name,
+            template=self.template,
+            parameters=self.parameters)
+
+        self.stack = self.client.stacks.get(self.stack_name)
+        self.stack_identifier = '%s/%s' % (self.stack_name, self.stack.id)
+        self.addCleanup(self._stack_delete, self.stack_identifier)
+
+    def check_stack(self):
+        sid = self.stack_identifier
+        self._wait_for_resource_status(
+            sid, 'WaitHandle', 'CREATE_COMPLETE')
+        self._wait_for_resource_status(
+            sid, 'SmokeSecurityGroup', 'CREATE_COMPLETE')
+        self._wait_for_resource_status(
+            sid, 'SmokeKeys', 'CREATE_COMPLETE')
+        self._wait_for_resource_status(
+            sid, 'CfnUser', 'CREATE_COMPLETE')
+        self._wait_for_resource_status(
+            sid, 'SmokeServer', 'CREATE_COMPLETE')
+
+        server_resource = self.client.resources.get(sid, 'SmokeServer')
+        server_id = server_resource.physical_resource_id
+        server = self.compute_client.servers.get(server_id)
+        server_ip = server.networks[CONF.compute.network_for_ssh][0]
+
+        if not self._ping_ip_address(server_ip):
+            self._log_console_output(servers=[server])
+            self.fail(
+                "Timed out waiting for %s to become reachable" % server_ip)
+
+        try:
+            self._wait_for_resource_status(
+                sid, 'WaitCondition', 'CREATE_COMPLETE')
+        except (exceptions.StackResourceBuildErrorException,
+                exceptions.TimeoutException) as e:
+            raise e
+        finally:
+            # attempt to log the server console regardless of WaitCondition
+            # going to complete. This allows successful and failed cloud-init
+            # logs to be compared
+            self._log_console_output(servers=[server])
+
+        self._wait_for_stack_status(sid, 'CREATE_COMPLETE')
+
+        stack = self.client.stacks.get(sid)
+
+        # 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 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(
+            self._stack_output(stack, 'WaitConditionStatus'))
+        self.assertEqual('smoke test complete', wait_status['smoke_status'])
+
+        if self.keypair:
+            # Check that the user can authenticate with the generated
+            # keypair
+            try:
+                linux_client = self.get_remote_client(
+                    server_ip, username='ec2-user')
+                linux_client.validate_authentication()
+            except (exceptions.ServerUnreachable,
+                    exceptions.SSHTimeout) as e:
+                self._log_console_output(servers=[server])
+                raise e
+
+    @test.attr(type='slow')
+    @test.services('orchestration', 'compute')
+    def test_server_cfn_init(self):
+        self.assign_keypair()
+        self.launch_stack()
+        self.check_stack()
diff --git a/tempest/scenario/test_aggregates_basic_ops.py b/tempest/scenario/test_aggregates_basic_ops.py
index 8e34c16..6817c48 100644
--- a/tempest/scenario/test_aggregates_basic_ops.py
+++ b/tempest/scenario/test_aggregates_basic_ops.py
@@ -54,8 +54,8 @@
     def _get_host_name(self):
         hosts = self.compute_client.hosts.list()
         self.assertTrue(len(hosts) >= 1)
-        hostname = hosts[0].host_name
-        return hostname
+        computes = [x for x in hosts if x.service == 'compute']
+        return computes[0].host_name
 
     def _add_host(self, aggregate_name, host):
         aggregate = self.compute_client.aggregates.add_host(aggregate_name,
diff --git a/tempest/scenario/test_large_ops.py b/tempest/scenario/test_large_ops.py
index 0210c56..ed5743c 100644
--- a/tempest/scenario/test_large_ops.py
+++ b/tempest/scenario/test_large_ops.py
@@ -63,11 +63,20 @@
             self.set_resource(server.name, server)
         self._wait_for_server_status('ACTIVE')
 
-    @test.services('compute', 'image')
-    def test_large_ops_scenario(self):
+    def _large_ops_scenario(self):
         if CONF.scenario.large_ops_number < 1:
             return
         self.glance_image_create()
         self.nova_boot()
-        self.nova_boot()
-        self.nova_boot()
+
+    @test.services('compute', 'image')
+    def test_large_ops_scenario_1(self):
+        self._large_ops_scenario()
+
+    @test.services('compute', 'image')
+    def test_large_ops_scenario_2(self):
+        self._large_ops_scenario()
+
+    @test.services('compute', 'image')
+    def test_large_ops_scenario_3(self):
+        self._large_ops_scenario()
diff --git a/tempest/scenario/test_load_balancer_basic.py b/tempest/scenario/test_load_balancer_basic.py
index d771aed..1c24b5c 100644
--- a/tempest/scenario/test_load_balancer_basic.py
+++ b/tempest/scenario/test_load_balancer_basic.py
@@ -13,10 +13,14 @@
 #    License for the specific language governing permissions and limitations
 #    under the License.
 
+
+import httplib
+import tempfile
 import time
-import urllib
+import urllib2
 
 from tempest.api.network import common as net_common
+from tempest.common import commands
 from tempest import config
 from tempest import exceptions
 from tempest.scenario import manager
@@ -68,6 +72,7 @@
     def setUp(self):
         super(TestLoadBalancerBasic, self).setUp()
         self.server_ips = {}
+        self.server_fixed_ips = {}
         self._create_security_group()
 
     def cleanup_wrapper(self, resource):
@@ -119,6 +124,7 @@
             self.server_ips[server.id] = floating_ip.floating_ip_address
         else:
             self.server_ips[server.id] = server.networks[net['name']][0]
+        self.server_fixed_ips[server.id] = server.networks[net['name']][0]
         self.assertTrue(self.servers_keypairs)
         return server
 
@@ -133,71 +139,53 @@
 
         1. SSH to the instance
         2. Start two http backends listening on ports 80 and 88 respectively
-        In case there are two instances, each backend is created on a separate
-        instance.
-
-        The backends are the inetd services. To start them we need to edit
-        /etc/inetd.conf in the following way:
-        www stream tcp nowait root /bin/sh sh /home/cirros/script_name
-
-        Where /home/cirros/script_name is a path to a script which
-        echoes the responses:
-        echo -e 'HTTP/1.0 200 OK\r\n\r\nserver_name
-
-        If we want the server to listen on port 88, then we use
-        "kerberos" instead of "www".
         """
 
         for server_id, ip in self.server_ips.iteritems():
             private_key = self.servers_keypairs[server_id].private_key
             server_name = self.compute_client.servers.get(server_id).name
+            username = config.scenario.ssh_user
             ssh_client = self.get_remote_client(
                 server_or_ip=ip,
                 private_key=private_key)
             ssh_client.validate_authentication()
-            # Create service for inetd
-            create_script = """sudo sh -c "echo -e \\"echo -e 'HTTP/1.0 """ \
-                            """200 OK\\\\\\r\\\\\\n\\\\\\r\\\\\\n""" \
-                            """%(server)s'\\" >>/home/cirros/%(script)s\""""
 
-            cmd = create_script % {
-                'server': server_name,
-                'script': 'script1'}
+            # Write a backend's responce into a file
+            resp = """HTTP/1.0 200 OK\r\nContent-Length: 8\r\n\r\n%s"""
+            with tempfile.NamedTemporaryFile() as script:
+                script.write(resp % server_name)
+                script.flush()
+                with tempfile.NamedTemporaryFile() as key:
+                    key.write(private_key)
+                    key.flush()
+                    commands.copy_file_to_host(script.name,
+                                               "~/script1",
+                                               ip,
+                                               username, key.name)
+            # Start netcat
+            start_server = """sudo nc -ll -p %(port)s -e cat """ \
+                           """~/%(script)s &"""
+            cmd = start_server % {'port': self.port1,
+                                  'script': 'script1'}
             ssh_client.exec_command(cmd)
-            # Configure inetd
-            configure_inetd = """sudo sh -c "echo -e \\"%(service)s """ \
-                              """stream tcp nowait root /bin/sh sh """ \
-                              """/home/cirros/%(script)s\\" >> """ \
-                              """/etc/inetd.conf\""""
-            # "www" stands for port 80
-            cmd = configure_inetd % {'service': 'www',
-                                     'script': 'script1'}
-            ssh_client.exec_command(cmd)
-
             if len(self.server_ips) == 1:
-                cmd = create_script % {'server': 'server2',
-                                       'script': 'script2'}
+                with tempfile.NamedTemporaryFile() as script:
+                    script.write(resp % 'server2')
+                    script.flush()
+                    with tempfile.NamedTemporaryFile() as key:
+                        key.write(private_key)
+                        key.flush()
+                        commands.copy_file_to_host(script.name,
+                                                   "~/script2", ip,
+                                                   username, key.name)
+                cmd = start_server % {'port': self.port2,
+                                      'script': 'script2'}
                 ssh_client.exec_command(cmd)
-                # "kerberos" stands for port 88
-                cmd = configure_inetd % {'service': 'kerberos',
-                                         'script': 'script2'}
-                ssh_client.exec_command(cmd)
-
-            # Get PIDs of inetd
-            pids = ssh_client.get_pids('inetd')
-            if pids != ['']:
-                # If there are any inetd processes, reload them
-                kill_cmd = "sudo kill -HUP %s" % ' '.join(pids)
-                ssh_client.exec_command(kill_cmd)
-            else:
-                # In other case start inetd
-                start_inetd = "sudo /usr/sbin/inetd /etc/inetd.conf"
-                ssh_client.exec_command(start_inetd)
 
     def _check_connection(self, check_ip, port=80):
         def try_connect(ip, port):
             try:
-                resp = urllib.urlopen("http://{0}:{1}/".format(ip, port))
+                resp = urllib2.urlopen("http://{0}:{1}/".format(ip, port))
                 if resp.getcode() == 200:
                     return True
                 return False
@@ -231,8 +219,8 @@
         but with different ports to listen on.
         """
 
-        for server_id, ip in self.server_ips.iteritems():
-            if len(self.server_ips) == 1:
+        for server_id, ip in self.server_fixed_ips.iteritems():
+            if len(self.server_fixed_ips) == 1:
                 member1 = self._create_member(address=ip,
                                               protocol_port=self.port1,
                                               pool_id=self.pool.id)
@@ -282,27 +270,32 @@
 
     def _check_load_balancing(self):
         """
-        1. Send 100 requests on the floating ip associated with the VIP
+        1. Send 10 requests on the floating ip associated with the VIP
         2. Check that the requests are shared between
            the two servers and that both of them get equal portions
            of the requests
         """
 
         self._check_connection(self.vip_ip)
-        resp = self._send_requests(self.vip_ip)
-        self.assertEqual(set(["server1\n", "server2\n"]), set(resp))
-        self.assertEqual(50, resp.count("server1\n"))
-        self.assertEqual(50, resp.count("server2\n"))
+        self._send_requests(self.vip_ip, set(["server1", "server2"]))
 
-    def _send_requests(self, vip_ip):
-        resp = []
-        for count in range(100):
-            resp.append(
-                urllib.urlopen(
-                    "http://{0}/".format(vip_ip)).read())
-        return resp
+    def _send_requests(self, vip_ip, expected, num_req=10):
+        count = 0
+        while count < num_req:
+            try:
+                resp = []
+                for i in range(len(self.members)):
+                    resp.append(
+                        urllib2.urlopen(
+                            "http://{0}/".format(vip_ip)).read())
+                count += 1
+                self.assertEqual(expected,
+                                 set(resp))
+            # NOTE: There always is a slim chance of getting this exception
+            #       due to special aspects of haproxy internal behavior.
+            except httplib.BadStatusLine:
+                pass
 
-    @test.skip_because(bug='1295165')
     @test.attr(type='smoke')
     @test.services('compute', 'network')
     def test_load_balancer_basic(self):
diff --git a/tempest/scenario/test_network_advanced_server_ops.py b/tempest/scenario/test_network_advanced_server_ops.py
index 0ba65cf..9b435bd 100644
--- a/tempest/scenario/test_network_advanced_server_ops.py
+++ b/tempest/scenario/test_network_advanced_server_ops.py
@@ -20,7 +20,7 @@
 from tempest import config
 from tempest.openstack.common import log as logging
 from tempest.scenario import manager
-from tempest.test import services
+from tempest import test
 
 CONF = config.CONF
 LOG = logging.getLogger(__name__)
@@ -84,6 +84,7 @@
         self.floating_ip = self._create_floating_ip(self.server,
                                                     public_network_id)
         self.addCleanup(self.cleanup_wrapper, self.floating_ip)
+        self._wait_server_status_and_check_network_connectivity()
 
     def _check_tenant_network_connectivity(self, server,
                                            username,
@@ -140,7 +141,7 @@
                             'ACTIVE')
         self._check_network_connectivity()
 
-    @services('compute', 'network')
+    @test.services('compute', 'network')
     def test_server_connectivity_stop_start(self):
         self.server.stop()
         self.status_timeout(self.compute_client.servers, self.server.id,
@@ -149,12 +150,12 @@
         self.server.start()
         self._wait_server_status_and_check_network_connectivity()
 
-    @services('compute', 'network')
+    @test.services('compute', 'network')
     def test_server_connectivity_reboot(self):
         self.server.reboot()
         self._wait_server_status_and_check_network_connectivity()
 
-    @services('compute', 'network')
+    @test.services('compute', 'network')
     def test_server_connectivity_rebuild(self):
         image_ref_alt = CONF.compute.image_ref_alt
         self.server.rebuild(image_ref_alt)
@@ -162,7 +163,7 @@
 
     @testtools.skipUnless(CONF.compute_feature_enabled.pause,
                           'Pause is not available.')
-    @services('compute', 'network')
+    @test.services('compute', 'network')
     def test_server_connectivity_pause_unpause(self):
         self.server.pause()
         self.status_timeout(self.compute_client.servers, self.server.id,
@@ -173,7 +174,7 @@
 
     @testtools.skipUnless(CONF.compute_feature_enabled.suspend,
                           'Suspend is not available.')
-    @services('compute', 'network')
+    @test.services('compute', 'network')
     def test_server_connectivity_suspend_resume(self):
         self.server.suspend()
         self.status_timeout(self.compute_client.servers, self.server.id,
@@ -184,7 +185,7 @@
 
     @testtools.skipUnless(CONF.compute_feature_enabled.resize,
                           'Resize is not available.')
-    @services('compute', 'network')
+    @test.services('compute', 'network')
     def test_server_connectivity_resize(self):
         resize_flavor = CONF.compute.flavor_ref_alt
         if resize_flavor == CONF.compute.flavor_ref:
diff --git a/tempest/services/compute/json/interfaces_client.py b/tempest/services/compute/json/interfaces_client.py
index 8d51123..cdac8b7 100644
--- a/tempest/services/compute/json/interfaces_client.py
+++ b/tempest/services/compute/json/interfaces_client.py
@@ -17,6 +17,7 @@
 import time
 
 from tempest.api_schema.compute import interfaces as common_schema
+from tempest.api_schema.compute import servers as servers_schema
 from tempest.api_schema.compute.v2 import interfaces as schema
 from tempest.common import rest_client
 from tempest import config
@@ -94,6 +95,8 @@
         })
         resp, body = self.post('servers/%s/action' % str(server_id),
                                post_body)
+        self.validate_response(servers_schema.server_actions_common_schema,
+                               resp, body)
         return resp, body
 
     def remove_fixed_ip(self, server_id, ip_address):
@@ -105,4 +108,6 @@
         })
         resp, body = self.post('servers/%s/action' % str(server_id),
                                post_body)
+        self.validate_response(servers_schema.server_actions_common_schema,
+                               resp, body)
         return resp, body
diff --git a/tempest/services/compute/json/security_groups_client.py b/tempest/services/compute/json/security_groups_client.py
index c19baf3..a86f3df 100644
--- a/tempest/services/compute/json/security_groups_client.py
+++ b/tempest/services/compute/json/security_groups_client.py
@@ -88,7 +88,10 @@
 
     def delete_security_group(self, security_group_id):
         """Deletes the provided Security Group."""
-        return self.delete('os-security-groups/%s' % str(security_group_id))
+        resp, body = self.delete(
+            'os-security-groups/%s' % str(security_group_id))
+        self.validate_response(schema.delete_security_group, resp, body)
+        return resp, body
 
     def create_security_group_rule(self, parent_group_id, ip_proto, from_port,
                                    to_port, **kwargs):
diff --git a/tempest/services/compute/json/servers_client.py b/tempest/services/compute/json/servers_client.py
index 92cfc8e..70123fe 100644
--- a/tempest/services/compute/json/servers_client.py
+++ b/tempest/services/compute/json/servers_client.py
@@ -193,6 +193,7 @@
         """Lists all addresses for a server."""
         resp, body = self.get("servers/%s/ips" % str(server_id))
         body = json.loads(body)
+        self.validate_response(schema.list_addresses, resp, body)
         return resp, body['addresses']
 
     def list_addresses_by_network(self, server_id, network_id):
@@ -204,20 +205,24 @@
         return resp, body
 
     def action(self, server_id, action_name, response_key,
-               schema=None, **kwargs):
+               schema=common_schema.server_actions_common_schema, **kwargs):
         post_body = json.dumps({action_name: kwargs})
         resp, body = self.post('servers/%s/action' % str(server_id),
                                post_body)
         if response_key is not None:
             body = json.loads(body)
-            # Check for Schema as 'None' because if we donot have any server
+            # Check for Schema as 'None' because if we do not have any server
             # action schema implemented yet then they can pass 'None' to skip
             # the validation.Once all server action has their schema
             # implemented then, this check can be removed if every actions are
             # supposed to validate their response.
+            # TODO(GMann): Remove the below 'if' check once all server actions
+            # schema are implemented.
             if schema is not None:
                 self.validate_response(schema, resp, body)
             body = body[response_key]
+        else:
+            self.validate_response(schema, resp, body)
         return resp, body
 
     def create_backup(self, server_id, backup_type, rotation, name):
@@ -245,8 +250,11 @@
         Note that this does not actually change the instance server
         password.
         """
-        return self.delete("servers/%s/os-server-password" %
-                           str(server_id))
+        resp, body = self.delete("servers/%s/os-server-password" %
+                                 str(server_id))
+        self.validate_response(common_schema.server_actions_delete_password,
+                               resp, body)
+        return resp, body
 
     def reboot(self, server_id, reboot_type):
         """Reboots a server."""
@@ -258,7 +266,7 @@
         if 'disk_config' in kwargs:
             kwargs['OS-DCF:diskConfig'] = kwargs['disk_config']
             del kwargs['disk_config']
-        return self.action(server_id, 'rebuild', 'server', **kwargs)
+        return self.action(server_id, 'rebuild', 'server', None, **kwargs)
 
     def resize(self, server_id, flavor_ref, **kwargs):
         """Changes the flavor of a server."""
@@ -270,7 +278,9 @@
 
     def confirm_resize(self, server_id, **kwargs):
         """Confirms the flavor change for a server."""
-        return self.action(server_id, 'confirmResize', None, **kwargs)
+        return self.action(server_id, 'confirmResize',
+                           None, schema.server_actions_confirm_resize,
+                           **kwargs)
 
     def revert_resize(self, server_id, **kwargs):
         """Reverts a server back to its original flavor."""
@@ -370,6 +380,8 @@
         req_body = json.dumps({'os-migrateLive': migrate_params})
 
         resp, body = self.post("servers/%s/action" % str(server_id), req_body)
+        self.validate_response(common_schema.server_actions_common_schema,
+                               resp, body)
         return resp, body
 
     def migrate_server(self, server_id, **kwargs):
@@ -418,7 +430,7 @@
 
     def get_console_output(self, server_id, length):
         return self.action(server_id, 'os-getConsoleOutput', 'output',
-                           length=length)
+                           common_schema.get_console_output, length=length)
 
     def list_virtual_interfaces(self, server_id):
         """
@@ -432,7 +444,7 @@
 
     def rescue_server(self, server_id, **kwargs):
         """Rescue the provided server."""
-        return self.action(server_id, 'rescue', None, **kwargs)
+        return self.action(server_id, 'rescue', 'adminPass', None, **kwargs)
 
     def unrescue_server(self, server_id):
         """Unrescue the provided server."""
@@ -478,3 +490,36 @@
         return self.action(server_id, "os-getVNCConsole",
                            "console", common_schema.get_vnc_console,
                            type=console_type)
+
+    def create_server_group(self, name, policies):
+        """
+        Create the server group
+        name : Name of the server-group
+        policies : List of the policies - affinity/anti-affinity)
+        """
+        post_body = {
+            'name': name,
+            'policies': policies,
+        }
+
+        post_body = json.dumps({'server_group': post_body})
+        resp, body = self.post('os-server-groups', post_body)
+
+        body = json.loads(body)
+        return resp, body['server_group']
+
+    def delete_server_group(self, server_group_id):
+        """Delete the given server-group."""
+        return self.delete("os-server-groups/%s" % str(server_group_id))
+
+    def list_server_groups(self):
+        """List the server-groups."""
+        resp, body = self.get("os-server-groups")
+        body = json.loads(body)
+        return resp, body['server_groups']
+
+    def get_server_group(self, server_group_id):
+        """Get the details of given server_group."""
+        resp, body = self.get("os-server-groups/%s" % str(server_group_id))
+        body = json.loads(body)
+        return resp, body['server_group']
diff --git a/tempest/services/compute/v3/json/interfaces_client.py b/tempest/services/compute/v3/json/interfaces_client.py
index 77b3179..e66ccaa 100644
--- a/tempest/services/compute/v3/json/interfaces_client.py
+++ b/tempest/services/compute/v3/json/interfaces_client.py
@@ -17,6 +17,7 @@
 import time
 
 from tempest.api_schema.compute import interfaces as common_schema
+from tempest.api_schema.compute import servers as servers_schema
 from tempest.api_schema.compute.v3 import interfaces as schema
 from tempest.common import rest_client
 from tempest import config
@@ -95,6 +96,8 @@
         })
         resp, body = self.post('servers/%s/action' % str(server_id),
                                post_body)
+        self.validate_response(servers_schema.server_actions_common_schema,
+                               resp, body)
         return resp, body
 
     def remove_fixed_ip(self, server_id, ip_address):
@@ -106,4 +109,6 @@
         })
         resp, body = self.post('servers/%s/action' % str(server_id),
                                post_body)
+        self.validate_response(servers_schema.server_actions_common_schema,
+                               resp, body)
         return resp, body
diff --git a/tempest/services/compute/v3/json/servers_client.py b/tempest/services/compute/v3/json/servers_client.py
index 1990d39..f397c4b 100644
--- a/tempest/services/compute/v3/json/servers_client.py
+++ b/tempest/services/compute/v3/json/servers_client.py
@@ -193,6 +193,7 @@
         """Lists all addresses for a server."""
         resp, body = self.get("servers/%s/ips" % str(server_id))
         body = json.loads(body)
+        self.validate_response(schema.list_addresses, resp, body)
         return resp, body['addresses']
 
     def list_addresses_by_network(self, server_id, network_id):
@@ -203,12 +204,25 @@
         self.validate_response(schema.list_addresses_by_network, resp, body)
         return resp, body
 
-    def action(self, server_id, action_name, response_key, **kwargs):
+    def action(self, server_id, action_name, response_key,
+               schema=common_schema.server_actions_common_schema, **kwargs):
         post_body = json.dumps({action_name: kwargs})
         resp, body = self.post('servers/%s/action' % str(server_id),
                                post_body)
         if response_key is not None:
-            body = json.loads(body)[response_key]
+            body = json.loads(body)
+            # Check for Schema as 'None' because if we do not have any server
+            # action schema implemented yet then they can pass 'None' to skip
+            # the validation.Once all server action has their schema
+            # implemented then, this check can be removed if every actions are
+            # supposed to validate their response.
+            # TODO(GMann): Remove the below 'if' check once all server actions
+            # schema are implemented.
+            if schema is not None:
+                self.validate_response(schema, resp, body)
+            body = body[response_key]
+        else:
+            self.validate_response(schema, resp, body)
         return resp, body
 
     def create_backup(self, server_id, backup_type, rotation, name):
@@ -220,7 +234,8 @@
 
     def change_password(self, server_id, admin_password):
         """Changes the root password for the server."""
-        return self.action(server_id, 'change_password', None,
+        return self.action(server_id, 'change_password',
+                           None, schema.server_actions_change_password,
                            admin_password=admin_password)
 
     def get_password(self, server_id):
@@ -236,8 +251,11 @@
         Note that this does not actually change the instance server
         password.
         """
-        return self.delete("servers/%s/os-server-password" %
-                           str(server_id))
+        resp, body = self.delete("servers/%s/os-server-password" %
+                                 str(server_id))
+        self.validate_response(common_schema.server_actions_delete_password,
+                               resp, body)
+        return resp, body
 
     def reboot(self, server_id, reboot_type):
         """Reboots a server."""
@@ -249,7 +267,7 @@
         if 'disk_config' in kwargs:
             kwargs['os-disk-config:disk_config'] = kwargs['disk_config']
             del kwargs['disk_config']
-        return self.action(server_id, 'rebuild', 'server', **kwargs)
+        return self.action(server_id, 'rebuild', 'server', None, **kwargs)
 
     def resize(self, server_id, flavor_ref, **kwargs):
         """Changes the flavor of a server."""
@@ -364,6 +382,8 @@
 
         resp, body = self.post("servers/%s/action" % str(server_id),
                                req_body)
+        self.validate_response(common_schema.server_actions_common_schema,
+                               resp, body)
         return resp, body
 
     def migrate_server(self, server_id, **kwargs):
@@ -412,11 +432,12 @@
 
     def get_console_output(self, server_id, length):
         return self.action(server_id, 'get_console_output', 'output',
-                           length=length)
+                           common_schema.get_console_output, length=length)
 
     def rescue_server(self, server_id, **kwargs):
         """Rescue the provided server."""
-        return self.action(server_id, 'rescue', None, **kwargs)
+        return self.action(server_id, 'rescue', 'admin_password',
+                           None, **kwargs)
 
     def unrescue_server(self, server_id):
         """Unrescue the provided server."""
@@ -474,9 +495,9 @@
     def get_spice_console(self, server_id, console_type):
         """Get URL of Spice console."""
         return self.action(server_id, "get_spice_console"
-                           "console", type=console_type)
+                           "console", None, type=console_type)
 
     def get_rdp_console(self, server_id, console_type):
         """Get URL of RDP console."""
         return self.action(server_id, "get_rdp_console"
-                           "console", type=console_type)
+                           "console", None, type=console_type)
diff --git a/tempest/services/data_processing/v1_1/client.py b/tempest/services/data_processing/v1_1/client.py
index 194e300..73e67c3 100644
--- a/tempest/services/data_processing/v1_1/client.py
+++ b/tempest/services/data_processing/v1_1/client.py
@@ -1,17 +1,16 @@
 # Copyright (c) 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
+#    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
+#         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.
+#    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 json
 
@@ -162,3 +161,28 @@
 
         uri = 'data-sources/%s' % source_id
         return self.delete(uri)
+
+    def list_job_binary_internals(self):
+        """List all job binary internals for a user."""
+
+        uri = 'job-binary-internals'
+        return self._request_and_parse(self.get, uri, 'binaries')
+
+    def get_job_binary_internal(self, job_binary_id):
+        """Returns the details of a single job binary internal."""
+
+        uri = 'job-binary-internals/%s' % job_binary_id
+        return self._request_and_parse(self.get, uri, 'job_binary_internal')
+
+    def create_job_binary_internal(self, name, data):
+        """Creates job binary internal with specified params."""
+
+        uri = 'job-binary-internals/%s' % name
+        return self._request_and_parse(self.put, uri, 'job_binary_internal',
+                                       data)
+
+    def delete_job_binary_internal(self, job_binary_id):
+        """Deletes the specified job binary internal by id."""
+
+        uri = 'job-binary-internals/%s' % job_binary_id
+        return self.delete(uri)
diff --git a/tempest/services/identity/json/identity_client.py b/tempest/services/identity/json/identity_client.py
index 55239f7..479a289 100644
--- a/tempest/services/identity/json/identity_client.py
+++ b/tempest/services/identity/json/identity_client.py
@@ -227,6 +227,16 @@
         url = '/OS-KSADM/services/%s' % service_id
         return self.delete(url)
 
+    def update_user_password(self, user_id, new_pass):
+        """Update User Password."""
+        put_body = {
+            'password': new_pass,
+            'id': user_id
+        }
+        put_body = json.dumps({'user': put_body})
+        resp, body = self.put('users/%s/OS-KSADM/password' % user_id, put_body)
+        return resp, self._parse_resp(body)
+
 
 class TokenClientJSON(IdentityClientJSON):
 
diff --git a/tempest/services/identity/xml/identity_client.py b/tempest/services/identity/xml/identity_client.py
index c48bc90..b213c1a 100644
--- a/tempest/services/identity/xml/identity_client.py
+++ b/tempest/services/identity/xml/identity_client.py
@@ -118,6 +118,15 @@
                                str(xml.Document(create_service)))
         return resp, self._parse_resp(body)
 
+    def update_user_password(self, user_id, new_pass):
+        """Update User Password."""
+        put_body = xml.Element("user",
+                               id=user_id,
+                               password=new_pass)
+        resp, body = self.put('users/%s/OS-KSADM/password' % user_id,
+                              str(xml.Document(put_body)))
+        return resp, self._parse_resp(body)
+
 
 class TokenClientXML(identity_client.TokenClientJSON):
     TYPE = "xml"
diff --git a/tempest/services/image/v2/json/image_client.py b/tempest/services/image/v2/json/image_client.py
index b3014fc..201869e 100644
--- a/tempest/services/image/v2/json/image_client.py
+++ b/tempest/services/image/v2/json/image_client.py
@@ -70,13 +70,12 @@
             "disk_format": disk_format,
         }
 
-        for option in ['visibility']:
-            if option in kwargs:
-                value = kwargs.get(option)
-                if isinstance(value, dict) or isinstance(value, tuple):
-                    params.update(value)
-                else:
-                    params[option] = value
+        for option in kwargs:
+            value = kwargs.get(option)
+            if isinstance(value, dict) or isinstance(value, tuple):
+                params.update(value)
+            else:
+                params[option] = value
 
         data = json.dumps(params)
         self._validate_schema(data)
diff --git a/tempest/services/network/xml/network_client.py b/tempest/services/network/xml/network_client.py
index a9d4880..a7a6b2c 100644
--- a/tempest/services/network/xml/network_client.py
+++ b/tempest/services/network/xml/network_client.py
@@ -24,7 +24,7 @@
     # list of plurals used for xml serialization
     PLURALS = ['dns_nameservers', 'host_routes', 'allocation_pools',
                'fixed_ips', 'extensions', 'extra_dhcp_opts', 'pools',
-               'health_monitors', 'vips', 'members']
+               'health_monitors', 'vips', 'members', 'allowed_address_pairs']
 
     def get_rest_client(self, auth_provider):
         rc = rest_client.RestClient(auth_provider)
diff --git a/tempest/services/orchestration/json/orchestration_client.py b/tempest/services/orchestration/json/orchestration_client.py
index 2311bdd..c459f28 100644
--- a/tempest/services/orchestration/json/orchestration_client.py
+++ b/tempest/services/orchestration/json/orchestration_client.py
@@ -45,28 +45,32 @@
         return resp, body['stacks']
 
     def create_stack(self, name, disable_rollback=True, parameters={},
-                     timeout_mins=60, template=None, template_url=None):
+                     timeout_mins=60, template=None, template_url=None,
+                     environment=None, files=None):
         headers, body = self._prepare_update_create(
             name,
             disable_rollback,
             parameters,
             timeout_mins,
             template,
-            template_url)
+            template_url,
+            environment,
+            files)
         uri = 'stacks'
         resp, body = self.post(uri, headers=headers, body=body)
         return resp, body
 
     def update_stack(self, stack_identifier, name, disable_rollback=True,
                      parameters={}, timeout_mins=60, template=None,
-                     template_url=None):
+                     template_url=None, environment=None, files=None):
         headers, body = self._prepare_update_create(
             name,
             disable_rollback,
             parameters,
             timeout_mins,
             template,
-            template_url)
+            template_url,
+            environment)
 
         uri = "stacks/%s" % stack_identifier
         resp, body = self.put(uri, headers=headers, body=body)
@@ -74,13 +78,16 @@
 
     def _prepare_update_create(self, name, disable_rollback=True,
                                parameters={}, timeout_mins=60,
-                               template=None, template_url=None):
+                               template=None, template_url=None,
+                               environment=None, files=None):
         post_body = {
             "stack_name": name,
             "disable_rollback": disable_rollback,
             "parameters": parameters,
             "timeout_mins": timeout_mins,
-            "template": "HeatTemplateFormatVersion: '2012-12-12'\n"
+            "template": "HeatTemplateFormatVersion: '2012-12-12'\n",
+            "environment": environment,
+            "files": files
         }
         if template:
             post_body['template'] = template
diff --git a/tempest/services/queuing/json/queuing_client.py b/tempest/services/queuing/json/queuing_client.py
index 4a0c495..e5978f5 100644
--- a/tempest/services/queuing/json/queuing_client.py
+++ b/tempest/services/queuing/json/queuing_client.py
@@ -15,6 +15,7 @@
 
 import json
 
+from tempest.api_schema.queuing.v1 import queues as queues_schema
 from tempest.common import rest_client
 from tempest import config
 
@@ -33,6 +34,7 @@
         uri = '{0}/queues'.format(self.uri_prefix)
         resp, body = self.get(uri)
         body = json.loads(body)
+        self.validate_response(queues_schema.list_queues, resp, body)
         return resp, body
 
     def create_queue(self, queue_name):
@@ -43,16 +45,32 @@
     def get_queue(self, queue_name):
         uri = '{0}/queues/{1}'.format(self.uri_prefix, queue_name)
         resp, body = self.get(uri)
-        body = json.loads(body)
         return resp, body
 
     def head_queue(self, queue_name):
         uri = '{0}/queues/{1}'.format(self.uri_prefix, queue_name)
         resp, body = self.head(uri)
-        body = json.loads(body)
         return resp, body
 
     def delete_queue(self, queue_name):
         uri = '{0}/queues/{1}'.format(self.uri_prefix, queue_name)
         resp = self.delete(uri)
         return resp
+
+    def get_queue_stats(self, queue_name):
+        uri = '{0}/queues/{1}/stats'.format(self.uri_prefix, queue_name)
+        resp, body = self.get(uri)
+        body = json.loads(body)
+        self.validate_response(queues_schema.queue_stats, resp, body)
+        return resp, body
+
+    def get_queue_metadata(self, queue_name):
+        uri = '{0}/queues/{1}/metadata'.format(self.uri_prefix, queue_name)
+        resp, body = self.get(uri)
+        body = json.loads(body)
+        return resp, body
+
+    def set_queue_metadata(self, queue_name, rbody):
+        uri = '{0}/queues/{1}/metadata'.format(self.uri_prefix, queue_name)
+        resp, body = self.put(uri, body=json.dumps(rbody))
+        return resp, body
diff --git a/tempest/services/volume/json/admin/volume_quotas_client.py b/tempest/services/volume/json/admin/volume_quotas_client.py
index ea9c92e..961c7da 100644
--- a/tempest/services/volume/json/admin/volume_quotas_client.py
+++ b/tempest/services/volume/json/admin/volume_quotas_client.py
@@ -77,3 +77,7 @@
         post_body = jsonutils.dumps({'quota_set': post_body})
         resp, body = self.put('os-quota-sets/%s' % tenant_id, post_body)
         return resp, self._parse_resp(body)
+
+    def delete_quota_set(self, tenant_id):
+        """Delete the tenant's quota set."""
+        return self.delete('os-quota-sets/%s' % tenant_id)
diff --git a/tempest/services/volume/json/admin/volume_types_client.py b/tempest/services/volume/json/admin/volume_types_client.py
index c9c0582..65ecc67 100644
--- a/tempest/services/volume/json/admin/volume_types_client.py
+++ b/tempest/services/volume/json/admin/volume_types_client.py
@@ -18,6 +18,7 @@
 
 from tempest.common import rest_client
 from tempest import config
+from tempest import exceptions
 
 CONF = config.CONF
 
@@ -34,6 +35,26 @@
         self.build_interval = CONF.volume.build_interval
         self.build_timeout = CONF.volume.build_timeout
 
+    def is_resource_deleted(self, resource):
+        # to use this method self.resource must be defined to respective value
+        # Resource is a dictionary containing resource id and type
+        # Resource : {"id" : resource_id
+        #             "type": resource_type}
+        try:
+            if resource['type'] == "volume-type":
+                self.get_volume_type(resource['id'])
+            elif resource['type'] == "encryption-type":
+                resp, body = self.get_encryption_type(resource['id'])
+                assert 200 == resp.status
+                if not body:
+                    return True
+            else:
+                msg = (" resource value is either not defined or incorrect.")
+                raise exceptions.UnprocessableEntity(msg)
+        except exceptions.NotFound:
+            return True
+        return False
+
     def list_volume_types(self, params=None):
         """List all the volume_types created."""
         url = 'types'
@@ -150,3 +171,7 @@
         resp, body = self.post(url, post_body)
         body = json.loads(body)
         return resp, body['encryption']
+
+    def delete_encryption_type(self, vol_type_id):
+        """Delete the encryption type for the specified volume-type."""
+        return self.delete("/types/%s/encryption/provider" % str(vol_type_id))
diff --git a/tempest/services/volume/json/availability_zone_client.py b/tempest/services/volume/json/availability_zone_client.py
new file mode 100644
index 0000000..6839d3a
--- /dev/null
+++ b/tempest/services/volume/json/availability_zone_client.py
@@ -0,0 +1,34 @@
+# Copyright 2014 NEC 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 json
+
+from tempest.common import rest_client
+from tempest import config
+
+CONF = config.CONF
+
+
+class VolumeAvailabilityZoneClientJSON(rest_client.RestClient):
+
+    def __init__(self, auth_provider):
+        super(VolumeAvailabilityZoneClientJSON, self).__init__(
+            auth_provider)
+        self.service = CONF.volume.catalog_type
+
+    def get_availability_zone_list(self):
+        resp, body = self.get('os-availability-zone')
+        body = json.loads(body)
+        return resp, body['availabilityZoneInfo']
diff --git a/tempest/services/volume/xml/admin/volume_quotas_client.py b/tempest/services/volume/xml/admin/volume_quotas_client.py
index 710fb3a..a38410b 100644
--- a/tempest/services/volume/xml/admin/volume_quotas_client.py
+++ b/tempest/services/volume/xml/admin/volume_quotas_client.py
@@ -14,7 +14,7 @@
 #    License for the specific language governing permissions and limitations
 #    under the License.
 
-from ast import literal_eval
+import ast
 from lxml import etree
 
 from tempest.common import xml_utils as xml
@@ -35,7 +35,7 @@
         quota = {}
         for k, v in q.items():
             try:
-                v = literal_eval(v)
+                v = ast.literal_eval(v)
             except (ValueError, SyntaxError):
                 pass
 
@@ -68,3 +68,7 @@
                               str(xml.Document(element)))
         body = xml.xml_to_json(etree.fromstring(body))
         return resp, self._format_quota(body)
+
+    def delete_quota_set(self, tenant_id):
+        """Delete the tenant's quota set."""
+        return self.delete('os-quota-sets/%s' % tenant_id)
diff --git a/tempest/services/volume/xml/availability_zone_client.py b/tempest/services/volume/xml/availability_zone_client.py
new file mode 100644
index 0000000..e4a004a
--- /dev/null
+++ b/tempest/services/volume/xml/availability_zone_client.py
@@ -0,0 +1,39 @@
+# Copyright 2014 NEC 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 lxml import etree
+
+from tempest.common import rest_client
+from tempest.common import xml_utils
+from tempest import config
+
+CONF = config.CONF
+
+
+class VolumeAvailabilityZoneClientXML(rest_client.RestClient):
+    TYPE = "xml"
+
+    def __init__(self, auth_provider):
+        super(VolumeAvailabilityZoneClientXML, self).__init__(
+            auth_provider)
+        self.service = CONF.volume.catalog_type
+
+    def _parse_array(self, node):
+        return [xml_utils.xml_to_json(x) for x in node]
+
+    def get_availability_zone_list(self):
+        resp, body = self.get('os-availability-zone')
+        availability_zone = self._parse_array(etree.fromstring(body))
+        return resp, availability_zone
diff --git a/tempest/services/volume/xml/volumes_client.py b/tempest/services/volume/xml/volumes_client.py
index 65bc321..9799e55 100644
--- a/tempest/services/volume/xml/volumes_client.py
+++ b/tempest/services/volume/xml/volumes_client.py
@@ -26,6 +26,11 @@
 
 CONF = config.CONF
 
+VOLUME_NS_BASE = 'http://docs.openstack.org/volume/ext/'
+VOLUME_HOST_NS = VOLUME_NS_BASE + 'volume_host_attribute/api/v1'
+VOLUME_MIG_STATUS_NS = VOLUME_NS_BASE + 'volume_mig_status_attribute/api/v1'
+VOLUMES_TENANT_NS = VOLUME_NS_BASE + 'volume_tenant_attribute/api/v1'
+
 
 class VolumesClientXML(rest_client.RestClient):
     """
@@ -39,6 +44,23 @@
         self.build_interval = CONF.compute.build_interval
         self.build_timeout = CONF.compute.build_timeout
 
+    def _translate_attributes_to_json(self, volume):
+        volume_host_attr = '{' + VOLUME_HOST_NS + '}host'
+        volume_mig_stat_attr = '{' + VOLUME_MIG_STATUS_NS + '}migstat'
+        volume_mig_name_attr = '{' + VOLUME_MIG_STATUS_NS + '}name_id'
+        volume_tenant_id_attr = '{' + VOLUMES_TENANT_NS + '}tenant_id'
+        if volume_host_attr in volume:
+            volume['os-vol-host-attr:host'] = volume.pop(volume_host_attr)
+        if volume_mig_stat_attr in volume:
+            volume['os-vol-mig-status-attr:migstat'] = volume.pop(
+                volume_mig_stat_attr)
+        if volume_mig_name_attr in volume:
+            volume['os-vol-mig-status-attr:name_id'] = volume.pop(
+                volume_mig_name_attr)
+        if volume_tenant_id_attr in volume:
+            volume['os-vol-tenant-attr:tenant_id'] = volume.pop(
+                volume_tenant_id_attr)
+
     def _parse_volume(self, body):
         vol = dict((attr, body.get(attr)) for attr in body.keys())
 
@@ -52,6 +74,8 @@
                                        child.getchildren())
             else:
                 vol[tag] = common.xml_to_json(child)
+        self._translate_attributes_to_json(vol)
+        self._check_if_bootable(vol)
         return vol
 
     def get_attachment_from_volume(self, volume):
@@ -90,8 +114,6 @@
         volumes = []
         if body is not None:
             volumes += [self._parse_volume(vol) for vol in list(body)]
-        for v in volumes:
-            v = self._check_if_bootable(v)
         return resp, volumes
 
     def list_volumes_with_detail(self, params=None):
@@ -106,8 +128,6 @@
         volumes = []
         if body is not None:
             volumes += [self._parse_volume(vol) for vol in list(body)]
-        for v in volumes:
-            v = self._check_if_bootable(v)
         return resp, volumes
 
     def get_volume(self, volume_id):
@@ -115,7 +135,6 @@
         url = "volumes/%s" % str(volume_id)
         resp, body = self.get(url)
         body = self._parse_volume(etree.fromstring(body))
-        body = self._check_if_bootable(body)
         return resp, body
 
     def create_volume(self, size=None, **kwargs):
diff --git a/tempest/tests/base.py b/tempest/tests/base.py
index 15e4311..f4df3b9 100644
--- a/tempest/tests/base.py
+++ b/tempest/tests/base.py
@@ -12,28 +12,16 @@
 #    License for the specific language governing permissions and limitations
 #    under the License.
 
-import os
-
-import fixtures
 import mock
-import testtools
 
-from tempest.openstack.common.fixture import moxstubout
+from oslotest import base
+from oslotest import moxstubout
 
 
-class TestCase(testtools.TestCase):
+class TestCase(base.BaseTestCase):
 
     def setUp(self):
         super(TestCase, self).setUp()
-        if (os.environ.get('OS_STDOUT_CAPTURE') == 'True' or
-                os.environ.get('OS_STDOUT_CAPTURE') == '1'):
-            stdout = self.useFixture(fixtures.StringStream('stdout')).stream
-            self.useFixture(fixtures.MonkeyPatch('sys.stdout', stdout))
-        if (os.environ.get('OS_STDERR_CAPTURE') == 'True' or
-                os.environ.get('OS_STDERR_CAPTURE') == '1'):
-            stderr = self.useFixture(fixtures.StringStream('stderr')).stream
-            self.useFixture(fixtures.MonkeyPatch('sys.stderr', stderr))
-
         mox_fixture = self.useFixture(moxstubout.MoxStubout())
         self.mox = mox_fixture.mox
         self.stubs = mox_fixture.stubs
diff --git a/tempest/tests/common/utils/test_file_utils.py b/tempest/tests/common/utils/test_file_utils.py
index 99ae033..605e82a 100644
--- a/tempest/tests/common/utils/test_file_utils.py
+++ b/tempest/tests/common/utils/test_file_utils.py
@@ -14,7 +14,6 @@
 #    under the License.
 
 import mock
-from mock import patch
 
 from tempest.common.utils import file_utils
 from tempest.tests import base
@@ -23,7 +22,7 @@
 class TestFileUtils(base.TestCase):
 
     def test_have_effective_read_path(self):
-        with patch('__builtin__.open', mock.mock_open(), create=True):
+        with mock.patch('__builtin__.open', mock.mock_open(), create=True):
             result = file_utils.have_effective_read_access('fake_path')
         self.assertTrue(result)
 
diff --git a/tempest/tests/test_auth.py b/tempest/tests/test_auth.py
index 03333be..1dcddad 100644
--- a/tempest/tests/test_auth.py
+++ b/tempest/tests/test_auth.py
@@ -16,11 +16,12 @@
 import copy
 import datetime
 
+from oslotest import mockpatch
+
 from tempest import auth
 from tempest.common import http
 from tempest import config
 from tempest import exceptions
-from tempest.openstack.common.fixture import mockpatch
 from tempest.tests import base
 from tempest.tests import fake_auth_provider
 from tempest.tests import fake_config
diff --git a/tempest/tests/test_decorators.py b/tempest/tests/test_decorators.py
index 804204a..6b678f7 100644
--- a/tempest/tests/test_decorators.py
+++ b/tempest/tests/test_decorators.py
@@ -14,13 +14,12 @@
 
 
 import mock
-import testtools
-
 from oslo.config import cfg
+from oslotest import mockpatch
+import testtools
 
 from tempest import config
 from tempest import exceptions
-from tempest.openstack.common.fixture import mockpatch
 from tempest import test
 from tempest.tests import base
 from tempest.tests import fake_config
diff --git a/tempest/tests/test_rest_client.py b/tempest/tests/test_rest_client.py
index 64ad3bc..d20520c 100644
--- a/tempest/tests/test_rest_client.py
+++ b/tempest/tests/test_rest_client.py
@@ -15,11 +15,12 @@
 import httplib2
 import json
 
+from oslotest import mockpatch
+
 from tempest.common import rest_client
 from tempest.common import xml_utils as xml
 from tempest import config
 from tempest import exceptions
-from tempest.openstack.common.fixture import mockpatch
 from tempest.tests import base
 from tempest.tests import fake_auth_provider
 from tempest.tests import fake_config
diff --git a/tempest/tests/test_ssh.py b/tempest/tests/test_ssh.py
index a6eedc4..0da52dc 100644
--- a/tempest/tests/test_ssh.py
+++ b/tempest/tests/test_ssh.py
@@ -14,6 +14,7 @@
 
 import contextlib
 import socket
+import time
 
 import mock
 import testtools
@@ -43,25 +44,21 @@
             rsa_mock.assert_not_called()
             cs_mock.assert_not_called()
 
-    def test_get_ssh_connection(self):
-        c_mock = self.patch('paramiko.SSHClient')
-        aa_mock = self.patch('paramiko.AutoAddPolicy')
-        s_mock = self.patch('time.sleep')
-        t_mock = self.patch('time.time')
+    def _set_ssh_connection_mocks(self):
+        client_mock = mock.MagicMock()
+        client_mock.connect.return_value = True
+        return (self.patch('paramiko.SSHClient'),
+                self.patch('paramiko.AutoAddPolicy'),
+                client_mock)
 
+    def test_get_ssh_connection(self):
+        c_mock, aa_mock, client_mock = self._set_ssh_connection_mocks()
+        s_mock = self.patch('time.sleep')
+
+        c_mock.return_value = client_mock
         aa_mock.return_value = mock.sentinel.aa
 
-        def reset_mocks():
-            aa_mock.reset_mock()
-            c_mock.reset_mock()
-            s_mock.reset_mock()
-            t_mock.reset_mock()
-
         # Test normal case for successful connection on first try
-        client_mock = mock.MagicMock()
-        c_mock.return_value = client_mock
-        client_mock.connect.return_value = True
-
         client = ssh.Client('localhost', 'root', timeout=2)
         client._get_ssh_connection(sleep=1)
 
@@ -79,50 +76,40 @@
         )]
         self.assertEqual(expected_connect, client_mock.connect.mock_calls)
         s_mock.assert_not_called()
-        t_mock.assert_called_once_with()
 
-        reset_mocks()
+    def test_get_ssh_connection_two_attemps(self):
+        c_mock, aa_mock, client_mock = self._set_ssh_connection_mocks()
 
-        # Test case when connection fails on first two tries and
-        # succeeds on third try (this validates retry logic)
-        client_mock.connect.side_effect = [socket.error, socket.error, True]
-        t_mock.side_effect = [
-            1000,  # Start time
-            1000,  # LOG.warning() calls time.time() loop 1
-            1001,  # Sleep loop 1
-            1001,  # LOG.warning() calls time.time() loop 2
-            1002   # Sleep loop 2
+        c_mock.return_value = client_mock
+        client_mock.connect.side_effect = [
+            socket.error,
+            mock.MagicMock()
         ]
 
+        client = ssh.Client('localhost', 'root', timeout=1)
+        start_time = int(time.time())
         client._get_ssh_connection(sleep=1)
+        end_time = int(time.time())
+        self.assertTrue((end_time - start_time) < 3)
+        self.assertTrue((end_time - start_time) > 1)
 
-        expected_sleeps = [
-            mock.call(2),
-            mock.call(3)
-        ]
-        self.assertEqual(expected_sleeps, s_mock.mock_calls)
+    def test_get_ssh_connection_timeout(self):
+        c_mock, aa_mock, client_mock = self._set_ssh_connection_mocks()
 
-        reset_mocks()
-
-        # Test case when connection fails on first three tries and
-        # exceeds the timeout, so expect to raise a Timeout exception
+        c_mock.return_value = client_mock
         client_mock.connect.side_effect = [
             socket.error,
             socket.error,
-            socket.error
-        ]
-        t_mock.side_effect = [
-            1000,  # Start time
-            1000,  # LOG.warning() calls time.time() loop 1
-            1001,  # Sleep loop 1
-            1001,  # LOG.warning() calls time.time() loop 2
-            1002,  # Sleep loop 2
-            1003,  # Sleep loop 3
-            1004  # LOG.error() calls time.time()
+            socket.error,
         ]
 
+        client = ssh.Client('localhost', 'root', timeout=2)
+        start_time = int(time.time())
         with testtools.ExpectedException(exceptions.SSHTimeout):
             client._get_ssh_connection()
+        end_time = int(time.time())
+        self.assertTrue((end_time - start_time) < 4)
+        self.assertTrue((end_time - start_time) >= 2)
 
     def test_exec_command(self):
         gsc_mock = self.patch('tempest.common.ssh.Client._get_ssh_connection')
diff --git a/tempest/tests/test_tenant_isolation.py b/tempest/tests/test_tenant_isolation.py
index 9292dcb..7a9b6be 100644
--- a/tempest/tests/test_tenant_isolation.py
+++ b/tempest/tests/test_tenant_isolation.py
@@ -13,7 +13,7 @@
 #    under the License.
 
 import keystoneclient.v2_0.client as keystoneclient
-from mock import patch
+import mock
 import neutronclient.v2_0.client as neutronclient
 from oslo.config import cfg
 
@@ -114,7 +114,7 @@
                           {'router': {'id': id, 'name': name}})))
         return router_fix
 
-    @patch('tempest.common.rest_client.RestClient')
+    @mock.patch('tempest.common.rest_client.RestClient')
     def test_primary_creds(self, MockRestClient):
         cfg.CONF.set_default('neutron', False, 'service_available')
         iso_creds = isolated_creds.IsolatedCreds('test class',
@@ -128,7 +128,7 @@
         self.assertEqual(primary_creds.tenant_id, '1234')
         self.assertEqual(primary_creds.user_id, '1234')
 
-    @patch('tempest.common.rest_client.RestClient')
+    @mock.patch('tempest.common.rest_client.RestClient')
     def test_admin_creds(self, MockRestClient):
         cfg.CONF.set_default('neutron', False, 'service_available')
         iso_creds = isolated_creds.IsolatedCreds('test class',
@@ -141,12 +141,12 @@
             return_value=({'status': 200},
                           [{'id': '1234', 'name': 'admin'}])))
 
-        user_mock = patch.object(json_iden_client.IdentityClientJSON,
-                                 'assign_user_role')
+        user_mock = mock.patch.object(json_iden_client.IdentityClientJSON,
+                                      'assign_user_role')
         user_mock.start()
         self.addCleanup(user_mock.stop)
-        with patch.object(json_iden_client.IdentityClientJSON,
-                          'assign_user_role') as user_mock:
+        with mock.patch.object(json_iden_client.IdentityClientJSON,
+                               'assign_user_role') as user_mock:
             admin_creds = iso_creds.get_admin_creds()
         user_mock.assert_called_once_with('1234', '1234', '1234')
         self.assertEqual(admin_creds.username, 'fake_admin_user')
@@ -155,7 +155,7 @@
         self.assertEqual(admin_creds.tenant_id, '1234')
         self.assertEqual(admin_creds.user_id, '1234')
 
-    @patch('tempest.common.rest_client.RestClient')
+    @mock.patch('tempest.common.rest_client.RestClient')
     def test_all_cred_cleanup(self, MockRestClient):
         cfg.CONF.set_default('neutron', False, 'service_available')
         iso_creds = isolated_creds.IsolatedCreds('test class',
@@ -177,8 +177,8 @@
             'list_roles',
             return_value=({'status': 200},
                           [{'id': '123456', 'name': 'admin'}])))
-        with patch.object(json_iden_client.IdentityClientJSON,
-                          'assign_user_role'):
+        with mock.patch.object(json_iden_client.IdentityClientJSON,
+                               'assign_user_role'):
             iso_creds.get_admin_creds()
         user_mock = self.patch(
             'tempest.services.identity.json.identity_client.'
@@ -202,7 +202,7 @@
         self.assertIn('12345', args)
         self.assertIn('123456', args)
 
-    @patch('tempest.common.rest_client.RestClient')
+    @mock.patch('tempest.common.rest_client.RestClient')
     def test_alt_creds(self, MockRestClient):
         cfg.CONF.set_default('neutron', False, 'service_available')
         iso_creds = isolated_creds.IsolatedCreds('test class',
@@ -216,7 +216,7 @@
         self.assertEqual(alt_creds.tenant_id, '1234')
         self.assertEqual(alt_creds.user_id, '1234')
 
-    @patch('tempest.common.rest_client.RestClient')
+    @mock.patch('tempest.common.rest_client.RestClient')
     def test_network_creation(self, MockRestClient):
         iso_creds = isolated_creds.IsolatedCreds('test class',
                                                  password='fake_password')
@@ -240,7 +240,7 @@
         self.assertEqual(router['id'], '1234')
         self.assertEqual(router['name'], 'fake_router')
 
-    @patch('tempest.common.rest_client.RestClient')
+    @mock.patch('tempest.common.rest_client.RestClient')
     def test_network_cleanup(self, MockRestClient):
         iso_creds = isolated_creds.IsolatedCreds('test class',
                                                  password='fake_password')
@@ -289,28 +289,28 @@
             'list_roles',
             return_value=({'status': 200},
                           [{'id': '123456', 'name': 'admin'}])))
-        with patch.object(json_iden_client.IdentityClientJSON,
-                          'assign_user_role'):
+        with mock.patch.object(json_iden_client.IdentityClientJSON,
+                               'assign_user_role'):
             iso_creds.get_admin_creds()
         self.patch('tempest.services.identity.json.identity_client.'
                    'IdentityClientJSON.delete_user')
         self.patch('tempest.services.identity.json.identity_client.'
                    'IdentityClientJSON.delete_tenant')
-        net = patch.object(iso_creds.network_admin_client,
-                           'delete_network')
+        net = mock.patch.object(iso_creds.network_admin_client,
+                                'delete_network')
         net_mock = net.start()
-        subnet = patch.object(iso_creds.network_admin_client,
-                              'delete_subnet')
+        subnet = mock.patch.object(iso_creds.network_admin_client,
+                                   'delete_subnet')
         subnet_mock = subnet.start()
-        router = patch.object(iso_creds.network_admin_client,
-                              'delete_router')
+        router = mock.patch.object(iso_creds.network_admin_client,
+                                   'delete_router')
         router_mock = router.start()
         remove_router_interface_mock = self.patch(
             'tempest.services.network.json.network_client.NetworkClientJSON.'
             'remove_router_interface_with_subnet_id')
-        port_list_mock = patch.object(iso_creds.network_admin_client,
-                                      'list_ports', return_value=(
-                                      {'status': 200}, {'ports': []}))
+        port_list_mock = mock.patch.object(iso_creds.network_admin_client,
+                                           'list_ports', return_value=(
+                                           {'status': 200}, {'ports': []}))
         port_list_mock.start()
         iso_creds.clear_isolated_creds()
         # Verify remove router interface calls
@@ -342,7 +342,7 @@
         self.assertIn('12345', args)
         self.assertIn('123456', args)
 
-    @patch('tempest.common.rest_client.RestClient')
+    @mock.patch('tempest.common.rest_client.RestClient')
     def test_network_alt_creation(self, MockRestClient):
         iso_creds = isolated_creds.IsolatedCreds('test class',
                                                  password='fake_password')
@@ -366,7 +366,7 @@
         self.assertEqual(router['id'], '1234')
         self.assertEqual(router['name'], 'fake_alt_router')
 
-    @patch('tempest.common.rest_client.RestClient')
+    @mock.patch('tempest.common.rest_client.RestClient')
     def test_network_admin_creation(self, MockRestClient):
         iso_creds = isolated_creds.IsolatedCreds('test class',
                                                  password='fake_password')
@@ -383,8 +383,8 @@
             'list_roles',
             return_value=({'status': 200},
                           [{'id': '123456', 'name': 'admin'}])))
-        with patch.object(json_iden_client.IdentityClientJSON,
-                          'assign_user_role'):
+        with mock.patch.object(json_iden_client.IdentityClientJSON,
+                               'assign_user_role'):
             iso_creds.get_admin_creds()
         router_interface_mock.called_once_with('1234', '1234')
         network = iso_creds.get_admin_network()
@@ -397,7 +397,7 @@
         self.assertEqual(router['id'], '1234')
         self.assertEqual(router['name'], 'fake_admin_router')
 
-    @patch('tempest.common.rest_client.RestClient')
+    @mock.patch('tempest.common.rest_client.RestClient')
     def test_no_network_resources(self, MockRestClient):
         net_dict = {
             'network': False,
@@ -410,14 +410,14 @@
                                                  network_resources=net_dict)
         self._mock_user_create('1234', 'fake_prim_user')
         self._mock_tenant_create('1234', 'fake_prim_tenant')
-        net = patch.object(iso_creds.network_admin_client,
-                           'delete_network')
+        net = mock.patch.object(iso_creds.network_admin_client,
+                                'delete_network')
         net_mock = net.start()
-        subnet = patch.object(iso_creds.network_admin_client,
-                              'delete_subnet')
+        subnet = mock.patch.object(iso_creds.network_admin_client,
+                                   'delete_subnet')
         subnet_mock = subnet.start()
-        router = patch.object(iso_creds.network_admin_client,
-                              'delete_router')
+        router = mock.patch.object(iso_creds.network_admin_client,
+                                   'delete_router')
         router_mock = router.start()
 
         iso_creds.get_primary_creds()
@@ -431,7 +431,7 @@
         self.assertIsNone(subnet)
         self.assertIsNone(router)
 
-    @patch('tempest.common.rest_client.RestClient')
+    @mock.patch('tempest.common.rest_client.RestClient')
     def test_router_without_network(self, MockRestClient):
         net_dict = {
             'network': False,
@@ -447,7 +447,7 @@
         self.assertRaises(exceptions.InvalidConfiguration,
                           iso_creds.get_primary_creds)
 
-    @patch('tempest.common.rest_client.RestClient')
+    @mock.patch('tempest.common.rest_client.RestClient')
     def test_subnet_without_network(self, MockRestClient):
         net_dict = {
             'network': False,
@@ -463,7 +463,7 @@
         self.assertRaises(exceptions.InvalidConfiguration,
                           iso_creds.get_primary_creds)
 
-    @patch('tempest.common.rest_client.RestClient')
+    @mock.patch('tempest.common.rest_client.RestClient')
     def test_dhcp_without_subnet(self, MockRestClient):
         net_dict = {
             'network': False,
diff --git a/tempest/thirdparty/boto/test_ec2_instance_run.py b/tempest/thirdparty/boto/test_ec2_instance_run.py
index 33b8d6e..b2eb18d 100644
--- a/tempest/thirdparty/boto/test_ec2_instance_run.py
+++ b/tempest/thirdparty/boto/test_ec2_instance_run.py
@@ -193,7 +193,6 @@
             instance.terminate()
         self.cancelResourceCleanUp(rcuk)
 
-    @test.skip_because(bug="1098891")
     @test.attr(type='smoke')
     def test_run_terminate_instance(self):
         # EC2 run, terminate immediately
@@ -211,7 +210,7 @@
             pass
         except exception.EC2ResponseError as exc:
             if self.ec2_error_code.\
-                client.InvalidInstanceID.NotFound.match(exc):
+                client.InvalidInstanceID.NotFound.match(exc) is None:
                 pass
             else:
                 raise
diff --git a/test-requirements.txt b/test-requirements.txt
index 8d64167..b9c75c8 100644
--- a/test-requirements.txt
+++ b/test-requirements.txt
@@ -1,9 +1,10 @@
 hacking>=0.8.0,<0.9
 # needed for doc build
 docutils==0.9.1
-sphinx>=1.1.2,<1.2
+sphinx>=1.2.1,<1.3
 python-subunit>=0.0.18
 oslosphinx
 mox>=0.5.3
 mock>=1.0
 coverage>=3.6
+oslotest
diff --git a/tox.ini b/tox.ini
index 5e8d283..2110362 100644
--- a/tox.ini
+++ b/tox.ini
@@ -95,9 +95,10 @@
 
 [hacking]
 local-check-factory = tempest.hacking.checks.factory
+import_exceptions = tempest.services
 
 [flake8]
 # E125 is a won't fix until https://github.com/jcrocholl/pep8/issues/126 is resolved.  For further detail see https://review.openstack.org/#/c/36788/
-ignore = E125,H302,H404
+ignore = E125,H404
 show-source = True
 exclude = .git,.venv,.tox,dist,doc,openstack,*egg