Merge "simplify heat test_limits"
diff --git a/tempest/api/compute/admin/test_flavors.py b/tempest/api/compute/admin/test_flavors.py
index 05b763a..759585e 100644
--- a/tempest/api/compute/admin/test_flavors.py
+++ b/tempest/api/compute/admin/test_flavors.py
@@ -170,10 +170,12 @@
                 flag = True
         self.assertTrue(flag)
 
+    @test.skip_because(bug='1286297')
     @test.attr(type='gate')
     def test_list_non_public_flavor(self):
-        # Create a flavor with os-flavor-access:is_public false should
-        # be present in list_details.
+        # Create a flavor with os-flavor-access:is_public false.
+        # The flavor should not be present in list_details as the
+        # tenant is not automatically added access list.
         # This operation requires the user to have 'admin' role
         flavor_name = data_utils.rand_name(self.flavor_name_prefix)
         new_flavor_id = data_utils.rand_int_id(start=1000)
@@ -192,7 +194,7 @@
         for flavor in flavors:
             if flavor['name'] == flavor_name:
                 flag = True
-        self.assertTrue(flag)
+        self.assertFalse(flag)
 
         # Verify flavor is not retrieved with other user
         flag = False
diff --git a/tempest/api/compute/admin/test_flavors_access.py b/tempest/api/compute/admin/test_flavors_access.py
index 4804ce4..aa0138f 100644
--- a/tempest/api/compute/admin/test_flavors_access.py
+++ b/tempest/api/compute/admin/test_flavors_access.py
@@ -46,9 +46,11 @@
         cls.vcpus = 1
         cls.disk = 10
 
+    @test.skip_because(bug='1286297')
     @test.attr(type='gate')
     def test_flavor_access_list_with_private_flavor(self):
-        # Test to list flavor access successfully by querying private flavor
+        # Test to make sure that list flavor access on a newly created
+        # private flavor will return an empty access list
         flavor_name = data_utils.rand_name(self.flavor_name_prefix)
         new_flavor_id = data_utils.rand_int_id(start=1000)
         resp, new_flavor = self.client.create_flavor(flavor_name,
@@ -60,10 +62,7 @@
         self.assertEqual(resp.status, 200)
         resp, flavor_access = self.client.list_flavor_access(new_flavor_id)
         self.assertEqual(resp.status, 200)
-        self.assertEqual(len(flavor_access), 1, str(flavor_access))
-        first_flavor = flavor_access[0]
-        self.assertEqual(str(new_flavor_id), str(first_flavor['flavor_id']))
-        self.assertEqual(self.adm_tenant_id, first_flavor['tenant_id'])
+        self.assertEqual(len(flavor_access), 0, str(flavor_access))
 
     @test.attr(type='gate')
     def test_flavor_access_add_remove(self):
diff --git a/tempest/api_schema/compute/v2/security_groups.py b/tempest/api_schema/compute/v2/security_groups.py
new file mode 100644
index 0000000..68b65b4
--- /dev/null
+++ b/tempest/api_schema/compute/v2/security_groups.py
@@ -0,0 +1,38 @@
+# 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.
+
+list_security_groups = {
+    'status_code': [200],
+    'response_body': {
+        'type': 'object',
+        'properties': {
+            'security_groups': {
+                'type': 'array',
+                'items': {
+                    'type': 'object',
+                    'properties': {
+                        'id': {'type': ['integer', 'string']},
+                        'name': {'type': 'string'},
+                        'tenant_id': {'type': 'string'},
+                        'rules': {'type': 'array'},
+                        'description': {'type': 'string'},
+                    },
+                    'required': ['id', 'name', 'tenant_id', 'rules',
+                                 'description'],
+                }
+            }
+        },
+        'required': ['security_groups']
+    }
+}
diff --git a/tempest/cli/output_parser.py b/tempest/cli/output_parser.py
index 4edcd47..80234a3 100644
--- a/tempest/cli/output_parser.py
+++ b/tempest/cli/output_parser.py
@@ -17,6 +17,7 @@
 
 import re
 
+from tempest import exceptions
 from tempest.openstack.common import log as logging
 
 
@@ -37,7 +38,7 @@
     for table_ in tables_:
         if 'Property' not in table_['headers'] \
            or 'Value' not in table_['headers']:
-            raise Exception('Invalid structure of table with details')
+            raise exceptions.InvalidStructure()
         item = {}
         for value in table_['values']:
             item[value[0]] = value[1]
diff --git a/tempest/exceptions/__init__.py b/tempest/exceptions/__init__.py
index 485f532..d313def 100644
--- a/tempest/exceptions/__init__.py
+++ b/tempest/exceptions/__init__.py
@@ -158,3 +158,7 @@
 
 class UnexpectedResponseCode(base.RestClientException):
     message = "Unexpected response code received"
+
+
+class InvalidStructure(base.TempestException):
+    message = "Invalid structure of table with details"
diff --git a/tempest/services/compute/json/security_groups_client.py b/tempest/services/compute/json/security_groups_client.py
index 899d4ef..9267be7 100644
--- a/tempest/services/compute/json/security_groups_client.py
+++ b/tempest/services/compute/json/security_groups_client.py
@@ -16,6 +16,7 @@
 import json
 import urllib
 
+from tempest.api_schema.compute.v2 import security_groups as schema
 from tempest.common import rest_client
 from tempest import config
 from tempest import exceptions
@@ -38,6 +39,7 @@
 
         resp, body = self.get(url)
         body = json.loads(body)
+        self.validate_response(schema.list_security_groups, resp, body)
         return resp, body['security_groups']
 
     def get_security_group(self, security_group_id):
@@ -119,6 +121,7 @@
         """List all rules for a security group."""
         resp, body = self.get('os-security-groups')
         body = json.loads(body)
+        self.validate_response(schema.list_security_groups, resp, body)
         for sg in body['security_groups']:
             if sg['id'] == security_group_id:
                 return resp, sg['rules']