Pushing all codes for initial commit
diff --git a/tungsten_tempest_plugin/README.rst b/tungsten_tempest_plugin/README.rst
new file mode 100644
index 0000000..b1bbe8c
--- /dev/null
+++ b/tungsten_tempest_plugin/README.rst
@@ -0,0 +1,6 @@
+===============================================
+Tempest Integration of tungsten-tempest
+===============================================
+
+This directory contains Tempest tests to cover the tungsten-tempest project.
+
diff --git a/tungsten_tempest_plugin/__init__.py b/tungsten_tempest_plugin/__init__.py
new file mode 100644
index 0000000..7a957f3
--- /dev/null
+++ b/tungsten_tempest_plugin/__init__.py
@@ -0,0 +1 @@
+name = "tungsten_tempest"
diff --git a/tungsten_tempest_plugin/config.py b/tungsten_tempest_plugin/config.py
new file mode 100644
index 0000000..b82299e
--- /dev/null
+++ b/tungsten_tempest_plugin/config.py
@@ -0,0 +1,73 @@
+# Copyright 2016 AT&T Corp
+# All Rights Reserved.
+#
+# Licensed under the Apache License, Version 2.0 (the "License"); you may
+# not use this file except in compliance with the License. You may obtain
+# a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
+# License for the specific language governing permissions and limitations
+# under the License.
+from oslo_config import cfg
+
+service_available_group = cfg.OptGroup(name="service_available",
+ title="Available OpenStack Services")
+
+ServiceAvailableGroup = [
+ cfg.BoolOpt("contrail",
+ default=True,
+ help="Whether or not contrail is expected to be available."),
+]
+
+sdn_group = cfg.OptGroup(name='sdn',
+ title='SDN service options')
+
+SDNGroup = [
+ cfg.StrOpt('endpoint_type',
+ default='publicURL',
+ choices=['public', 'admin', 'internal',
+ 'publicURL', 'adminURL', 'internalURL'],
+ help="The endpoint type to use for the SDN service"),
+ cfg.StrOpt('catalog_type',
+ default='sdn-l-config',
+ help="Catalog type of the SDN service"),
+]
+
+tungsten_log_group = cfg.OptGroup(
+ name='tungsten_log', title='tungsten Tempest Logging Options')
+
+TungstenLogGroup = [
+ cfg.BoolOpt('enable_reporting',
+ default=False,
+ help="Enables reporting on RBAC expected and actual test "
+ "results for each tungstenTempest test"),
+ cfg.StrOpt('report_log_name',
+ default='tungsten.log',
+ help="Name of file where output from 'enable_reporting' is "
+ "logged. Note that this file is recreated on each "
+ "invocation of tungsten_tempest"),
+ cfg.StrOpt('report_log_path',
+ default='.',
+ help="Path (relative or absolute) where the output from "
+ "'enable_reporting' is logged. This is combined with"
+ "report_log_name to generate the full path."),
+]
+
+
+def list_opts():
+ """Return a list of oslo.config options available.
+
+ The purpose of this is to allow tools like the Oslo sample config file
+ generator to discover the options exposed to users.
+ """
+ opt_list = [
+ (service_available_group, ServiceAvailableGroup),
+ (sdn_group, SDNGroup),
+ (tungsten_log_group, TungstenLogGroup)
+
+ ]
+ return opt_list
diff --git a/tungsten_tempest_plugin/plugin.py b/tungsten_tempest_plugin/plugin.py
new file mode 100644
index 0000000..70e020d
--- /dev/null
+++ b/tungsten_tempest_plugin/plugin.py
@@ -0,0 +1,81 @@
+# Copyright 2017 AT&T Corporation.
+# All Rights Reserved.
+#
+# Licensed under the Apache License, Version 2.0 (the "License"); you may
+# not use this file except in compliance with the License. You may obtain
+# a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
+# License for the specific language governing permissions and limitations
+# under the License.
+
+import logging
+import os
+
+from oslo_concurrency import lockutils
+
+from tempest import config
+from tempest.test_discover import plugins
+
+from tungsten_tempest_plugin import config as project_config
+
+RBACLOG = logging.getLogger('rbac_reporting')
+
+
+class TungstenTempestPlugin(plugins.TempestPlugin):
+
+ def load_tests(self):
+ base_path = os.path.split(os.path.dirname(
+ os.path.abspath(__file__)))[0]
+ test_dir = "tungsten_tempest_plugin/tests/api"
+ full_test_dir = os.path.join(base_path, test_dir)
+ return full_test_dir, base_path
+
+ @lockutils.synchronized('_reset_log_file')
+ def _reset_log_file(self, logfile):
+ try:
+ os.remove(logfile)
+ except OSError:
+ pass
+
+ def _configure_per_test_logging(self, conf):
+ # Separate log handler for rbac reporting
+ RBACLOG.setLevel(level=logging.INFO)
+ # Set up proper directory handling
+ report_abs_path = os.path.abspath(conf.tungsten_log.report_log_path)
+ report_path = os.path.join(
+ report_abs_path, conf.tungsten_log.report_log_name)
+
+ # Remove the log file if it exists
+ self._reset_log_file(report_path)
+ # Delay=True so that we don't end up creating an empty file if we
+ # never log to it.
+ rbac_report_handler = logging.FileHandler(
+ filename=report_path, delay=True, mode='a')
+ rbac_report_handler.setFormatter(
+ fmt=logging.Formatter(fmt='%(message)s'))
+ RBACLOG.addHandler(rbac_report_handler)
+
+ def register_opts(self, conf):
+ config.register_opt_group(conf, project_config.service_available_group,
+ project_config.ServiceAvailableGroup)
+ config.register_opt_group(conf, project_config.sdn_group,
+ project_config.SDNGroup)
+ config.register_opt_group(conf, project_config.tungsten_log_group,
+ project_config.TungstenLogGroup)
+
+ if conf.tungsten_log.enable_reporting:
+ self._configure_per_test_logging(conf)
+
+ def get_opt_lists(self):
+ return [
+ (project_config.service_available_group.name,
+ project_config.ServiceAvailableGroup),
+ (project_config.sdn_group.name, project_config.SDNGroup),
+ (project_config.tungsten_log_group.name,
+ project_config.TungstenLogGroup),
+ ]
diff --git a/tungsten_tempest_plugin/services/__init__.py b/tungsten_tempest_plugin/services/__init__.py
new file mode 100644
index 0000000..e69de29
--- /dev/null
+++ b/tungsten_tempest_plugin/services/__init__.py
diff --git a/tungsten_tempest_plugin/services/contrail/__init__.py b/tungsten_tempest_plugin/services/contrail/__init__.py
new file mode 100644
index 0000000..e69de29
--- /dev/null
+++ b/tungsten_tempest_plugin/services/contrail/__init__.py
diff --git a/tungsten_tempest_plugin/services/contrail/json/__init__.py b/tungsten_tempest_plugin/services/contrail/json/__init__.py
new file mode 100644
index 0000000..e69de29
--- /dev/null
+++ b/tungsten_tempest_plugin/services/contrail/json/__init__.py
diff --git a/tungsten_tempest_plugin/services/contrail/json/access_control_client.py b/tungsten_tempest_plugin/services/contrail/json/access_control_client.py
new file mode 100644
index 0000000..7e724b9
--- /dev/null
+++ b/tungsten_tempest_plugin/services/contrail/json/access_control_client.py
@@ -0,0 +1,129 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest service class for access control test cases
+"""
+
+import json
+from six.moves.urllib import parse as urllib
+from tungsten_tempest_plugin.services.contrail.json import base
+
+
+class AccessControlClient(base.BaseContrailClient):
+
+ """
+ Service class for access control test cases
+ """
+
+ def list_access_control_lists(self, params=None):
+ """
+ :param params:
+ :return: list object
+ """
+ url = '/access-control-lists'
+ if params:
+ url += '?%s' % urllib.urlencode(params)
+ return self.get(url)
+
+ def create_access_control_lists(self, **kwargs):
+ """
+ :param kwargs:
+ :return: map object
+ """
+ url = '/access-control-lists'
+ post_body = json.dumps({'access-control-list': kwargs})
+ resp, body = self.post(url, post_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def show_access_control_list(self, list_id):
+ """
+ :param list_id:
+ :return: response object
+ """
+ url = '/access-control-list/%s' % str(list_id)
+ return self.get(url)
+
+ def delete_access_control_list(self, list_id):
+ """
+ :param list_id:
+ :return: response object
+ """
+ url = '/access-control-list/%s' % str(list_id)
+ return self.delete(url)
+
+ def update_access_control_list(self, list_id, **kwargs):
+ """
+ :param list_id:
+ :param kwargs:
+ :return: map object
+ """
+ url = '/access-control-list/%s' % str(list_id)
+ post_data = {'access-control-list': kwargs}
+ req_post_data = json.dumps(post_data)
+ resp, body = self.put(url, req_post_data)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def list_api_access_lists(self, params=None):
+ """
+ :param params:
+ :return: response object
+ """
+ url = '/api-access-lists'
+ if params:
+ url += '?%s' % urllib.urlencode(params)
+ return self.get(url)
+
+ def create_api_access_lists(self, **kwargs):
+ """
+ :param kwargs:
+ :return: map object
+ """
+ url = '/api-access-lists'
+ post_body = json.dumps({'api-access-list': kwargs})
+ resp, body = self.post(url, post_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def show_api_access_list(self, list_id):
+ """
+ :param list_id:
+ :return: response object
+ """
+ url = '/api-access-list/%s' % str(list_id)
+ return self.get(url)
+
+ def delete_api_access_list(self, list_id):
+ """
+ :param list_id:
+ :return: response object
+ """
+ url = '/api-access-list/%s' % str(list_id)
+ return self.delete(url)
+
+ def update_api_access_list(self, list_id, **kwargs):
+ """
+ :param list_id:
+ :param kwargs:
+ :return: map object
+ """
+ url = '/api-access-list/%s' % str(list_id)
+ post_data = {'api-access-list': kwargs}
+ req_post_data = json.dumps(post_data)
+ resp, body = self.put(url, req_post_data)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
diff --git a/tungsten_tempest_plugin/services/contrail/json/alarm_client.py b/tungsten_tempest_plugin/services/contrail/json/alarm_client.py
new file mode 100644
index 0000000..35f59da
--- /dev/null
+++ b/tungsten_tempest_plugin/services/contrail/json/alarm_client.py
@@ -0,0 +1,83 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest service class for alarm client test cases
+"""
+
+import json
+from six.moves.urllib import parse as urllib
+from tungsten_tempest_plugin.services.contrail.json import base
+
+
+class AlarmClient(base.BaseContrailClient):
+
+ """
+ Service class for alarm test cases
+ """
+
+ def list_alarms(self, params=None):
+ """
+ :param params:
+ :return: map object
+ """
+ url = '/alarms'
+ if params:
+ url += '?%s' % urllib.urlencode(params)
+ resp, body = self.get(url)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def create_alarms(self, **kwargs):
+ """
+ :param kwargs:
+ :return: map object
+ """
+ url = '/alarms'
+ resp, body = self.post(url, json.dumps({'alarm': kwargs}))
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def show_alarm(self, uuid, params=None):
+ """
+ :param uuid:
+ :param params:
+ :return: map object
+ """
+ url = '/alarm/{0}'.format(uuid)
+ if params:
+ url += '?%s' % urllib.urlencode(params)
+ resp, body = self.get(url)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def update_alarm(self, uuid, **kwargs):
+ """
+ :param uuid:
+ :param kwargs:
+ :return: map object
+ """
+ url = '/alarm/{0}'.format(uuid)
+ resp, body = self.put(url, json.dumps({'alarm': kwargs}))
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def delete_alarm(self, uuid):
+ """
+ :param uuid:
+ :return: response object
+ """
+ url = '/alarm/{0}'.format(uuid)
+ return self.delete(url)
diff --git a/tungsten_tempest_plugin/services/contrail/json/alias_ip_client.py b/tungsten_tempest_plugin/services/contrail/json/alias_ip_client.py
new file mode 100644
index 0000000..2fc1898
--- /dev/null
+++ b/tungsten_tempest_plugin/services/contrail/json/alias_ip_client.py
@@ -0,0 +1,129 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest service class for alarm ip client test cases
+"""
+
+import json
+from six.moves.urllib import parse as urllib
+from tungsten_tempest_plugin.services.contrail.json import base
+
+
+class AliasIPsClient(base.BaseContrailClient):
+
+ """
+ Service class for alias ip test cases
+ """
+
+ def list_alias_ip_pools(self, params=None):
+ """
+ :param params:
+ :return: response object
+ """
+ url = '/alias-ip-pools'
+ if params:
+ url += '?%s' % urllib.urlencode(params)
+ return self.get(url)
+
+ def create_alias_ip_pools(self, **kwargs):
+ """
+ :param kwargs:
+ :return: map object
+ """
+ url = '/alias-ip-pools'
+ post_body = json.dumps({'alias-ip-pool': kwargs})
+ resp, body = self.post(url, post_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def show_alias_ip_pool(self, pool_id):
+ """
+ :param pool_id:
+ :return: response object
+ """
+ url = '/alias-ip-pool/%s' % str(pool_id)
+ return self.get(url)
+
+ def delete_alias_ip_pool(self, pool_id):
+ """
+ :param pool_id:
+ :return: response object
+ """
+ url = '/alias-ip-pool/%s' % str(pool_id)
+ return self.delete(url)
+
+ def update_alias_ip_pool(self, pool_id, **kwargs):
+ """
+ :param pool_id:
+ :param kwargs:
+ :return: map object
+ """
+ url = '/alias-ip-pool/%s' % str(pool_id)
+ post_data = {'alias-ip-pool': kwargs}
+ req_post_data = json.dumps(post_data)
+ resp, body = self.put(url, req_post_data)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def list_alias_ips(self, params=None):
+ """
+ :param params:
+ :return: response object
+ """
+ url = '/alias-ips'
+ if params:
+ url += '?%s' % urllib.urlencode(params)
+ return self.get(url)
+
+ def create_alias_ips(self, **kwargs):
+ """
+ :param kwargs:
+ :return: map object
+ """
+ url = '/alias-ips'
+ post_body = json.dumps({'alias-ip': kwargs})
+ resp, body = self.post(url, post_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def show_alias_ip(self, ip_id):
+ """
+ :param ip_id:
+ :return: response object
+ """
+ url = '/alias-ip/%s' % str(ip_id)
+ return self.get(url)
+
+ def delete_alias_ip(self, ip_id):
+ """
+ :param ip_id:
+ :return: response object
+ """
+ url = '/alias-ip/%s' % str(ip_id)
+ return self.delete(url)
+
+ def update_alias_ip(self, ip_id, **kwargs):
+ """
+ :param ip_id:
+ :param kwargs:
+ :return: map object
+ """
+ url = '/alias-ip/%s' % str(ip_id)
+ post_data = {'alias-ip': kwargs}
+ req_post_data = json.dumps(post_data)
+ resp, body = self.put(url, req_post_data)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
diff --git a/tungsten_tempest_plugin/services/contrail/json/analytics_node_client.py b/tungsten_tempest_plugin/services/contrail/json/analytics_node_client.py
new file mode 100644
index 0000000..629749f
--- /dev/null
+++ b/tungsten_tempest_plugin/services/contrail/json/analytics_node_client.py
@@ -0,0 +1,78 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest service class for analytics node test cases
+"""
+
+import json
+from six.moves.urllib import parse as urllib
+from tungsten_tempest_plugin.services.contrail.json import base
+
+
+class AnalyticsNodeClient(base.BaseContrailClient):
+
+ """
+ Service class for analytics node test cases
+ """
+
+ def list_analytics_nodes(self, params=None):
+ """
+ :param params:
+ :return: response object
+ """
+ url = '/analytics-nodes'
+ if params:
+ url += '?{0}'.format(urllib.urlencode(params))
+ return self.get(url)
+
+ def show_analytics_node(self, uuid):
+ """
+ :param uuid:
+ :return: response object
+ """
+ url = '/analytics-node/{0}'.format(uuid)
+ return self.get(url)
+
+ def create_analytics_nodes(self, **kwargs):
+ """
+ :param kwargs:
+ :return: map object
+ """
+ url = '/analytics-nodes'
+ post_body = json.dumps({'analytics-node': kwargs})
+ resp, body = self.post(url, post_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def update_analytics_node(self, uuid, **kwargs):
+ """
+ :param uuid:
+ :param kwargs:
+ :return: map object
+ """
+ url = '/analytics-node/{0}'.format(uuid)
+ put_body = json.dumps({'analytics-node': kwargs})
+ resp, body = self.put(url, put_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def delete_analytics_node(self, uuid):
+ """
+ :param uuid:
+ :return: response object
+ """
+ url = '/analytics-node/{0}'.format(uuid)
+ return self.delete(url)
diff --git a/tungsten_tempest_plugin/services/contrail/json/attachments_client.py b/tungsten_tempest_plugin/services/contrail/json/attachments_client.py
new file mode 100644
index 0000000..7ab9aa7
--- /dev/null
+++ b/tungsten_tempest_plugin/services/contrail/json/attachments_client.py
@@ -0,0 +1,129 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest service class for attachment clients test cases
+"""
+
+import json
+from six.moves.urllib import parse as urllib
+from tungsten_tempest_plugin.services.contrail.json import base
+
+
+class AttachmentsClient(base.BaseContrailClient):
+
+ """
+ Service class for attachment client test cases
+ """
+
+ def list_provider_attachments(self, params=None):
+ """
+ :param params:
+ :return: response object
+ """
+ url = '/provider-attachments'
+ if params:
+ url += '?%s' % urllib.urlencode(params)
+ return self.get(url)
+
+ def create_provider_attachments(self, **kwargs):
+ """
+ :param kwargs:
+ :return: map object
+ """
+ url = '/provider-attachments'
+ post_body = json.dumps({'provider-attachment': kwargs})
+ resp, body = self.post(url, post_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def show_provider_attachment(self, appliance_id):
+ """
+ :param appliance_id:
+ :return: response object
+ """
+ url = '/provider-attachment/%s' % str(appliance_id)
+ return self.get(url)
+
+ def delete_provider_attachment(self, appliance_id):
+ """
+ :param appliance_id:
+ :return: response object
+ """
+ url = '/provider-attachment/%s' % str(appliance_id)
+ return self.delete(url)
+
+ def update_provider_attachment(self, appliance_id, **kwargs):
+ """
+ :param appliance_id:
+ :param kwargs:
+ :return: map object
+ """
+ url = '/provider-attachment/%s' % str(appliance_id)
+ post_data = {'provider-attachment': kwargs}
+ req_post_data = json.dumps(post_data)
+ resp, body = self.put(url, req_post_data)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def list_customer_attachments(self, params=None):
+ """
+ :param params:
+ :return: response object
+ """
+ url = '/customer-attachments'
+ if params:
+ url += '?%s' % urllib.urlencode(params)
+ return self.get(url)
+
+ def create_customer_attachments(self, **kwargs):
+ """
+ :param kwargs:
+ :return: map object
+ """
+ url = '/customer-attachments'
+ post_body = json.dumps({'customer-attachment': kwargs})
+ resp, body = self.post(url, post_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def show_customer_attachment(self, appliance_id):
+ """
+ :param appliance_id:
+ :return: response object
+ """
+ url = '/customer-attachment/%s' % str(appliance_id)
+ return self.get(url)
+
+ def delete_customer_attachment(self, appliance_id):
+ """
+ :param appliance_id:
+ :return: response object
+ """
+ url = '/customer-attachment/%s' % str(appliance_id)
+ return self.delete(url)
+
+ def update_customer_attachment(self, appliance_id, **kwargs):
+ """
+ :param appliance_id:
+ :param kwargs:
+ :return: map object
+ """
+ url = '/customer-attachment/%s' % str(appliance_id)
+ post_data = {'customer-attachment': kwargs}
+ req_post_data = json.dumps(post_data)
+ resp, body = self.put(url, req_post_data)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
diff --git a/tungsten_tempest_plugin/services/contrail/json/base.py b/tungsten_tempest_plugin/services/contrail/json/base.py
new file mode 100644
index 0000000..352bffc
--- /dev/null
+++ b/tungsten_tempest_plugin/services/contrail/json/base.py
@@ -0,0 +1,45 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Base service class for all service classes
+"""
+
+from oslo_log import log as logging
+from tempest.lib.common import rest_client
+
+LOG = logging.getLogger(__name__)
+
+
+class BaseContrailClient(rest_client.RestClient):
+ """Base Tempest REST client for Designate API"""
+
+
+class ResponseBody(dict):
+ """Class that wraps an http response and dict body into a single value.
+
+ Callers that receive this object will normally use it as a dict but
+ can extract the response if needed.
+ """
+
+ def __init__(self, response, body=None, **kwargs):
+ super(ResponseBody, self).__init__(**kwargs)
+ body_data = body or {}
+ self.update(body_data)
+ self.response = response
+
+ def __str__(self):
+ body = super(ResponseBody, self).__str__()
+ return "response: %s\nBody: %s" % (self.response, body)
diff --git a/tungsten_tempest_plugin/services/contrail/json/bgp_as_a_service_client.py b/tungsten_tempest_plugin/services/contrail/json/bgp_as_a_service_client.py
new file mode 100644
index 0000000..98c2742
--- /dev/null
+++ b/tungsten_tempest_plugin/services/contrail/json/bgp_as_a_service_client.py
@@ -0,0 +1,79 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest service class for BGP as a service test cases
+"""
+
+import json
+from six.moves.urllib import parse as urllib
+from tungsten_tempest_plugin.services.contrail.json import base
+
+
+class BGPAsAServiceClient(base.BaseContrailClient):
+
+ """
+ Service class for bgp as a service test cases
+ """
+
+ def list_bgp_as_a_services(self, params=None):
+ """
+ :param params:
+ :return: response object
+ """
+ url = '/bgp-as-a-services'
+ if params:
+ url += '?%s' % urllib.urlencode(params)
+ return self.get(url)
+
+ def create_bgp_as_a_services(self, **kwargs):
+ """
+ :param kwargs:
+ :return: map object
+ """
+ url = '/bgp-as-a-services'
+ post_body = json.dumps({'bgp-as-a-service': kwargs})
+ resp, body = self.post(url, post_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def show_bgp_as_a_service(self, bgp_id):
+ """
+ :param bgp_id:
+ :return: response object
+ """
+ url = '/bgp-as-a-service/%s' % str(bgp_id)
+ return self.get(url)
+
+ def delete_bgp_as_a_service(self, bgp_id):
+ """
+ :param bgp_id:
+ :return: response object
+ """
+ url = '/bgp-as-a-service/%s' % str(bgp_id)
+ return self.delete(url)
+
+ def update_bgp_as_a_service(self, bgp_id, **kwargs):
+ """
+ :param bgp_id:
+ :param kwargs:
+ :return: map object
+ """
+ url = '/bgp-as-a-service/%s' % str(bgp_id)
+ post_data = {'bgp-as-a-service': kwargs}
+ req_post_data = json.dumps(post_data)
+ resp, body = self.put(url, req_post_data)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
diff --git a/tungsten_tempest_plugin/services/contrail/json/config_client.py b/tungsten_tempest_plugin/services/contrail/json/config_client.py
new file mode 100644
index 0000000..18212d3
--- /dev/null
+++ b/tungsten_tempest_plugin/services/contrail/json/config_client.py
@@ -0,0 +1,180 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest service class for config test cases
+"""
+
+from oslo_serialization import jsonutils as json
+from six.moves.urllib import parse as urllib
+from tungsten_tempest_plugin.services.contrail.json import base
+
+
+class ConfigClient(base.BaseContrailClient):
+
+ """
+ Service class for config test cases
+ """
+
+ # Below are client codes for global-system-config APIs
+ def list_global_system_configs(self, params=None):
+ """
+ :param params:
+ :return: response object
+ """
+ url = '/global-system-configs'
+ if params:
+ url += '?%s' % urllib.urlencode(params)
+ return self.get(url)
+
+ def create_global_system_configs(self, **kwargs):
+ """
+ :param kwargs:
+ :return: map object
+ """
+ url = '/global-system-configs'
+ post_body = json.dumps({'global-system-config': kwargs})
+ resp, body = self.post(url, post_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def show_global_system_config(self, template_id):
+ """
+ :param template_id:
+ :return: response object
+ """
+ url = '/global-system-config/%s' % str(template_id)
+ return self.get(url)
+
+ def delete_global_system_config(self, template_id):
+ """
+ :param template_id:
+ :return: response object
+ """
+ url = '/global-system-config/%s' % str(template_id)
+ return self.delete(url)
+
+ def update_global_system_config(self, template_id, **kwargs):
+ """
+ :param template_id:
+ :param kwargs:
+ :return: map object
+ """
+ url = '/global-system-config/%s' % str(template_id)
+ put_data = {'global-system-config': kwargs}
+ req_put_data = json.dumps(put_data)
+ resp, body = self.put(url, req_put_data)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ # Below are client codes for config-node APIs
+ def list_config_nodes(self):
+ """
+ :return: map object
+ """
+ url = '/config-nodes'
+ resp, body = self.get(url)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def create_config_nodes(self, **kwargs):
+ """
+ :param kwargs:
+ :return: map object
+ """
+ url = '/config-nodes'
+ post_body = json.dumps({'config-node': kwargs})
+ resp, body = self.post(url, post_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def delete_config_node(self, node_id):
+ """
+ :param node_id:
+ :return: response object
+ """
+ url = '/config-node/%s' % str(node_id)
+ return self.delete(url)
+
+ def show_config_node(self, node_id):
+ """
+ :param node_id:
+ :return: response object
+ """
+ url = '/config-node/%s' % str(node_id)
+ return self.get(url)
+
+ def update_config_node(self, node_id, **kwargs):
+ """
+ :param node_id:
+ :param kwargs:
+ :return: map object
+ """
+ url = '/config-node/%s' % str(node_id)
+ put_data = {'config-node': kwargs}
+ req_put_data = json.dumps(put_data)
+ resp, body = self.put(url, req_put_data)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ # Below are client codes for config-root APIs
+ def list_config_roots(self):
+ """
+ :return: map object
+ """
+ url = '/config-roots'
+ resp, body = self.get(url)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def create_config_roots(self, **kwargs):
+ """
+ :param kwargs:
+ :return: map object
+ """
+ url = '/config-roots'
+ post_body = json.dumps({'config-root': kwargs})
+ resp, body = self.post(url, post_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def delete_config_root(self, root_id):
+ """
+ :param root_id:
+ :return: response object
+ """
+ url = '/config-root/%s' % str(root_id)
+ return self.delete(url)
+
+ def show_config_root(self, root_id):
+ """
+ :param root_id:
+ :return: response object
+ """
+ url = '/config-root/%s' % str(root_id)
+ return self.get(url)
+
+ def update_config_root(self, root_id, **kwargs):
+ """
+ :param root_id:
+ :param kwargs:
+ :return: map object
+ """
+ url = '/config-root/%s' % str(root_id)
+ put_data = {'config-root': kwargs}
+ req_put_data = json.dumps(put_data)
+ resp, body = self.put(url, req_put_data)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
diff --git a/tungsten_tempest_plugin/services/contrail/json/database_client.py b/tungsten_tempest_plugin/services/contrail/json/database_client.py
new file mode 100644
index 0000000..8cc5a3b
--- /dev/null
+++ b/tungsten_tempest_plugin/services/contrail/json/database_client.py
@@ -0,0 +1,74 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest service class for database test cases
+"""
+
+from oslo_serialization import jsonutils as json
+from tungsten_tempest_plugin.services.contrail.json import base
+
+
+class ContrailDatabaseClient(base.BaseContrailClient):
+
+ """
+ Service class for database test cases
+ """
+
+ def list_database_nodes(self):
+ """
+ :return: response object
+ """
+ url = '/database-nodes'
+ return self.get(url)
+
+ def show_database_node(self, db_node_id):
+ """
+ :param db_node_id:
+ :return: response object
+ """
+ url = '/database-node/%s' % db_node_id
+ return self.get(url)
+
+ def create_databse_nodes(self, **kwargs):
+ """
+ :param kwargs:
+ :return: map object
+ """
+ post_body = json.dumps({'database-node': kwargs})
+ url = '/database-nodes'
+ resp, body = self.post(url, post_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def delete_database_node(self, db_node_id):
+ """
+ :param db_node_id:
+ :return: response object
+ """
+ url = '/database-node/%s' % db_node_id
+ return self.delete(url)
+
+ def update_database_node(self, db_node_id, **kwargs):
+ """
+ :param db_node_id:
+ :param kwargs:
+ :return: map object
+ """
+ post_body = json.dumps({'database-node': kwargs})
+ url = '/database-node/%s' % db_node_id
+ resp, body = self.put(url, post_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
diff --git a/tungsten_tempest_plugin/services/contrail/json/discovery_service_assignment_client.py b/tungsten_tempest_plugin/services/contrail/json/discovery_service_assignment_client.py
new file mode 100644
index 0000000..870c30f
--- /dev/null
+++ b/tungsten_tempest_plugin/services/contrail/json/discovery_service_assignment_client.py
@@ -0,0 +1,79 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest service class for database service assignment test cases
+"""
+
+import json
+from six.moves.urllib import parse as urllib
+from tungsten_tempest_plugin.services.contrail.json import base
+
+
+class DiscoveryServiceAssignmentClient(base.BaseContrailClient):
+
+ """
+ Service class for dsa test cases
+ """
+
+ def list_ds_assignments(self, params=None):
+ """
+ :param params:
+ :return: response object
+ """
+ url = '/discovery-service-assignments'
+ if params:
+ url += '?%s' % urllib.urlencode(params)
+ return self.get(url)
+
+ def create_ds_assignments(self, **kwargs):
+ """
+ :param kwargs:
+ :return: map object
+ """
+ url = '/discovery-service-assignments'
+ post_body = json.dumps({'discovery-service-assignment': kwargs})
+ resp, body = self.post(url, post_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def show_ds_assignment(self, assignment_id):
+ """
+ :param assignment_id:
+ :return: response object
+ """
+ url = '/discovery-service-assignment/%s' % str(assignment_id)
+ return self.get(url)
+
+ def delete_ds_assignment(self, assignment_id):
+ """
+ :param assignment_id:
+ :return: response object
+ """
+ url = '/discovery-service-assignment/%s' % str(assignment_id)
+ return self.delete(url)
+
+ def update_ds_assignment(self, assignment_id, **kwargs):
+ """
+ :param assignment_id:
+ :param kwargs:
+ :return: map object
+ """
+ url = '/discovery-service-assignment/%s' % str(assignment_id)
+ post_data = {'discovery-service-assignment': kwargs}
+ req_post_data = json.dumps(post_data)
+ resp, body = self.put(url, req_post_data)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
diff --git a/tungsten_tempest_plugin/services/contrail/json/domain_client.py b/tungsten_tempest_plugin/services/contrail/json/domain_client.py
new file mode 100644
index 0000000..447a020
--- /dev/null
+++ b/tungsten_tempest_plugin/services/contrail/json/domain_client.py
@@ -0,0 +1,84 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest service class for domain test cases
+"""
+
+import json
+from six.moves.urllib import parse as urllib
+from tungsten_tempest_plugin.services.contrail.json import base
+
+
+class DomainClient(base.BaseContrailClient):
+
+ """
+ Service class for domain test cases
+ """
+
+
+ def list_domains(self, params=None):
+ """
+ :param params:
+ :return: map object
+ """
+ url = '/domains'
+ if params:
+ url += '?%s' % urllib.urlencode(params)
+ resp, body = self.get(url)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def create_domains(self, **kwargs):
+ """
+ :param kwargs:
+ :return: map object
+ """
+ url = '/domains'
+ resp, body = self.post(url, json.dumps({'domain': kwargs}))
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def show_domain(self, uuid, params=None):
+ """
+ :param uuid:
+ :param params:
+ :return: map object
+ """
+ url = '/domain/{0}'.format(uuid)
+ if params:
+ url += '?%s' % urllib.urlencode(params)
+ resp, body = self.get(url)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def update_domain(self, uuid, **kwargs):
+ """
+ :param uuid:
+ :param kwargs:
+ :return: map object
+ """
+ url = '/domain/{0}'.format(uuid)
+ resp, body = self.put(url, json.dumps({'domain': kwargs}))
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def delete_domain(self, uuid):
+ """
+ :param uuid:
+ :return: response object
+ """
+ url = '/domain/{0}'.format(uuid)
+ return self.delete(url)
diff --git a/tungsten_tempest_plugin/services/contrail/json/dsa_rule_client.py b/tungsten_tempest_plugin/services/contrail/json/dsa_rule_client.py
new file mode 100644
index 0000000..07ccb87
--- /dev/null
+++ b/tungsten_tempest_plugin/services/contrail/json/dsa_rule_client.py
@@ -0,0 +1,78 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest service class for dsa rule test cases
+"""
+
+import json
+from six.moves.urllib import parse as urllib
+from tungsten_tempest_plugin.services.contrail.json import base
+
+
+class DSARuleClient(base.BaseContrailClient):
+
+ """
+ Service class for dsa rules test cases
+ """
+
+ def list_dsa_rules(self, params=None):
+ """
+ :param params:
+ :return: response object
+ """
+ url = '/dsa-rules'
+ if params:
+ url += '?%s' % urllib.urlencode(params)
+ return self.get(url)
+
+ def create_dsa_rules(self, **kwargs):
+ """
+ :param kwargs:
+ :return: map object
+ """
+ url = '/dsa-rules'
+ post_body = json.dumps({'dsa-rule': kwargs})
+ resp, body = self.post(url, post_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def show_dsa_rule(self, dns_id):
+ """
+ :param dns_id:
+ :return: response object
+ """
+ url = '/dsa-rule/%s' % dns_id
+ return self.get(url)
+
+ def delete_dsa_rule(self, dns_id):
+ """
+ :param dns_id:
+ :return: response object
+ """
+ url = '/dsa-rule/%s' % dns_id
+ return self.delete(url)
+
+ def update_dsa_rule(self, dns_id, **kwargs):
+ """
+ :param dns_id:
+ :param kwargs:
+ :return: map object
+ """
+ url = '/dsa-rule/%s' % dns_id
+ post_body = json.dumps({'dsa-rule': kwargs})
+ resp, body = self.put(url, post_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
diff --git a/tungsten_tempest_plugin/services/contrail/json/floating_ip_client.py b/tungsten_tempest_plugin/services/contrail/json/floating_ip_client.py
new file mode 100644
index 0000000..1fd27cc
--- /dev/null
+++ b/tungsten_tempest_plugin/services/contrail/json/floating_ip_client.py
@@ -0,0 +1,169 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest service class for floating IP test cases
+"""
+
+from oslo_serialization import jsonutils as json
+from six.moves.urllib import parse as urllib
+from tungsten_tempest_plugin.services.contrail.json import base
+
+
+class FloatingIpClient(base.BaseContrailClient):
+
+ """
+ Service class for floating ip test cases
+ """
+
+ def create_floating_ip_pools(self, **kwargs):
+ """
+ :param kwargs:
+ :return: map object
+ """
+ uri = '/floating-ip-pools'
+
+ post_data = {'floating-ip-pool': kwargs}
+ req_post_data = json.dumps(post_data)
+
+ resp, body = self.post(uri, req_post_data)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def list_floating_ip_pools(self, **kwargs):
+ """
+ :param kwargs:
+ :return: map object
+ """
+ uri = '/floating-ip-pools'
+
+ if kwargs:
+ uri += '?' + urllib.urlencode(kwargs)
+
+ resp, body = self.get(uri)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def update_floating_ip_pool(self, floatingip_pool_id, **kwargs):
+ """
+ :param floatingip_pool_id:
+ :param kwargs:
+ :return: map object
+ """
+ uri = '/floating-ip-pool/%s' % floatingip_pool_id
+
+ post_data = {'floating-ip-pool': kwargs}
+ req_post_data = json.dumps(post_data)
+
+ resp, body = self.put(uri, req_post_data)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def show_floating_ip_pool(self, floatingip_pool_id, **fields):
+ """
+ :param floatingip_pool_id:
+ :param fields:
+ :return: map object
+ """
+ uri = '/floating-ip-pool/%s' % floatingip_pool_id
+
+ # fields is a dict which key is 'fields' and value is a
+ # list of field's name. An example:
+ # {'fields': ['id', 'name']}
+ if fields:
+ uri += '?' + urllib.urlencode(fields)
+
+ resp, body = self.get(uri)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def delete_floating_ip_pool(self, floatingip_pool_id):
+ """
+ :param floatingip_pool_id:
+ :return: map object
+ """
+ uri = '/floating-ip-pool/%s' % floatingip_pool_id
+ resp, body = self.delete(uri)
+ return base.ResponseBody(resp, body)
+
+ def create_floating_ips(self, **kwargs):
+ """
+ :param kwargs:
+ :return: map object
+ """
+ uri = '/floating-ips'
+
+ post_data = {'floating-ip': kwargs}
+ req_post_data = json.dumps(post_data)
+
+ resp, body = self.post(uri, req_post_data)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def list_floating_ips(self, **kwargs):
+ """
+ :param kwargs:
+ :return: map object
+ """
+ uri = '/floating-ips'
+
+ if kwargs:
+ uri += '?' + urllib.urlencode(kwargs)
+
+ resp, body = self.get(uri)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def show_floating_ip(self, floatingip_id, **fields):
+ """
+ :param floatingip_id:
+ :param fields:
+ :return: map object
+ """
+ uri = '/floating-ip/%s' % floatingip_id
+
+ # fields is a dict which key is 'fields' and value is a
+ # list of field's name. An example:
+ # {'fields': ['id', 'name']}
+ if fields:
+ uri += '?' + urllib.urlencode(fields)
+
+ resp, body = self.get(uri)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def update_floating_ip(self, floatingip_id, **kwargs):
+ """
+ :param floatingip_id:
+ :param kwargs:
+ :return: map object
+ """
+ uri = '/floating-ip/%s' % floatingip_id
+
+ post_data = {'floating-ip': kwargs}
+ req_post_data = json.dumps(post_data)
+
+ resp, body = self.put(uri, req_post_data)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def delete_floating_ip(self, floatingip_id):
+ """
+ :param floatingip_id:
+ :return: map object
+ """
+ uri = '/floating-ip/%s' % floatingip_id
+ resp, body = self.delete(uri)
+ return base.ResponseBody(resp, body)
diff --git a/tungsten_tempest_plugin/services/contrail/json/forwarding_class_client.py b/tungsten_tempest_plugin/services/contrail/json/forwarding_class_client.py
new file mode 100644
index 0000000..b5b9faf
--- /dev/null
+++ b/tungsten_tempest_plugin/services/contrail/json/forwarding_class_client.py
@@ -0,0 +1,74 @@
+# Copyright 2016 AT&T Corp
+# 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 six.moves.urllib import parse as urllib
+from tungsten_tempest_plugin.services.contrail.json import base
+
+
+class ForwardingClassClient(base.BaseContrailClient):
+
+ """
+ Service class for forwarding class test cases
+ """
+
+ def list_forwarding_classs(self, params=None):
+ """
+ :param params:
+ :return: response object
+ """
+ url = '/forwarding-classs'
+ if params:
+ url += '?{0}'.format(urllib.urlencode(params))
+ return self.get(url)
+
+ def show_forwarding_class(self, uuid):
+ """
+ :param uuid:
+ :return: response object
+ """
+ url = '/forwarding-class/{0}'.format(uuid)
+ return self.get(url)
+
+ def create_forwarding_classs(self, **kwargs):
+ """
+ :param kwargs:
+ :return: map object
+ """
+ url = '/forwarding-classs'
+ post_body = json.dumps({'forwarding-class': kwargs})
+ resp, body = self.post(url, post_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def update_forwarding_class(self, uuid, **kwargs):
+ """
+ :param uuid:
+ :param kwargs:
+ :return: map object
+ """
+ url = '/forwarding-class/{0}'.format(uuid)
+ put_body = json.dumps({'forwarding-class': kwargs})
+ resp, body = self.put(url, put_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def delete_forwarding_class(self, uuid):
+ """
+ :param uuid:
+ :return: response object
+ """
+ url = '/forwarding-class/{0}'.format(uuid)
+ return self.delete(url)
diff --git a/tungsten_tempest_plugin/services/contrail/json/fq_client.py b/tungsten_tempest_plugin/services/contrail/json/fq_client.py
new file mode 100644
index 0000000..77b980a
--- /dev/null
+++ b/tungsten_tempest_plugin/services/contrail/json/fq_client.py
@@ -0,0 +1,52 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest service class for forward class test cases
+"""
+
+from oslo_serialization import jsonutils as json
+from tungsten_tempest_plugin.services.contrail.json import base
+
+
+class FqnameIdClient(base.BaseContrailClient):
+
+ """
+ Service class for fq name test cases
+ """
+
+ def fqname_to_id(self, **kwargs):
+ """
+ :param kwargs:
+ :return: map object
+ """
+ uri = '/fqname-to-id'
+ req_post_data = json.dumps(kwargs)
+
+ resp, body = self.post(uri, req_post_data)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def id_to_fqname(self, **kwargs):
+ """
+ :param kwargs:
+ :return: map object
+ """
+ uri = '/id-to-fqname'
+ req_post_data = json.dumps(kwargs)
+
+ resp, body = self.post(uri, req_post_data)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
diff --git a/tungsten_tempest_plugin/services/contrail/json/instance_ip_client.py b/tungsten_tempest_plugin/services/contrail/json/instance_ip_client.py
new file mode 100644
index 0000000..b93e9cf
--- /dev/null
+++ b/tungsten_tempest_plugin/services/contrail/json/instance_ip_client.py
@@ -0,0 +1,83 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest service class for instance IP test cases
+"""
+
+from oslo_serialization import jsonutils as json
+from six.moves.urllib import parse as urllib
+from tungsten_tempest_plugin.services.contrail.json import base
+
+
+class InstanceIPClient(base.BaseContrailClient):
+
+ """
+ Service class for instance ip test cases
+ """
+
+ def list_instance_ips(self, **kwargs):
+ """
+ :param kwargs:
+ :return: map object
+ """
+ url = '/instance-ips'
+ if kwargs:
+ url += '?%s' % urllib.urlencode(kwargs)
+ resp, body = self.get(url)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def create_instance_ips(self, **kwargs):
+ """
+ :param kwargs:
+ :return: map object
+ """
+ url = '/instance-ips'
+ post_body = {'instance-ip': kwargs}
+ resp, body = self.post(url, json.dumps(post_body))
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def show_instance_ip(self, uuid):
+ """
+ :param uuid:
+ :return: map object
+ """
+ url = '/instance-ip/{0}'.format(uuid)
+ resp, body = self.get(url)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def update_instance_ip(self, uuid, **kwargs):
+ """
+ :param uuid:
+ :param kwargs:
+ :return: map object
+ """
+ url = '/instance-ip/{0}'.format(uuid)
+ put_body = {'instance-ip': kwargs}
+ resp, body = self.put(url, json.dumps(put_body))
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def delete_instance_ip(self, uuid):
+ """
+ :param uuid:
+ :return: map object
+ """
+ url = '/instance-ip/{0}'.format(uuid)
+ resp, body = self.delete(url)
+ return base.ResponseBody(resp, body)
diff --git a/tungsten_tempest_plugin/services/contrail/json/interface_client.py b/tungsten_tempest_plugin/services/contrail/json/interface_client.py
new file mode 100644
index 0000000..e1267d2
--- /dev/null
+++ b/tungsten_tempest_plugin/services/contrail/json/interface_client.py
@@ -0,0 +1,126 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest service class for interface test cases
+"""
+
+from oslo_serialization import jsonutils as json
+from tungsten_tempest_plugin.services.contrail.json import base
+
+
+class InterfaceClient(base.BaseContrailClient):
+
+ """
+ Service class for interface test cases
+ """
+
+ def list_physical_interfaces(self):
+ """
+ :return: response object
+ """
+ url = '/physical-interfaces'
+ return self.get(url)
+
+ def create_physical_interfaces(self, **kwargs):
+ """
+ :param kwargs:
+ :return: map object
+ """
+ url = '/physical-interfaces'
+ post_body = json.dumps({'physical-interface': kwargs})
+ resp, body = self.post(url, post_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def update_physical_interface(self, uuid, **kwargs):
+ """
+ :param uuid:
+ :param kwargs:
+ :return: map object
+ """
+ url = '/physical-interface/%s' % uuid
+ post_data = {'physical-interface': kwargs}
+ req_post_data = json.dumps(post_data)
+ resp, body = self.put(url, req_post_data)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def delete_physical_interface(self, uuid):
+ """
+ :param uuid:
+ :return: response object
+ """
+ url = '/physical-interface/%s' % uuid
+ return self.delete(url)
+
+ def show_physical_interface(self, uuid):
+ """
+ :param uuid:
+ :return: map object
+ """
+ url = '/physical-interface/%s' % uuid
+ resp, body = self.get(url)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def list_logical_interfaces(self):
+ """
+ :return: response object
+ """
+ url = '/logical-interfaces'
+ return self.get(url)
+
+ def create_logical_interfaces(self, **kwargs):
+ """
+ :param kwargs:
+ :return: map object
+ """
+ url = '/logical-interfaces'
+ post_body = json.dumps({'logical-interface': kwargs})
+ resp, body = self.post(url, post_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def update_logical_interface(self, uuid, **kwargs):
+ """
+ :param uuid:
+ :param kwargs:
+ :return: map object
+ """
+ url = '/logical-interface/%s' % uuid
+ post_data = {'logical-interface': kwargs}
+ req_post_data = json.dumps(post_data)
+ resp, body = self.put(url, req_post_data)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def delete_logical_interface(self, uuid):
+ """
+ :param uuid:
+ :return: response object
+ """
+ url = '/logical-interface/%s' % uuid
+ return self.delete(url)
+
+ def show_logical_interface(self, uuid):
+ """
+ :param uuid:
+ :return: map object
+ """
+ url = '/logical-interface/%s' % uuid
+ resp, body = self.get(url)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
diff --git a/tungsten_tempest_plugin/services/contrail/json/load_balancer_client.py b/tungsten_tempest_plugin/services/contrail/json/load_balancer_client.py
new file mode 100644
index 0000000..741804b
--- /dev/null
+++ b/tungsten_tempest_plugin/services/contrail/json/load_balancer_client.py
@@ -0,0 +1,307 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest service class for load balancer test cases
+"""
+
+import json
+from six.moves.urllib import parse as urllib
+from tungsten_tempest_plugin.services.contrail.json import base
+
+
+class LoadBalancerClient(base.BaseContrailClient):
+
+ """
+ Service class for load balancer test cases
+ """
+
+ def list_load_balancers(self, params=None):
+ """
+ :param params:
+ :return:
+ """
+ url = '/loadbalancers'
+ if params:
+ url += '?%s' % urllib.urlencode(params)
+ resp, body = self.get(url)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def create_load_balancers(self, **kwargs):
+ """
+ :param kwargs:
+ :return:
+ """
+ url = '/loadbalancers'
+ resp, body = self.post(url, json.dumps({'loadbalancer': kwargs}))
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def show_load_balancer(self, uuid, params=None):
+ """
+ :param uuid:
+ :param params:
+ :return:
+ """
+ url = '/loadbalancer/{0}'.format(uuid)
+ if params:
+ url += '?%s' % urllib.urlencode(params)
+ resp, body = self.get(url)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def update_load_balancer(self, uuid, **kwargs):
+ """
+ :param uuid:
+ :param kwargs:
+ :return:
+ """
+ url = '/loadbalancer/{0}'.format(uuid)
+ resp, body = self.put(url, json.dumps({'loadbalancer': kwargs}))
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def delete_load_balancer(self, uuid):
+ """
+ :param uuid:
+ :return:
+ """
+ url = '/loadbalancer/{0}'.format(uuid)
+ return self.delete(url)
+
+ def list_lb_healthmonitors(self, params=None):
+ """
+ :param params:
+ :return:
+ """
+ url = '/loadbalancer-healthmonitors'
+ if params:
+ url += '?%s' % urllib.urlencode(params)
+ resp, body = self.get(url)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def create_lb_healthmonitors(self, **kwargs):
+ """
+ :param kwargs:
+ :return:
+ """
+ url = '/loadbalancer-healthmonitors'
+ resp, body = self.post(url, json.dumps(
+ {'loadbalancer-healthmonitor': kwargs}))
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def show_lb_healthmonitor(self, uuid, params=None):
+ """
+ :param uuid:
+ :param params:
+ :return:
+ """
+ url = '/loadbalancer-healthmonitor/{0}'.format(uuid)
+ if params:
+ url += '?%s' % urllib.urlencode(params)
+ resp, body = self.get(url)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def update_lb_healthmonitor(self, uuid, **kwargs):
+ """
+ :param uuid:
+ :param kwargs:
+ :return:
+ """
+ url = '/loadbalancer-healthmonitor/{0}'.format(uuid)
+ resp, body = self.put(url, json.dumps(
+ {'loadbalancer-healthmonitor': kwargs}))
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def delete_lb_healthmonitor(self, uuid):
+ """
+ :param uuid:
+ :return:
+ """
+ url = '/loadbalancer-healthmonitor/{0}'.format(uuid)
+ return self.delete(url)
+
+ def list_load_balancer_listeners(self, params=None):
+ """
+ :param params:
+ :return:
+ """
+ url = '/loadbalancer-listeners'
+ if params:
+ url += '?%s' % urllib.urlencode(params)
+ resp, body = self.get(url)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def create_load_balancer_listeners(self, **kwargs):
+ """
+ :param kwargs:
+ :return:
+ """
+ url = '/loadbalancer-listeners'
+ resp, body = self.post(url, json.dumps(
+ {'loadbalancer-listener': kwargs}))
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def show_load_balancer_listener(self, uuid, params=None):
+ """
+ :param uuid:
+ :param params:
+ :return:
+ """
+ url = '/loadbalancer-listener/{0}'.format(uuid)
+ if params:
+ url += '?%s' % urllib.urlencode(params)
+ resp, body = self.get(url)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def update_load_balancer_listener(self, uuid, **kwargs):
+ """
+ :param uuid:
+ :param kwargs:
+ :return:
+ """
+ url = '/loadbalancer-listener/{0}'.format(uuid)
+ resp, body = self.put(url, json.dumps(
+ {'loadbalancer-listener': kwargs}))
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def delete_load_balancer_listener(self, uuid):
+ """
+ :param uuid:
+ :return:
+ """
+ url = '/loadbalancer-listener/{0}'.format(uuid)
+ return self.delete(url)
+
+ def list_load_balancer_pools(self, params=None):
+ """
+ :param params:
+ :return:
+ """
+ url = '/loadbalancer-pools'
+ if params:
+ url += '?%s' % urllib.urlencode(params)
+ resp, body = self.get(url)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def create_load_balancer_pools(self, **kwargs):
+ """
+ :param kwargs:
+ :return:
+ """
+ url = '/loadbalancer-pools'
+ resp, body = self.post(url, json.dumps(
+ {'loadbalancer-pool': kwargs}))
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def show_load_balancer_pool(self, uuid, params=None):
+ """
+ :param uuid:
+ :param params:
+ :return:
+ """
+ url = '/loadbalancer-pool/{0}'.format(uuid)
+ if params:
+ url += '?%s' % urllib.urlencode(params)
+ resp, body = self.get(url)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def update_load_balancer_pool(self, uuid, **kwargs):
+ """
+ :param uuid:
+ :param kwargs:
+ :return:
+ """
+ url = '/loadbalancer-pool/{0}'.format(uuid)
+ resp, body = self.put(url, json.dumps(
+ {'loadbalancer-pool': kwargs}))
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def delete_load_balancer_pool(self, uuid):
+ """
+ :param uuid:
+ :return:
+ """
+ url = '/loadbalancer-pool/{0}'.format(uuid)
+ return self.delete(url)
+
+ def list_load_balancer_members(self, params=None):
+ """
+ :param params:
+ :return:
+ """
+ url = '/loadbalancer-members'
+ if params:
+ url += '?%s' % urllib.urlencode(params)
+ resp, body = self.get(url)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def create_load_balancer_members(self, **kwargs):
+ """
+ :param kwargs:
+ :return:
+ """
+ url = '/loadbalancer-members'
+ resp, body = self.post(url, json.dumps(
+ {'loadbalancer-member': kwargs}))
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def show_load_balancer_member(self, uuid, params=None):
+ """
+ :param uuid:
+ :param params:
+ :return:
+ """
+ url = '/loadbalancer-member/{0}'.format(uuid)
+ if params:
+ url += '?%s' % urllib.urlencode(params)
+ resp, body = self.get(url)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def update_load_balancer_member(self, uuid, **kwargs):
+ """
+ :param uuid:
+ :param kwargs:
+ :return:
+ """
+ url = '/loadbalancer-member/{0}'.format(uuid)
+ resp, body = self.put(url, json.dumps(
+ {'loadbalancer-member': kwargs}))
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def delete_load_balancer_member(self, uuid):
+ """
+ :param uuid:
+ :return:
+ """
+ url = '/loadbalancer-member/{0}'.format(uuid)
+ return self.delete(url)
diff --git a/tungsten_tempest_plugin/services/contrail/json/namespace_client.py b/tungsten_tempest_plugin/services/contrail/json/namespace_client.py
new file mode 100644
index 0000000..c9a3ed9
--- /dev/null
+++ b/tungsten_tempest_plugin/services/contrail/json/namespace_client.py
@@ -0,0 +1,83 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest service class for namespace test cases
+"""
+
+import json
+from six.moves.urllib import parse as urllib
+from tungsten_tempest_plugin.services.contrail.json import base
+
+
+class NamespaceClient(base.BaseContrailClient):
+
+ """
+ Service class for namespace test cases
+ """
+
+ def list_namespaces(self, params=None):
+ """
+ :param params:
+ :return:
+ """
+ url = '/namespaces'
+ if params:
+ url += '?%s' % urllib.urlencode(params)
+ resp, body = self.get(url)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def create_namespaces(self, **kwargs):
+ """
+ :param kwargs:
+ :return:
+ """
+ url = '/namespaces'
+ resp, body = self.post(url, json.dumps({'namespace': kwargs}))
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def show_namespace(self, uuid, params=None):
+ """
+ :param uuid:
+ :param params:
+ :return:
+ """
+ url = '/namespace/{0}'.format(uuid)
+ if params:
+ url += '?%s' % urllib.urlencode(params)
+ resp, body = self.get(url)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def update_namespace(self, uuid, **kwargs):
+ """
+ :param uuid:
+ :param kwargs:
+ :return:
+ """
+ url = '/namespace/{0}'.format(uuid)
+ resp, body = self.put(url, json.dumps({'namespace': kwargs}))
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def delete_namespace(self, uuid):
+ """
+ :param uuid:
+ :return:
+ """
+ url = '/namespace/{0}'.format(uuid)
+ return self.delete(url)
diff --git a/tungsten_tempest_plugin/services/contrail/json/network_ipams_client.py b/tungsten_tempest_plugin/services/contrail/json/network_ipams_client.py
new file mode 100644
index 0000000..ea0adfc
--- /dev/null
+++ b/tungsten_tempest_plugin/services/contrail/json/network_ipams_client.py
@@ -0,0 +1,79 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest service class for n/w ipam test cases
+"""
+
+import json
+from six.moves.urllib import parse as urllib
+from tungsten_tempest_plugin.services.contrail.json import base
+
+
+class NetworkIpamsClient(base.BaseContrailClient):
+
+ """
+ Service class for network ipam test cases
+ """
+
+ def list_network_ipams(self, params=None):
+ """
+ :param params:
+ :return:
+ """
+ url = '/network-ipams'
+ if params:
+ url += '?%s' % urllib.urlencode(params)
+ return self.get(url)
+
+ def create_network_ipams(self, **kwargs):
+ """
+ :param kwargs:
+ :return:
+ """
+ url = '/network-ipams'
+ post_body = json.dumps({'network-ipam': kwargs})
+ resp, body = self.post(url, post_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def show_network_ipam(self, instance_id):
+ """
+ :param instance_id:
+ :return:
+ """
+ url = '/network-ipam/%s' % str(instance_id)
+ return self.get(url)
+
+ def delete_network_ipam(self, instance_id):
+ """
+ :param instance_id:
+ :return:
+ """
+ url = '/network-ipam/%s' % str(instance_id)
+ return self.delete(url)
+
+ def update_network_ipam(self, instance_id, **kwargs):
+ """
+ :param instance_id:
+ :param kwargs:
+ :return:
+ """
+ url = '/network-ipam/%s' % str(instance_id)
+ post_data = {'network-ipam': kwargs}
+ req_post_data = json.dumps(post_data)
+ resp, body = self.put(url, req_post_data)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
diff --git a/tungsten_tempest_plugin/services/contrail/json/network_policy_client.py b/tungsten_tempest_plugin/services/contrail/json/network_policy_client.py
new file mode 100644
index 0000000..88ed49c
--- /dev/null
+++ b/tungsten_tempest_plugin/services/contrail/json/network_policy_client.py
@@ -0,0 +1,83 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest service class for netwrok policy test cases
+"""
+
+import json
+from six.moves.urllib import parse as urllib
+from tungsten_tempest_plugin.services.contrail.json import base
+
+
+class NetworkPolicyClient(base.BaseContrailClient):
+
+ """
+ Service class for network policy test cases
+ """
+
+ def list_network_policys(self, params=None):
+ """
+ :param params:
+ :return:
+ """
+ url = '/network-policys'
+ if params:
+ url += '?%s' % urllib.urlencode(params)
+ resp, body = self.get(url)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def create_network_policys(self, **kwargs):
+ """
+ :param kwargs:
+ :return:
+ """
+ url = '/network-policys'
+ resp, body = self.post(url, json.dumps({'network-policy': kwargs}))
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def show_network_policy(self, uuid, params=None):
+ """
+ :param uuid:
+ :param params:
+ :return:
+ """
+ url = '/network-policy/{0}'.format(uuid)
+ if params:
+ url += '?%s' % urllib.urlencode(params)
+ resp, body = self.get(url)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def update_network_policy(self, uuid, **kwargs):
+ """
+ :param uuid:
+ :param kwargs:
+ :return:
+ """
+ url = '/network-policy/{0}'.format(uuid)
+ resp, body = self.put(url, json.dumps({'network-policy': kwargs}))
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def delete_network_policy(self, uuid):
+ """
+ :param uuid:
+ :return:
+ """
+ url = '/network-policy/{0}'.format(uuid)
+ return self.delete(url)
diff --git a/tungsten_tempest_plugin/services/contrail/json/port_tuple_client.py b/tungsten_tempest_plugin/services/contrail/json/port_tuple_client.py
new file mode 100644
index 0000000..c7082bc
--- /dev/null
+++ b/tungsten_tempest_plugin/services/contrail/json/port_tuple_client.py
@@ -0,0 +1,75 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest service class for tuple test cases
+"""
+
+import json
+from six.moves.urllib import parse as urllib
+from tungsten_tempest_plugin.services.contrail.json import base
+
+
+class PortTupleClient(base.BaseContrailClient):
+
+
+ def list_port_tuples(self, params=None):
+ """
+ :param params:
+ :return:
+ """
+ url = '/port-tuples'
+ if params:
+ url += '?{0}'.format(urllib.urlencode(params))
+ return self.get(url)
+
+ def show_port_tuple(self, uuid):
+ """
+ :param uuid:
+ :return:
+ """
+ url = '/port-tuple/{0}'.format(uuid)
+ return self.get(url)
+
+ def create_port_tuples(self, **kwargs):
+ """
+ :param kwargs:
+ :return:
+ """
+ url = '/port-tuples'
+ post_body = json.dumps({'port-tuple': kwargs})
+ resp, body = self.post(url, post_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def update_port_tuple(self, uuid, **kwargs):
+ """
+ :param uuid:
+ :param kwargs:
+ :return:
+ """
+ url = '/port-tuple/{0}'.format(uuid)
+ put_body = json.dumps({'port-tuple': kwargs})
+ resp, body = self.put(url, put_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def delete_port_tuple(self, uuid):
+ """
+ :param uuid:
+ :return:
+ """
+ url = '/port-tuple/{0}'.format(uuid)
+ return self.delete(url)
diff --git a/tungsten_tempest_plugin/services/contrail/json/project_client.py b/tungsten_tempest_plugin/services/contrail/json/project_client.py
new file mode 100644
index 0000000..a5fb73b
--- /dev/null
+++ b/tungsten_tempest_plugin/services/contrail/json/project_client.py
@@ -0,0 +1,83 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest service class for project test cases
+"""
+
+import json
+from six.moves.urllib import parse as urllib
+from tungsten_tempest_plugin.services.contrail.json import base
+
+
+class ProjectClient(base.BaseContrailClient):
+
+ """
+ Service class for project test cases
+ """
+
+ def list_projects(self, params=None):
+ """
+ :param params:
+ :return:
+ """
+ url = '/projects'
+ if params:
+ url += '?%s' % urllib.urlencode(params)
+ resp, body = self.get(url)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def create_projects(self, **kwargs):
+ """
+ :param kwargs:
+ :return:
+ """
+ url = '/projects'
+ resp, body = self.post(url, json.dumps({'project': kwargs}))
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def show_project(self, uuid, params=None):
+ """
+ :param uuid:
+ :param params:
+ :return:
+ """
+ url = '/project/{0}'.format(uuid)
+ if params:
+ url += '?%s' % urllib.urlencode(params)
+ resp, body = self.get(url)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def update_project(self, uuid, **kwargs):
+ """
+ :param uuid:
+ :param kwargs:
+ :return:
+ """
+ url = '/project/{0}'.format(uuid)
+ resp, body = self.put(url, json.dumps({'project': kwargs}))
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def delete_project(self, uuid):
+ """
+ :param uuid:
+ :return:
+ """
+ url = '/project/{0}'.format(uuid)
+ return self.delete(url)
diff --git a/tungsten_tempest_plugin/services/contrail/json/qos_client.py b/tungsten_tempest_plugin/services/contrail/json/qos_client.py
new file mode 100644
index 0000000..c08c39a
--- /dev/null
+++ b/tungsten_tempest_plugin/services/contrail/json/qos_client.py
@@ -0,0 +1,179 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest service class for QoS test cases
+"""
+
+import json
+
+from tungsten_tempest_plugin.services.contrail.json import base
+
+
+class QosContrailClient(base.BaseContrailClient):
+
+ """
+ Service class for QoS test cases
+ """
+
+ def show_global_qos_config(self, instance_id):
+ """
+ :param instance_id:
+ :return:
+ """
+ url = '/global-qos-config/%s' % instance_id
+ resp, body = self.get(url)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def delete_global_qos_config(self, instance_id):
+ """
+ :param instance_id:
+ :return:
+ """
+ url = '/global-qos-config/%s' % instance_id
+ return self.delete(url)
+
+ def update_global_qos_config(self, instance_id, **kwargs):
+ """
+ :param instance_id:
+ :param kwargs:
+ :return:
+ """
+ post_body = json.dumps({'global-qos-config': kwargs})
+ url = '/global-qos-config/%s' % instance_id
+ resp, body = self.put(url, post_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def list_global_qos_configs(self):
+ """
+ :return:
+ """
+ url = '/global-qos-configs'
+ resp, body = self.get(url)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def create_global_qos_configs(self, **kwargs):
+ """
+ :param kwargs:
+ :return:
+ """
+ post_body = json.dumps({'global-qos-config': kwargs})
+ url = '/global-qos-configs'
+ resp, body = self.post(url, post_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def show_qos_config(self, qos_config_id):
+ """
+ :param qos_config_id:
+ :return:
+ """
+ url = '/qos-config/%s' % qos_config_id
+ resp, body = self.get(url)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def delete_qos_config(self, qos_config_id):
+ """
+ :param qos_config_id:
+ :return:
+ """
+ url = '/qos-config/%s' % qos_config_id
+ return self.delete(url)
+
+ def update_qos_config(self, qos_config_id, **kwargs):
+ """
+ :param qos_config_id:
+ :param kwargs:
+ :return:
+ """
+ post_body = json.dumps({'qos-config': kwargs})
+ url = '/qos-config/%s' % qos_config_id
+ resp, body = self.put(url, post_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def list_qos_configs(self):
+ """
+ :return:
+ """
+ url = '/qos-configs'
+ resp, body = self.get(url)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def create_qos_configs(self, **kwargs):
+ """
+ :param kwargs:
+ :return:
+ """
+ post_body = json.dumps({'qos-config': kwargs})
+ url = '/qos-configs'
+ resp, body = self.post(url, post_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def show_qos_queue(self, qos_queue_id):
+ """
+ :param qos_queue_id:
+ :return:
+ """
+ url = '/qos-queue/%s' % qos_queue_id
+ resp, body = self.get(url)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def delete_qos_queue(self, qos_queue_id):
+ """
+ :param qos_queue_id:
+ :return:
+ """
+ url = '/qos-queue/%s' % qos_queue_id
+ return self.delete(url)
+
+ def update_qos_queue(self, qos_queue_id, **kwargs):
+ """
+ :param qos_queue_id:
+ :param kwargs:
+ :return:
+ """
+ post_body = json.dumps({'qos-queue': kwargs})
+ url = '/qos-queue/%s' % qos_queue_id
+ resp, body = self.put(url, post_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def list_qos_queues(self):
+ """
+ :return:
+ """
+ url = '/qos-queues'
+ resp, body = self.get(url)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def create_qos_queues(self, **kwargs):
+ """
+ :param kwargs:
+ :return:
+ """
+ post_body = json.dumps({'qos-queue': kwargs})
+ url = '/qos-queues'
+ resp, body = self.post(url, post_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
diff --git a/tungsten_tempest_plugin/services/contrail/json/route_client.py b/tungsten_tempest_plugin/services/contrail/json/route_client.py
new file mode 100644
index 0000000..ba6c0ac
--- /dev/null
+++ b/tungsten_tempest_plugin/services/contrail/json/route_client.py
@@ -0,0 +1,232 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest service class for route test cases
+"""
+
+from oslo_serialization import jsonutils as json
+from tungsten_tempest_plugin.services.contrail.json import base
+
+
+class RouteClient(base.BaseContrailClient):
+
+ """
+ Service class for route test cases
+ """
+
+ def list_route_tables(self):
+ """
+ :return:
+ """
+ url = '/route-tables'
+ resp, body = self.get(url)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def show_route_table(self, route_id):
+ """
+ :param route_id:
+ :return:
+ """
+ url = '/route-table/%s' % route_id
+ resp, body = self.get(url)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def create_route_tables(self, **kwargs):
+ """
+ :param kwargs:
+ :return:
+ """
+ post_body = json.dumps({'route-table': kwargs})
+ url = 'route-tables'
+ resp, body = self.post(url, post_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def update_route_table(self, route_id, **kwargs):
+ """
+ :param route_id:
+ :param kwargs:
+ :return:
+ """
+ post_body = json.dumps({'route-table': kwargs})
+ url = '/route-table/%s' % route_id
+ resp, body = self.put(url, post_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def delete_route_table(self, route_id):
+ """
+ :param route_id:
+ :return:
+ """
+ url = '/route-table/%s' % route_id
+ resp, body = self.delete(url)
+ return base.ResponseBody(resp, body)
+
+ def list_interface_route_tables(self):
+ """
+ :return:
+ """
+ url = '/interface-route-tables'
+ resp, body = self.get(url)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def show_interface_route_table(self, interface_route_id):
+ """
+ :param interface_route_id:
+ :return:
+ """
+ url = '/interface-route-table/%s' % interface_route_id
+ resp, body = self.get(url)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def create_interface_route_tables(self, **kwargs):
+ """
+ :param kwargs:
+ :return:
+ """
+ post_body = json.dumps({'interface-route-table': kwargs})
+ url = 'interface-route-tables'
+ resp, body = self.post(url, post_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def update_interface_route_table(self, interface_route_id, **kwargs):
+ """
+ :param interface_route_id:
+ :param kwargs:
+ :return:
+ """
+ post_body = json.dumps({'interface-route-table': kwargs})
+ url = '/interface-route-table/%s' % interface_route_id
+ resp, body = self.put(url, post_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def delete_interface_route_table(self, interface_route_id):
+ """
+ :param interface_route_id:
+ :return:
+ """
+ url = '/interface-route-table/%s' % interface_route_id
+ resp, body = self.delete(url)
+ return base.ResponseBody(resp, body)
+
+ def list_route_targets(self):
+ """
+ :return:
+ """
+ url = '/route-targets'
+ resp, body = self.get(url)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def show_route_target(self, route_target_id):
+ """
+ :param route_target_id:
+ :return:
+ """
+ url = '/route-target/%s' % route_target_id
+ resp, body = self.get(url)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def create_route_targets(self, **kwargs):
+ """
+ :param kwargs:
+ :return:
+ """
+ post_body = json.dumps({'route-target': kwargs})
+ url = 'route-targets'
+ resp, body = self.post(url, post_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def update_route_target(self, route_target_id, **kwargs):
+ """
+ :param route_target_id:
+ :param kwargs:
+ :return:
+ """
+ post_body = json.dumps({'route-target': kwargs})
+ url = '/route-target/%s' % route_target_id
+ resp, body = self.put(url, post_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def delete_route_target(self, route_target_id):
+ """
+ :param route_target_id:
+ :return:
+ """
+ url = '/route-target/%s' % route_target_id
+ resp, body = self.delete(url)
+ return base.ResponseBody(resp, body)
+
+ def list_route_aggregates(self):
+ """
+ :return:
+ """
+ url = '/route-aggregates'
+ resp, body = self.get(url)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def show_route_aggregate(self, route_aggr_id):
+ """
+ :param route_aggr_id:
+ :return:
+ """
+ url = '/route-aggregate/%s' % route_aggr_id
+ resp, body = self.get(url)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def create_route_aggregates(self, **kwargs):
+ """
+ :param kwargs:
+ :return:
+ """
+ post_body = json.dumps({'route-aggregate': kwargs})
+ url = 'route-aggregates'
+ resp, body = self.post(url, post_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def update_route_aggregate(self, route_aggr_id, **kwargs):
+ """
+ :param route_aggr_id:
+ :param kwargs:
+ :return:
+ """
+ post_body = json.dumps({'route-aggregate': kwargs})
+ url = '/route-aggregate/%s' % route_aggr_id
+ resp, body = self.put(url, post_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def delete_route_aggregate(self, route_aggr_id):
+ """
+ :param route_aggr_id:
+ :return:
+ """
+ url = '/route-aggregate/%s' % route_aggr_id
+ resp, body = self.delete(url)
+ return base.ResponseBody(resp, body)
diff --git a/tungsten_tempest_plugin/services/contrail/json/router_client.py b/tungsten_tempest_plugin/services/contrail/json/router_client.py
new file mode 100644
index 0000000..f0ac8b3
--- /dev/null
+++ b/tungsten_tempest_plugin/services/contrail/json/router_client.py
@@ -0,0 +1,283 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest service class for router test cases
+"""
+
+from oslo_serialization import jsonutils as json
+from tungsten_tempest_plugin.services.contrail.json import base
+
+
+class RouterClient(base.BaseContrailClient):
+
+ """
+ Service class for router test cases
+ """
+
+ def list_virtual_routers(self):
+ """
+ :return:
+ """
+ url = '/virtual-routers'
+ resp, body = self.get(url)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def show_virtual_router(self, vrouter_id):
+ """
+ :param vrouter_id:
+ :return:
+ """
+ url = '/virtual-router/%s' % vrouter_id
+ resp, body = self.get(url)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def create_virtual_routers(self, **kwargs):
+ """
+ :param kwargs:
+ :return:
+ """
+ post_body = json.dumps({'virtual-router': kwargs})
+ url = '/virtual-routers'
+ resp, body = self.post(url, post_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def update_virtual_router(self, vrouter_id, **kwargs):
+ """
+ :param vrouter_id:
+ :param kwargs:
+ :return:
+ """
+ post_body = json.dumps({'virtual-router': kwargs})
+ url = '/virtual-router/%s' % vrouter_id
+ resp, body = self.put(url, post_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def delete_virtual_router(self, vrouter_id):
+ """
+ :param vrouter_id:
+ :return:
+ """
+ url = '/virtual-router/%s' % vrouter_id
+ resp, body = self.delete(url)
+ return base.ResponseBody(resp, body)
+
+ def list_global_vrouter_configs(self):
+ """
+ :return:
+ """
+ url = '/global-vrouter-configs'
+ resp, body = self.get(url)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def show_global_vrouter_config(self, global_vrouter_config_id):
+ """
+ :param global_vrouter_config_id:
+ :return:
+ """
+ url = '/global-vrouter-config/%s' % global_vrouter_config_id
+ resp, body = self.get(url)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def create_global_vrouter_configs(self, **kwargs):
+ """
+ :param kwargs:
+ :return:
+ """
+ post_body = json.dumps({'global-vrouter-config': kwargs})
+ url = '/global-vrouter-configs'
+ resp, body = self.post(url, post_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def update_global_vrouter_config(self, global_vrouter_config_id, **kwargs):
+ """
+ :param global_vrouter_config_id:
+ :param kwargs:
+ :return:
+ """
+ post_body = json.dumps({'global-vrouter-config': kwargs})
+ url = '/global-vrouter-config/%s' % global_vrouter_config_id
+ resp, body = self.put(url, post_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def delete_global_vrouter_config(self, global_vrouter_config_id):
+ """
+ :param global_vrouter_config_id:
+ :return:
+ """
+ url = '/global-vrouter-config/%s' % global_vrouter_config_id
+ resp, body = self.delete(url)
+ return base.ResponseBody(resp, body)
+
+ def list_logical_routers(self):
+ """
+ :return:
+ """
+ url = '/logical-routers'
+ resp, body = self.get(url)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def show_logical_router(self, logical_router_id):
+ """
+ :param logical_router_id:
+ :return:
+ """
+ url = '/logical-router/%s' % logical_router_id
+ resp, body = self.get(url)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def create_logical_routers(self, **kwargs):
+ """
+ :param kwargs:
+ :return:
+ """
+ post_body = json.dumps({'logical-router': kwargs})
+ url = '/logical-routers'
+ resp, body = self.post(url, post_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def update_logical_router(self, logical_router_id, **kwargs):
+ """
+ :param logical_router_id:
+ :param kwargs:
+ :return:
+ """
+ post_body = json.dumps({'logical-router': kwargs})
+ url = '/logical-router/%s' % logical_router_id
+ resp, body = self.put(url, post_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def delete_logical_router(self, logical_router_id):
+ """
+ :param logical_router_id:
+ :return:
+ """
+ url = '/logical-router/%s' % logical_router_id
+ resp, body = self.delete(url)
+ return base.ResponseBody(resp, body)
+
+ def list_bgp_routers(self):
+ """
+ :return:
+ """
+ url = '/bgp-routers'
+ resp, body = self.get(url)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def show_bgp_router(self, bgp_router_id):
+ """
+ :param bgp_router_id:
+ :return:
+ """
+ url = '/bgp-router/%s' % bgp_router_id
+ resp, body = self.get(url)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def create_bgp_routers(self, **kwargs):
+ """
+ :param kwargs:
+ :return:
+ """
+ post_body = json.dumps({'bgp-router': kwargs})
+ url = '/bgp-routers'
+ resp, body = self.post(url, post_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def update_bgp_router(self, bgp_router_id, **kwargs):
+ """
+ :param bgp_router_id:
+ :param kwargs:
+ :return:
+ """
+ post_body = json.dumps({'bgp-router': kwargs})
+ url = '/bgp-router/%s' % bgp_router_id
+ resp, body = self.put(url, post_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def delete_bgp_router(self, bgp_router_id):
+ """
+ :param bgp_router_id:
+ :return:
+ """
+ url = '/bgp-router/%s' % bgp_router_id
+ resp, body = self.delete(url)
+ return base.ResponseBody(resp, body)
+
+ def list_physical_routers(self):
+ """
+ :return:
+ """
+ url = '/physical-routers'
+ resp, body = self.get(url)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def show_physical_router(self, physical_router_id):
+ """
+ :param physical_router_id:
+ :return:
+ """
+ url = '/physical-router/%s' % physical_router_id
+ resp, body = self.get(url)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def create_physical_routers(self, **kwargs):
+ """
+ :param kwargs:
+ :return:
+ """
+ post_body = json.dumps({'physical-router': kwargs})
+ url = '/physical-routers'
+ resp, body = self.post(url, post_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def update_physical_router(self, physical_router_id, **kwargs):
+ """
+ :param physical_router_id:
+ :param kwargs:
+ :return:
+ """
+ post_body = json.dumps({'physical-router': kwargs})
+ url = '/physical-router/%s' % physical_router_id
+ resp, body = self.put(url, post_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def delete_physical_router(self, physical_router_id):
+ """
+ :param physical_router_id:
+ :return:
+ """
+ url = '/physical-router/%s' % physical_router_id
+ resp, body = self.delete(url)
+ return base.ResponseBody(resp, body)
diff --git a/tungsten_tempest_plugin/services/contrail/json/routing_client.py b/tungsten_tempest_plugin/services/contrail/json/routing_client.py
new file mode 100644
index 0000000..09fd36f
--- /dev/null
+++ b/tungsten_tempest_plugin/services/contrail/json/routing_client.py
@@ -0,0 +1,82 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest service class for routing test cases
+"""
+
+import json
+from six.moves.urllib import parse as urllib
+from tungsten_tempest_plugin.services.contrail.json import base
+
+
+class RoutingClient(base.BaseContrailClient):
+
+ """
+ Service class for routing test cases
+ """
+
+ def list_routing_instances(self, params=None):
+ """
+ :param params:
+ :return:
+ """
+ url = '/routing-instances'
+ if params:
+ url += '?%s' % urllib.urlencode(params)
+ return self.get(url)
+
+ def create_routing_instances(self, **kwargs):
+ """
+ :param kwargs:
+ :return:
+ """
+ url = '/routing-instances'
+ post_body = json.dumps({'routing-instance': kwargs})
+ resp, body = self.post(url, post_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def show_routing_instance(self, instance_id):
+ """
+
+ :param instance_id:
+ :return:
+ """
+ url = '/routing-instance/%s' % str(instance_id)
+ return self.get(url)
+
+ def delete_routing_instance(self, instance_id):
+ """
+
+ :param instance_id:
+ :return:
+ """
+ url = '/routing-instance/%s' % str(instance_id)
+ return self.delete(url)
+
+ def update_routing_instance(self, instance_id, **kwargs):
+ """
+
+ :param instance_id:
+ :param kwargs:
+ :return:
+ """
+ url = '/routing-instance/%s' % str(instance_id)
+ post_data = {'routing-instance': kwargs}
+ req_post_data = json.dumps(post_data)
+ resp, body = self.put(url, req_post_data)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
diff --git a/tungsten_tempest_plugin/services/contrail/json/routing_policy_client.py b/tungsten_tempest_plugin/services/contrail/json/routing_policy_client.py
new file mode 100644
index 0000000..e55b535
--- /dev/null
+++ b/tungsten_tempest_plugin/services/contrail/json/routing_policy_client.py
@@ -0,0 +1,83 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest service class for routing policy test cases
+"""
+
+import json
+from six.moves.urllib import parse as urllib
+from tungsten_tempest_plugin.services.contrail.json import base
+
+
+class RoutingPolicyClient(base.BaseContrailClient):
+
+ """
+ Service class for routing policy test cases
+ """
+
+ def list_routing_policys(self, params=None):
+ """
+ :param params:
+ :return:
+ """
+ url = '/routing-policys'
+ if params:
+ url += '?%s' % urllib.urlencode(params)
+ resp, body = self.get(url)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def create_routing_policys(self, **kwargs):
+ """
+ :param kwargs:
+ :return:
+ """
+ url = '/routing-policys'
+ resp, body = self.post(url, json.dumps({'routing-policy': kwargs}))
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def show_routing_policy(self, uuid, params=None):
+ """
+ :param uuid:
+ :param params:
+ :return:
+ """
+ url = '/routing-policy/{0}'.format(uuid)
+ if params:
+ url += '?%s' % urllib.urlencode(params)
+ resp, body = self.get(url)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def update_routing_policy(self, uuid, **kwargs):
+ """
+ :param uuid:
+ :param kwargs:
+ :return:
+ """
+ url = '/routing-policy/{0}'.format(uuid)
+ resp, body = self.put(url, json.dumps({'routing-policy': kwargs}))
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def delete_routing_policy(self, uuid):
+ """
+ :param uuid:
+ :return:
+ """
+ url = '/routing-policy/{0}'.format(uuid)
+ return self.delete(url)
diff --git a/tungsten_tempest_plugin/services/contrail/json/security_group_client.py b/tungsten_tempest_plugin/services/contrail/json/security_group_client.py
new file mode 100644
index 0000000..27535d4
--- /dev/null
+++ b/tungsten_tempest_plugin/services/contrail/json/security_group_client.py
@@ -0,0 +1,74 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest service class for security group test cases
+"""
+
+from oslo_serialization import jsonutils as json
+from tungsten_tempest_plugin.services.contrail.json import base
+
+
+class SecurityGroupClient(base.BaseContrailClient):
+
+ """
+ Service class for security group test cases
+ """
+
+ def list_security_groups(self):
+ """
+ :return:
+ """
+ url = '/security-groups'
+ return self.get(url)
+
+ def show_security_group(self, sec_group_id):
+ """
+ :param sec_group_id:
+ :return:
+ """
+ url = '/security-group/%s' % sec_group_id
+ return self.get(url)
+
+ def create_security_groups(self, **kwargs):
+ """
+ :param kwargs:
+ :return:
+ """
+ post_body = json.dumps({'security-group': kwargs})
+ url = '/security-groups'
+ resp, body = self.post(url, post_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def update_security_group(self, sec_group_id, **kwargs):
+ """
+ :param sec_group_id:
+ :param kwargs:
+ :return:
+ """
+ post_body = json.dumps({'security-group': kwargs})
+ url = '/security-group/%s' % sec_group_id
+ resp, body = self.put(url, post_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def delete_security_group(self, sec_group_id):
+ """
+ :param sec_group_id:
+ :return:
+ """
+ url = '/security-group/%s' % sec_group_id
+ return self.delete(url)
diff --git a/tungsten_tempest_plugin/services/contrail/json/service_appliances_client.py b/tungsten_tempest_plugin/services/contrail/json/service_appliances_client.py
new file mode 100644
index 0000000..1115bde
--- /dev/null
+++ b/tungsten_tempest_plugin/services/contrail/json/service_appliances_client.py
@@ -0,0 +1,129 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest service class for service appliance test cases
+"""
+
+import json
+from six.moves.urllib import parse as urllib
+from tungsten_tempest_plugin.services.contrail.json import base
+
+
+class ServiceAppliancesClient(base.BaseContrailClient):
+
+ """
+ Service class for service appliances test cases
+ """
+
+ def list_service_appliances(self, params=None):
+ """
+ :param params:
+ :return:
+ """
+ url = '/service-appliances'
+ if params:
+ url += '?%s' % urllib.urlencode(params)
+ return self.get(url)
+
+ def create_service_appliances(self, **kwargs):
+ """
+ :param kwargs:
+ :return:
+ """
+ url = '/service-appliances'
+ post_body = json.dumps({'service-appliance': kwargs})
+ resp, body = self.post(url, post_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def show_service_appliance(self, appliance_id):
+ """
+ :param appliance_id:
+ :return:
+ """
+ url = '/service-appliance/%s' % str(appliance_id)
+ return self.get(url)
+
+ def delete_service_appliance(self, appliance_id):
+ """
+ :param appliance_id:
+ :return:
+ """
+ url = '/service-appliance/%s' % str(appliance_id)
+ return self.delete(url)
+
+ def update_service_appliance(self, appliance_id, **kwargs):
+ """
+ :param appliance_id:
+ :param kwargs:
+ :return:
+ """
+ url = '/service-appliance/%s' % str(appliance_id)
+ post_data = {'service-appliance': kwargs}
+ req_post_data = json.dumps(post_data)
+ resp, body = self.put(url, req_post_data)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def list_service_appliance_sets(self, params=None):
+ """
+ :param params:
+ :return:
+ """
+ url = '/service-appliance-sets'
+ if params:
+ url += '?%s' % urllib.urlencode(params)
+ return self.get(url)
+
+ def create_service_appliance_sets(self, **kwargs):
+ """
+ :param kwargs:
+ :return:
+ """
+ url = '/service-appliance-sets'
+ post_body = json.dumps({'service-appliance-set': kwargs})
+ resp, body = self.post(url, post_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def show_service_appliance_set(self, appliance_id):
+ """
+ :param appliance_id:
+ :return:
+ """
+ url = '/service-appliance-set/%s' % str(appliance_id)
+ return self.get(url)
+
+ def delete_service_appliance_set(self, appliance_id):
+ """
+ :param appliance_id:
+ :return:
+ """
+ url = '/service-appliance-set/%s' % str(appliance_id)
+ return self.delete(url)
+
+ def update_service_appliance_set(self, appliance_id, **kwargs):
+ """
+ :param appliance_id:
+ :param kwargs:
+ :return:
+ """
+ url = '/service-appliance-set/%s' % str(appliance_id)
+ post_data = {'service-appliance-set': kwargs}
+ req_post_data = json.dumps(post_data)
+ resp, body = self.put(url, req_post_data)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
diff --git a/tungsten_tempest_plugin/services/contrail/json/service_client.py b/tungsten_tempest_plugin/services/contrail/json/service_client.py
new file mode 100644
index 0000000..ebbef8d
--- /dev/null
+++ b/tungsten_tempest_plugin/services/contrail/json/service_client.py
@@ -0,0 +1,179 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest service class for service test cases
+"""
+
+import json
+from six.moves.urllib import parse as urllib
+from tungsten_tempest_plugin.services.contrail.json import base
+
+
+class ServiceClient(base.BaseContrailClient):
+
+ """
+ Service class for service client test cases
+ """
+
+ def list_service_templates(self, params=None):
+ """
+ :param params:
+ :return:
+ """
+ url = '/service-templates'
+ if params:
+ url += '?%s' % urllib.urlencode(params)
+ return self.get(url)
+
+ def create_service_templates(self, **kwargs):
+ """
+ :param kwargs:
+ :return:
+ """
+ url = '/service-templates'
+ post_body = json.dumps({'service-template': kwargs})
+ resp, body = self.post(url, post_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def show_service_template(self, template_id):
+ """
+ :param template_id:
+ :return:
+ """
+ url = '/service-template/%s' % str(template_id)
+ return self.get(url)
+
+ def delete_service_template(self, template_id):
+ """
+ :param template_id:
+ :return:
+ """
+ url = '/service-template/%s' % str(template_id)
+ return self.delete(url)
+
+ def update_service_template(self, template_id, **kwargs):
+ """
+ :param template_id:
+ :param kwargs:
+ :return:
+ """
+ url = '/service-template/%s' % str(template_id)
+ put_data = {'service-template': kwargs}
+ req_put_data = json.dumps(put_data)
+ resp, body = self.put(url, req_put_data)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def list_service_health_checks(self, params=None):
+ """
+ :param params:
+ :return:
+ """
+ url = '/service-health-checks'
+ if params:
+ url += '?%s' % urllib.urlencode(params)
+ return self.get(url)
+
+ def create_service_health_checks(self, **kwargs):
+ """
+ :param kwargs:
+ :return:
+ """
+ url = '/service-health-checks'
+ post_body = json.dumps({'service-health-check': kwargs})
+ resp, body = self.post(url, post_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def show_service_health_check(self, template_id):
+ """
+ :param template_id:
+ :return:
+ """
+ url = '/service-health-check/%s' % str(template_id)
+ return self.get(url)
+
+ def delete_service_health_check(self, template_id):
+ """
+ :param template_id:
+ :return:
+ """
+ url = '/service-health-check/%s' % str(template_id)
+ return self.delete(url)
+
+ def update_service_health_check(self, template_id, **kwargs):
+ """
+ :param template_id:
+ :param kwargs:
+ :return:
+ """
+ url = '/service-health-check/%s' % str(template_id)
+ put_data = {'service-health-check': kwargs}
+ req_put_data = json.dumps(put_data)
+ resp, body = self.put(url, req_put_data)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def create_service_instances(self, **kwargs):
+ """
+ :param kwargs:
+ :return:
+ """
+ url = '/service-instances'
+ post_body = json.dumps({'service-instance': kwargs})
+ resp, body = self.post(url, post_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def show_service_instance(self, template_id):
+ """
+ :param template_id:
+ :return:
+ """
+ url = '/service-instance/%s' % str(template_id)
+ return self.get(url)
+
+ def delete_service_instance(self, template_id):
+ """
+ :param template_id:
+ :return:
+ """
+ url = '/service-instance/%s' % str(template_id)
+ return self.delete(url)
+
+ def list_service_instances(self, params=None):
+ """
+ :param params:
+ :return:
+ """
+ url = '/service-instances'
+ if params:
+ url += '?%s' % urllib.urlencode(params)
+ return self.get(url)
+
+ def update_service_instance(self, template_id, **kwargs):
+ """
+ :param template_id:
+ :param kwargs:
+ :return:
+ """
+ url = '/service-instance/%s' % str(template_id)
+ put_data = {'service-instance': kwargs}
+ req_put_data = json.dumps(put_data)
+ resp, body = self.put(url, req_put_data)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
diff --git a/tungsten_tempest_plugin/services/contrail/json/subnet_client.py b/tungsten_tempest_plugin/services/contrail/json/subnet_client.py
new file mode 100644
index 0000000..6c36b5a
--- /dev/null
+++ b/tungsten_tempest_plugin/services/contrail/json/subnet_client.py
@@ -0,0 +1,83 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest service class for subnet test cases
+"""
+
+import json
+from six.moves.urllib import parse as urllib
+from tungsten_tempest_plugin.services.contrail.json import base
+
+
+class SubnetClient(base.BaseContrailClient):
+
+ """
+ Service class for subnet client test cases
+ """
+
+ def list_subnets(self, params=None):
+ """
+ :param params:
+ :return:
+ """
+ url = '/subnets'
+ if params:
+ url += '?%s' % urllib.urlencode(params)
+ resp, body = self.get(url)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def create_subnets(self, **kwargs):
+ """
+ :param kwargs:
+ :return:
+ """
+ url = '/subnets'
+ resp, body = self.post(url, json.dumps({'subnet': kwargs}))
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def show_subnet(self, uuid, params=None):
+ """
+ :param uuid:
+ :param params:
+ :return:
+ """
+ url = '/subnet/{0}'.format(uuid)
+ if params:
+ url += '?%s' % urllib.urlencode(params)
+ resp, body = self.get(url)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def update_subnet(self, uuid, **kwargs):
+ """
+ :param uuid:
+ :param kwargs:
+ :return:
+ """
+ url = '/subnet/{0}'.format(uuid)
+ resp, body = self.put(url, json.dumps({'subnet': kwargs}))
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def delete_subnet(self, uuid):
+ """
+ :param uuid:
+ :return:
+ """
+ url = '/subnet/{0}'.format(uuid)
+ return self.delete(url)
diff --git a/tungsten_tempest_plugin/services/contrail/json/virtual_dns_client.py b/tungsten_tempest_plugin/services/contrail/json/virtual_dns_client.py
new file mode 100644
index 0000000..a3cca33
--- /dev/null
+++ b/tungsten_tempest_plugin/services/contrail/json/virtual_dns_client.py
@@ -0,0 +1,128 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest service class for dns test cases
+"""
+
+import json
+from six.moves.urllib import parse as urllib
+from tungsten_tempest_plugin.services.contrail.json import base
+
+
+# noinspection PyPep8Naming
+class VirtualDNSClient(base.BaseContrailClient):
+
+ """
+ Service class for virtual dns test cases
+ """
+
+ def list_virtual_dns(self, params=None):
+ """
+ :param params:
+ :return:
+ """
+ url = '/virtual-DNSs'
+ if params:
+ url += '?%s' % urllib.urlencode(params)
+ return self.get(url)
+
+ def create_virtual_dns(self, **kwargs):
+ """
+ :param kwargs:
+ :return:
+ """
+ url = '/virtual-DNSs'
+ post_body = json.dumps({'virtual-DNS': kwargs})
+ resp, body = self.post(url, post_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def show_virtual_dns(self, dns_id):
+ """
+ :param dns_id:
+ :return:
+ """
+ url = '/virtual-DNS/%s' % dns_id
+ return self.get(url)
+
+ def delete_virtual_dns(self, dns_id):
+ """
+ :param dns_id:
+ :return:
+ """
+ url = '/virtual-DNS/%s' % dns_id
+ return self.delete(url)
+
+ def update_virtual_dns(self, dns_id, **kwargs):
+ """
+ :param dns_id:
+ :param kwargs:
+ :return:
+ """
+ url = '/virtual-DNS/%s' % dns_id
+ post_body = json.dumps({'virtual-DNS': kwargs})
+ resp, body = self.put(url, post_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def list_virtual_dns_records(self, params=None):
+ """
+ :param params:
+ :return:
+ """
+ url = '/virtual-DNS-records'
+ if params:
+ url += '?%s' % urllib.urlencode(params)
+ return self.get(url)
+
+ def create_virtual_dns_records(self, **kwargs):
+ """
+ :param kwargs:
+ :return:
+ """
+ url = '/virtual-DNS-records'
+ post_body = json.dumps({'virtual-DNS-record': kwargs})
+ resp, body = self.post(url, post_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def delete_virtual_dns_record(self, dns_record_id):
+ """
+ :param dns_record_id:
+ :return:
+ """
+ url = 'virtual-DNS-record/%s' % dns_record_id
+ return self.delete(url)
+
+ def show_virtual_dns_record(self, dns_record_id):
+ """
+ :param dns_record_id:
+ :return:
+ """
+ url = '/virtual-DNS-record/%s' % dns_record_id
+ return self.get(url)
+
+ def update_virtual_dns_record(self, dns_record_id, **kwargs):
+ """
+ :param dns_record_id:
+ :param kwargs:
+ :return:
+ """
+ url = '/virtual-DNS-record/%s' % dns_record_id
+ post_body = json.dumps({'virtual-DNS-record': kwargs})
+ resp, body = self.put(url, post_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
diff --git a/tungsten_tempest_plugin/services/contrail/json/virtual_ip_client.py b/tungsten_tempest_plugin/services/contrail/json/virtual_ip_client.py
new file mode 100644
index 0000000..0b3f82f
--- /dev/null
+++ b/tungsten_tempest_plugin/services/contrail/json/virtual_ip_client.py
@@ -0,0 +1,83 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest service class for virtual ip test cases
+"""
+
+import json
+from six.moves.urllib import parse as urllib
+from tungsten_tempest_plugin.services.contrail.json import base
+
+
+class VirtualIPClient(base.BaseContrailClient):
+
+ """
+ Service class for virtual ip test cases
+ """
+
+ def list_virtual_ips(self, params=None):
+ """
+ :param params:
+ :return:
+ """
+ url = '/virtual-ips'
+ if params:
+ url += '?%s' % urllib.urlencode(params)
+ resp, body = self.get(url)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def create_virtual_ips(self, **kwargs):
+ """
+ :param kwargs:
+ :return:
+ """
+ url = '/virtual-ips'
+ resp, body = self.post(url, json.dumps({'virtual-ip': kwargs}))
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def show_virtual_ip(self, uuid, params=None):
+ """
+ :param uuid:
+ :param params:
+ :return:
+ """
+ url = '/virtual-ip/{0}'.format(uuid)
+ if params:
+ url += '?%s' % urllib.urlencode(params)
+ resp, body = self.get(url)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def update_virtual_ip(self, uuid, **kwargs):
+ """
+ :param uuid:
+ :param kwargs:
+ :return:
+ """
+ url = '/virtual-ip/{0}'.format(uuid)
+ resp, body = self.put(url, json.dumps({'virtual-ip': kwargs}))
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def delete_virtual_ip(self, uuid):
+ """
+ :param uuid:
+ :return:
+ """
+ url = '/virtual-ip/{0}'.format(uuid)
+ return self.delete(url)
diff --git a/tungsten_tempest_plugin/services/contrail/json/virtual_network_client.py b/tungsten_tempest_plugin/services/contrail/json/virtual_network_client.py
new file mode 100644
index 0000000..f7fccf6
--- /dev/null
+++ b/tungsten_tempest_plugin/services/contrail/json/virtual_network_client.py
@@ -0,0 +1,75 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest service class for virtual network test cases
+"""
+
+from oslo_serialization import jsonutils as json
+from tungsten_tempest_plugin.services.contrail.json import base
+
+
+class VirtualNetworkClient(base.BaseContrailClient):
+
+ """
+ Service class for virtual n/w test cases
+ """
+
+ def list_virtual_networks(self):
+ """
+ :return:
+ """
+ url = '/virtual-networks'
+ return self.get(url)
+
+ def create_virtual_networks(self, **kwargs):
+ """
+ :param kwargs:
+ :return:
+ """
+ url = '/virtual-networks'
+ post_body = json.dumps({'virtual-network': kwargs})
+ resp, body = self.post(url, post_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def update_virtual_network(self, uuid, **kwargs):
+ """
+ :param uuid:
+ :param kwargs:
+ :return:
+ """
+ url = '/virtual-network/%s' % uuid
+ post_data = {'virtual-network': kwargs}
+ req_post_data = json.dumps(post_data)
+ resp, body = self.put(url, req_post_data)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def delete_virtual_network(self, uuid):
+ """
+ :param uuid:
+ :return:
+ """
+ url = '/virtual-network/%s' % uuid
+ return self.delete(url)
+
+ def show_virtual_network(self, uuid):
+ """
+ :param uuid:
+ :return:
+ """
+ url = '/virtual-network/%s' % uuid
+ return self.get(url)
diff --git a/tungsten_tempest_plugin/services/contrail/json/vm_contrail_client.py b/tungsten_tempest_plugin/services/contrail/json/vm_contrail_client.py
new file mode 100644
index 0000000..a3ff70f
--- /dev/null
+++ b/tungsten_tempest_plugin/services/contrail/json/vm_contrail_client.py
@@ -0,0 +1,78 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest service class for virtual machine test cases
+"""
+
+import json
+from tungsten_tempest_plugin.services.contrail.json import base
+
+
+class VmContrailClient(base.BaseContrailClient):
+
+ """
+ Service class for vm test cases
+ """
+
+ def list_virtual_machine_interfaces(self):
+ """
+ :return:
+ """
+ url = '/virtual-machine-interfaces'
+ resp, body = self.get(url)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def create_vm_interfaces(self, **kwargs):
+ """
+ :param kwargs:
+ :return:
+ """
+ post_body = json.dumps({'virtual-machine-interface': kwargs})
+ url = '/virtual-machine-interfaces'
+ resp, body = self.post(url, post_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def show_virtual_machine_interface(self, instance_id):
+ """
+ :param instance_id:
+ :return:
+ """
+ url = '/virtual-machine-interface/%s' % instance_id
+ resp, body = self.get(url)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
+
+ def delete_vm_interface(self, instance_id):
+ """
+ :param instance_id:
+ :return:
+ """
+ url = '/virtual-machine-interface/%s' % instance_id
+ return self.delete(url)
+
+ def update_vm_interface(self, instance_id, **kwargs):
+ """
+ :param instance_id:
+ :param kwargs:
+ :return:
+ """
+ post_body = json.dumps({'virtual-machine-interface': kwargs})
+ url = '/virtual-machine-interface/%s' % instance_id
+ resp, body = self.put(url, post_body)
+ body = json.loads(body)
+ return base.ResponseBody(resp, body)
diff --git a/tungsten_tempest_plugin/tests/__init__.py b/tungsten_tempest_plugin/tests/__init__.py
new file mode 100644
index 0000000..e69de29
--- /dev/null
+++ b/tungsten_tempest_plugin/tests/__init__.py
diff --git a/tungsten_tempest_plugin/tests/api/__init__.py b/tungsten_tempest_plugin/tests/api/__init__.py
new file mode 100644
index 0000000..e69de29
--- /dev/null
+++ b/tungsten_tempest_plugin/tests/api/__init__.py
diff --git a/tungsten_tempest_plugin/tests/api/contrail/__init__.py b/tungsten_tempest_plugin/tests/api/contrail/__init__.py
new file mode 100644
index 0000000..e69de29
--- /dev/null
+++ b/tungsten_tempest_plugin/tests/api/contrail/__init__.py
diff --git a/tungsten_tempest_plugin/tests/api/contrail/rbac_base.py b/tungsten_tempest_plugin/tests/api/contrail/rbac_base.py
new file mode 100644
index 0000000..dc0b2c7
--- /dev/null
+++ b/tungsten_tempest_plugin/tests/api/contrail/rbac_base.py
@@ -0,0 +1,416 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Base class for contrail testing against RBAC rules
+"""
+
+from oslo_log import log as logging
+
+from tungsten_tempest_plugin.services.contrail.json.access_control_client \
+ import AccessControlClient
+from tungsten_tempest_plugin.services.contrail.json.alarm_client \
+ import AlarmClient
+from tungsten_tempest_plugin.services.contrail.json.alias_ip_client \
+ import AliasIPsClient
+from tungsten_tempest_plugin.services.contrail.json.analytics_node_client \
+ import AnalyticsNodeClient
+from tungsten_tempest_plugin.services.contrail.json.\
+ attachments_client import AttachmentsClient
+from tungsten_tempest_plugin.services.contrail.json.bgp_as_a_service_client \
+ import BGPAsAServiceClient
+from tungsten_tempest_plugin.services.contrail.json.config_client import \
+ ConfigClient
+from tungsten_tempest_plugin.services.contrail.json.database_client import \
+ ContrailDatabaseClient
+from tungsten_tempest_plugin.services.contrail.json.\
+ discovery_service_assignment_client import DiscoveryServiceAssignmentClient
+from tungsten_tempest_plugin.services.contrail.json.domain_client import \
+ DomainClient
+from tungsten_tempest_plugin.services.contrail.json.dsa_rule_client \
+ import DSARuleClient
+from tungsten_tempest_plugin.services.contrail.json.floating_ip_client import \
+ FloatingIpClient
+from tungsten_tempest_plugin.services.contrail.json.forwarding_class_client \
+ import ForwardingClassClient
+from tungsten_tempest_plugin.services.contrail.json.fq_client import \
+ FqnameIdClient
+from tungsten_tempest_plugin.services.contrail.json.instance_ip_client import \
+ InstanceIPClient
+from tungsten_tempest_plugin.services.contrail.json.interface_client import \
+ InterfaceClient
+from tungsten_tempest_plugin.services.contrail.json.\
+ load_balancer_client import LoadBalancerClient
+from tungsten_tempest_plugin.services.contrail.json.namespace_client import \
+ NamespaceClient
+from tungsten_tempest_plugin.services.contrail.json.network_ipams_client \
+ import NetworkIpamsClient
+from tungsten_tempest_plugin.services.contrail.json.\
+ network_policy_client import NetworkPolicyClient
+from tungsten_tempest_plugin.services.contrail.json.port_tuple_client import \
+ PortTupleClient
+from tungsten_tempest_plugin.services.contrail.json.project_client import \
+ ProjectClient
+from tungsten_tempest_plugin.services.contrail.json.qos_client import \
+ QosContrailClient
+from tungsten_tempest_plugin.services.contrail.json.route_client \
+ import RouteClient
+from tungsten_tempest_plugin.services.contrail.json.router_client \
+ import RouterClient
+from tungsten_tempest_plugin.services.contrail.json.routing_client \
+ import RoutingClient
+from tungsten_tempest_plugin.services.contrail.json.\
+ routing_policy_client import RoutingPolicyClient
+from tungsten_tempest_plugin.services.contrail.json.security_group_client \
+ import SecurityGroupClient
+from tungsten_tempest_plugin.services.contrail.json.service_appliances_client \
+ import ServiceAppliancesClient
+from tungsten_tempest_plugin.services.contrail.json.service_client \
+ import ServiceClient
+from tungsten_tempest_plugin.services.contrail.json.subnet_client \
+ import SubnetClient
+from tungsten_tempest_plugin.services.contrail.json.virtual_dns_client import \
+ VirtualDNSClient
+from tungsten_tempest_plugin.services.contrail.json.\
+ virtual_ip_client import VirtualIPClient
+from tungsten_tempest_plugin.services.contrail.json.\
+ virtual_network_client import VirtualNetworkClient
+from tungsten_tempest_plugin.services.contrail.json.vm_contrail_client import \
+ VmContrailClient
+
+from patrole_tempest_plugin import rbac_utils
+
+from tempest import config
+from tempest import test
+
+from tempest.lib import exceptions
+
+CONF = config.CONF
+LOG = logging.getLogger(__name__)
+
+
+class BaseContrailTest(test.BaseTestCase):
+ """Base class for Contrail tests."""
+ credentials = ['primary', 'admin']
+
+ @classmethod
+ def skip_checks(cls):
+ super(BaseContrailTest, cls).skip_checks()
+ if not CONF.service_available.contrail:
+ raise cls.skipException("Contrail support is required")
+ if not CONF.patrole.enable_rbac:
+ raise cls.skipException(
+ "%s skipped as RBAC Flag not enabled" % cls.__name__)
+ if CONF.auth.tempest_roles != ['admin']:
+ raise cls.skipException(
+ "%s skipped because tempest roles is not admin" % cls.__name__)
+
+ @classmethod
+ def setup_credentials(cls):
+ super(BaseContrailTest, cls).setup_credentials()
+
+ @classmethod
+ def setup_clients(cls):
+ super(BaseContrailTest, cls).setup_clients()
+ cls.auth_provider = cls.os_primary.auth_provider
+ cls.admin_client = cls.os_admin.networks_client
+ dscv = CONF.identity.disable_ssl_certificate_validation
+ ca_certs = CONF.identity.ca_certificates_file
+ cls.rbac_utils = rbac_utils.RbacUtils(cls)
+ cls.access_control_client = AccessControlClient(
+ cls.auth_provider,
+ CONF.sdn.catalog_type,
+ CONF.identity.region,
+ CONF.sdn.endpoint_type,
+ disable_ssl_certificate_validation=dscv,
+ ca_certs=ca_certs)
+ cls.alarm_client = AlarmClient(
+ cls.auth_provider,
+ CONF.sdn.catalog_type,
+ CONF.identity.region,
+ CONF.sdn.endpoint_type,
+ disable_ssl_certificate_validation=dscv,
+ ca_certs=ca_certs)
+ cls.vm_client = VmContrailClient(
+ cls.auth_provider,
+ CONF.sdn.catalog_type,
+ CONF.identity.region,
+ CONF.sdn.endpoint_type,
+ disable_ssl_certificate_validation=dscv,
+ ca_certs=ca_certs)
+ cls.dsa_client = DiscoveryServiceAssignmentClient(
+ cls.auth_provider,
+ CONF.sdn.catalog_type,
+ CONF.identity.region,
+ CONF.sdn.endpoint_type,
+ disable_ssl_certificate_validation=dscv,
+ ca_certs=ca_certs)
+ cls.dsa_rule_client = DSARuleClient(
+ cls.auth_provider,
+ CONF.sdn.catalog_type,
+ CONF.identity.region,
+ CONF.sdn.endpoint_type,
+ disable_ssl_certificate_validation=dscv,
+ ca_certs=ca_certs)
+ cls.forwarding_class_client = ForwardingClassClient(
+ cls.auth_provider,
+ CONF.sdn.catalog_type,
+ CONF.identity.region,
+ CONF.sdn.endpoint_type,
+ disable_ssl_certificate_validation=dscv,
+ ca_certs=ca_certs)
+ cls.qos_client = QosContrailClient(
+ cls.auth_provider,
+ CONF.sdn.catalog_type,
+ CONF.identity.region,
+ CONF.sdn.endpoint_type,
+ disable_ssl_certificate_validation=dscv,
+ ca_certs=ca_certs)
+ cls.routing_client = RoutingClient(
+ cls.auth_provider,
+ CONF.sdn.catalog_type,
+ CONF.identity.region,
+ CONF.sdn.endpoint_type,
+ disable_ssl_certificate_validation=dscv,
+ ca_certs=ca_certs)
+ cls.security_group_client = SecurityGroupClient(
+ cls.auth_provider,
+ CONF.sdn.catalog_type,
+ CONF.identity.region,
+ CONF.sdn.endpoint_type,
+ disable_ssl_certificate_validation=dscv,
+ ca_certs=ca_certs)
+ cls.service_appliances_client = ServiceAppliancesClient(
+ cls.auth_provider,
+ CONF.sdn.catalog_type,
+ CONF.identity.region,
+ CONF.sdn.endpoint_type,
+ disable_ssl_certificate_validation=dscv,
+ ca_certs=ca_certs)
+ cls.analytics_node_client = AnalyticsNodeClient(
+ cls.auth_provider,
+ CONF.sdn.catalog_type,
+ CONF.identity.region,
+ CONF.sdn.endpoint_type,
+ disable_ssl_certificate_validation=dscv,
+ ca_certs=ca_certs)
+ cls.vn_client = VirtualNetworkClient(
+ cls.auth_provider,
+ CONF.sdn.catalog_type,
+ CONF.identity.region,
+ CONF.sdn.endpoint_type,
+ disable_ssl_certificate_validation=dscv,
+ ca_certs=ca_certs)
+ cls.db_client = ContrailDatabaseClient(
+ cls.auth_provider,
+ CONF.sdn.catalog_type,
+ CONF.identity.region,
+ CONF.sdn.endpoint_type,
+ disable_ssl_certificate_validation=dscv,
+ ca_certs=ca_certs)
+ cls.fip_client = FloatingIpClient(
+ cls.auth_provider,
+ CONF.sdn.catalog_type,
+ CONF.identity.region,
+ CONF.sdn.endpoint_type,
+ disable_ssl_certificate_validation=dscv,
+ ca_certs=ca_certs)
+ cls.fq_client = FqnameIdClient(
+ cls.auth_provider,
+ CONF.sdn.catalog_type,
+ CONF.identity.region,
+ CONF.sdn.endpoint_type,
+ disable_ssl_certificate_validation=dscv,
+ ca_certs=ca_certs)
+ cls.virtual_ip_client = VirtualIPClient(
+ cls.auth_provider,
+ CONF.sdn.catalog_type,
+ CONF.identity.region,
+ CONF.sdn.endpoint_type,
+ disable_ssl_certificate_validation=dscv,
+ ca_certs=ca_certs)
+ cls.virtual_dns_client = VirtualDNSClient(
+ cls.auth_provider,
+ CONF.sdn.catalog_type,
+ CONF.identity.region,
+ CONF.sdn.endpoint_type,
+ disable_ssl_certificate_validation=dscv,
+ ca_certs=ca_certs)
+ cls.domain_client = DomainClient(
+ cls.auth_provider,
+ CONF.sdn.catalog_type,
+ CONF.identity.region,
+ CONF.sdn.endpoint_type,
+ disable_ssl_certificate_validation=dscv,
+ ca_certs=ca_certs)
+ cls.project_client = ProjectClient(
+ cls.auth_provider,
+ CONF.sdn.catalog_type,
+ CONF.identity.region,
+ CONF.sdn.endpoint_type,
+ disable_ssl_certificate_validation=dscv,
+ ca_certs=ca_certs)
+ cls.port_tuple_client = PortTupleClient(
+ cls.auth_provider,
+ CONF.sdn.catalog_type,
+ CONF.identity.region,
+ CONF.sdn.endpoint_type,
+ disable_ssl_certificate_validation=dscv,
+ ca_certs=ca_certs)
+ cls.network_policy_client = NetworkPolicyClient(
+ cls.auth_provider,
+ CONF.sdn.catalog_type,
+ CONF.identity.region,
+ CONF.sdn.endpoint_type,
+ disable_ssl_certificate_validation=dscv,
+ ca_certs=ca_certs)
+ cls.routing_policy_client = RoutingPolicyClient(
+ cls.auth_provider,
+ CONF.sdn.catalog_type,
+ CONF.identity.region,
+ CONF.sdn.endpoint_type,
+ disable_ssl_certificate_validation=dscv,
+ ca_certs=ca_certs)
+ cls.namespace_client = NamespaceClient(
+ cls.auth_provider,
+ CONF.sdn.catalog_type,
+ CONF.identity.region,
+ CONF.sdn.endpoint_type,
+ disable_ssl_certificate_validation=dscv,
+ ca_certs=ca_certs)
+ cls.network_ipams_client = NetworkIpamsClient(
+ cls.auth_provider,
+ CONF.sdn.catalog_type,
+ CONF.identity.region,
+ CONF.sdn.endpoint_type,
+ disable_ssl_certificate_validation=dscv,
+ ca_certs=ca_certs)
+ cls.bgp_as_a_service_client = BGPAsAServiceClient(
+ cls.auth_provider,
+ CONF.sdn.catalog_type,
+ CONF.identity.region,
+ CONF.sdn.endpoint_type,
+ disable_ssl_certificate_validation=dscv,
+ ca_certs=ca_certs)
+ cls.iip_client = InstanceIPClient(
+ cls.auth_provider,
+ CONF.sdn.catalog_type,
+ CONF.identity.region,
+ CONF.sdn.endpoint_type,
+ disable_ssl_certificate_validation=dscv,
+ ca_certs=ca_certs)
+ cls.subnet_client = SubnetClient(
+ cls.auth_provider,
+ CONF.sdn.catalog_type,
+ CONF.identity.region,
+ CONF.sdn.endpoint_type,
+ disable_ssl_certificate_validation=dscv,
+ ca_certs=ca_certs)
+ cls.load_balancer_client = LoadBalancerClient(
+ cls.auth_provider,
+ CONF.sdn.catalog_type,
+ CONF.identity.region,
+ CONF.sdn.endpoint_type,
+ disable_ssl_certificate_validation=dscv,
+ ca_certs=ca_certs)
+ cls.route_client = RouteClient(
+ cls.auth_provider,
+ CONF.sdn.catalog_type,
+ CONF.identity.region,
+ CONF.sdn.endpoint_type,
+ disable_ssl_certificate_validation=dscv,
+ ca_certs=ca_certs)
+ cls.interface_client = InterfaceClient(
+ cls.auth_provider,
+ CONF.sdn.catalog_type,
+ CONF.identity.region,
+ CONF.sdn.endpoint_type,
+ disable_ssl_certificate_validation=dscv,
+ ca_certs=ca_certs)
+ cls.router_client = RouterClient(
+ cls.auth_provider,
+ CONF.sdn.catalog_type,
+ CONF.identity.region,
+ CONF.sdn.endpoint_type,
+ disable_ssl_certificate_validation=dscv,
+ ca_certs=ca_certs)
+ cls.service_client = ServiceClient(
+ cls.auth_provider,
+ CONF.sdn.catalog_type,
+ CONF.identity.region,
+ CONF.sdn.endpoint_type,
+ disable_ssl_certificate_validation=dscv,
+ ca_certs=ca_certs)
+ cls.attachments_client = AttachmentsClient(
+ cls.auth_provider,
+ CONF.sdn.catalog_type,
+ CONF.identity.region,
+ CONF.sdn.endpoint_type,
+ disable_ssl_certificate_validation=dscv,
+ ca_certs=ca_certs)
+ cls.config_client = ConfigClient(
+ cls.auth_provider,
+ CONF.sdn.catalog_type,
+ CONF.identity.region,
+ CONF.sdn.endpoint_type,
+ disable_ssl_certificate_validation=dscv,
+ ca_certs=ca_certs)
+ cls.alias_ip_client = AliasIPsClient(
+ cls.auth_provider,
+ CONF.sdn.catalog_type,
+ CONF.identity.region,
+ CONF.sdn.endpoint_type,
+ disable_ssl_certificate_validation=dscv,
+ ca_certs=ca_certs)
+
+ @classmethod
+ def resource_setup(cls):
+ cls.tenant_name = cls.os_primary.credentials.tenant_name
+ if CONF.auth.allow_tenant_isolation:
+ # Create a contrail project for tests
+ post_body = {
+ 'parent_type': 'domain',
+ 'fq_name': ['default-domain', cls.tenant_name]
+ }
+ resp_body = cls.project_client.create_projects(**post_body)
+ cls.project_uuid = resp_body['project']['uuid']
+
+ @classmethod
+ def resource_cleanup(cls):
+ if CONF.auth.allow_tenant_isolation:
+ cls._try_delete_resource(cls.project_client.delete_project,
+ cls.project_uuid)
+
+ super(BaseContrailTest, cls).resource_cleanup()
+
+ @classmethod
+ def _try_delete_resource(cls, delete_callable, *args, **kwargs):
+ """Cleanup resources in case of test-failure
+
+ Some resources are explicitly deleted by the test.
+ If the test failed to delete a resource, this method will execute
+ the appropriate delete methods. Otherwise, the method ignores NotFound
+ exceptions thrown for resources that were correctly deleted by the
+ test.
+
+ :param delete_callable: delete method
+ :param args: arguments for delete method
+ :param kwargs: keyword arguments for delete method
+ """
+ try:
+ delete_callable(*args, **kwargs)
+ # if resource is not found, this means it was deleted in the test
+ except exceptions.NotFound:
+ pass
diff --git a/tungsten_tempest_plugin/tests/api/contrail/test_access_control.py b/tungsten_tempest_plugin/tests/api/contrail/test_access_control.py
new file mode 100644
index 0000000..4425cea
--- /dev/null
+++ b/tungsten_tempest_plugin/tests/api/contrail/test_access_control.py
@@ -0,0 +1,204 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest test-case to test Access Control using RBAC roles
+"""
+
+from tungsten_tempest_plugin.tests.api.contrail import rbac_base
+
+from patrole_tempest_plugin import rbac_rule_validation
+
+from tempest import config
+from tempest.lib.common.utils import data_utils
+from tempest.lib.decorators import idempotent_id
+
+CONF = config.CONF
+
+
+class AccessControlTest(rbac_base.BaseContrailTest):
+
+ """
+ Test class to test Access Control objects using RBAC roles
+ """
+
+ def _create_api_access_lists(self):
+ api_list_name = data_utils.rand_name('test-api-list')
+ api_list_fq_name = ['default-domain', self.tenant_name, api_list_name]
+ new_api_list = self.access_control_client.create_api_access_lists(
+ fq_name=api_list_fq_name,
+ parent_type="project")['api-access-list']
+
+ self.addCleanup(self._try_delete_resource,
+ self.access_control_client.delete_api_access_list,
+ new_api_list['uuid'])
+ return new_api_list
+
+ def _create_security_groups(self):
+ name = data_utils.rand_name('securitygroup')
+ domain_name = 'default-domain'
+ fq_name = ['default-domain', self.tenant_name, name]
+ parent_type = 'project'
+ sec_grp = self.security_group_client.create_security_groups(
+ domain_name=domain_name,
+ fq_name=fq_name,
+ display_name=name,
+ parent_type=parent_type)['security-group']
+ self.addCleanup(self._try_delete_resource,
+ self._delete_security_group,
+ sec_grp['uuid'])
+ return sec_grp
+
+ def _delete_security_group(self, sec_grp_id):
+ return self.security_group_client.delete_security_group(sec_grp_id)
+
+ def _create_access_control_lists(self, sec_group_name):
+ ctrl_list_name = data_utils.rand_name('test-set')
+ ctrl_list_fq_name = ['default-domain', self.tenant_name,
+ sec_group_name, ctrl_list_name]
+ new_ctrl_list = self.access_control_client.create_access_control_lists(
+ fq_name=ctrl_list_fq_name,
+ parent_type="security-group")['access-control-list']
+
+ self.addCleanup(self._try_delete_resource,
+ self.access_control_client.delete_access_control_list,
+ new_ctrl_list['uuid'])
+ return new_ctrl_list
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="list_api_access_lists")
+ @idempotent_id('2bfde8fd-36fe-4e69-ba59-6f2db8941e7d')
+ def test_list_api_access_lists(self):
+ """
+ test method for list api access list
+ """
+ with self.rbac_utils.override_role(self):
+ self.access_control_client.list_api_access_lists()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="create_api_access_lists")
+ @idempotent_id('b2b5f50c-07d8-4d79-b9a4-78187ad97353')
+ def test_create_api_access_lists(self):
+ """
+ test method for create api access list
+ """
+ with self.rbac_utils.override_role(self):
+ self._create_api_access_lists()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="show_api_access_list")
+ @idempotent_id('b82e8e6b-83b5-424d-9652-ef6a34067f4f')
+ def test_show_api_access_list(self):
+ """
+ test method for show api access list
+ """
+ new_api_list = self._create_api_access_lists()
+ with self.rbac_utils.override_role(self):
+ self.access_control_client.show_api_access_list(
+ new_api_list['uuid'])
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="update_api_access_list")
+ @idempotent_id('edc88825-1e2e-47ff-b7b4-f68d6310fbad')
+ def test_update_api_access_list(self):
+ """
+ test method for update api access list
+ """
+ new_api_list = self._create_api_access_lists()
+ update_name = data_utils.rand_name('test')
+ with self.rbac_utils.override_role(self):
+ self.access_control_client.update_api_access_list(
+ new_api_list['uuid'],
+ display_name=update_name)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="delete_api_access_list")
+ @idempotent_id('f27d9044-95f2-4733-81ed-df9340dbd421')
+ def test_delete_api_access_list(self):
+ """
+ test method for delete api access list
+ """
+ new_api_list = self._create_api_access_lists()
+ with self.rbac_utils.override_role(self):
+ self.access_control_client.delete_api_access_list(
+ new_api_list['uuid'])
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="list_access_control_lists")
+ @idempotent_id('c56a1338-a9d1-4286-8aeb-3a0d60d93037')
+ def test_list_access_control_lists(self):
+ """
+ test method for list access control list
+ """
+ with self.rbac_utils.override_role(self):
+ self.access_control_client.list_access_control_lists()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="create_access_control_lists")
+ @idempotent_id('9f225d2b-5376-42f5-97aa-cf63be47fa19')
+ def test_create_access_control(self):
+ """
+ test method for create access control list
+ """
+ # Create Security Group
+ sec_group = self._create_security_groups()
+ with self.rbac_utils.override_role(self):
+ self._create_access_control_lists(sec_group['name'])
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="show_access_control_list")
+ @idempotent_id('f0ed882b-f3de-48b7-884a-637ee0b7d6b6')
+ def test_show_access_control_list(self):
+ """
+ test method for show access control list
+ """
+ # Create Security Group
+ sec_group = self._create_security_groups()
+ new_ctrl_list = self._create_access_control_lists(
+ sec_group['name'])
+ with self.rbac_utils.override_role(self):
+ self.access_control_client.show_access_control_list(
+ new_ctrl_list['uuid'])
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="update_access_control_list")
+ @idempotent_id('9a4b3133-dd07-4a1a-b282-f7770c372fb8')
+ def test_update_access_control_list(self):
+ """
+ test method for update access control list
+ """
+ sec_group = self._create_security_groups()
+ new_ctrl_list = self._create_access_control_lists(
+ sec_group['name'])
+ update_name = data_utils.rand_name('test')
+ with self.rbac_utils.override_role(self):
+ self.access_control_client.update_access_control_list(
+ new_ctrl_list['uuid'],
+ display_name=update_name)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="delete_access_control_list")
+ @idempotent_id('36a8ace1-71ca-4c7c-8667-d8387d6f964a')
+ def test_delete_access_control_list(self):
+ """
+ test method for delete access control list
+ """
+ # Create Security Group
+ sec_group = self._create_security_groups()
+ new_ctrl_list = self._create_access_control_lists(
+ sec_group['name'])
+ with self.rbac_utils.override_role(self):
+ self.access_control_client.delete_access_control_list(
+ new_ctrl_list['uuid'])
diff --git a/tungsten_tempest_plugin/tests/api/contrail/test_alarm.py b/tungsten_tempest_plugin/tests/api/contrail/test_alarm.py
new file mode 100644
index 0000000..3996b9f
--- /dev/null
+++ b/tungsten_tempest_plugin/tests/api/contrail/test_alarm.py
@@ -0,0 +1,150 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest test-case to test Alarms object using RBAC roles
+"""
+
+from oslo_log import log as logging
+
+from tungsten_tempest_plugin.tests.api.contrail import rbac_base
+
+from patrole_tempest_plugin import rbac_rule_validation
+
+from tempest import config
+
+from tempest.lib.common.utils import data_utils
+from tempest.lib.decorators import idempotent_id
+
+CONF = config.CONF
+LOG = logging.getLogger(__name__)
+
+
+class AlarmContrailTest(rbac_base.BaseContrailTest):
+
+ """
+ Test class to test Alarm objects using RBAC roles
+ """
+
+ def _create_global_system_config(self):
+ config_name = data_utils.rand_name('test-config')
+ parent_type = 'config-root'
+ config_fq_name = [config_name]
+ new_config = \
+ self.config_client.create_global_system_configs(
+ parent_type=parent_type,
+ display_name=config_name,
+ fq_name=config_fq_name)['global-system-config']
+ self.addCleanup(self._try_delete_resource,
+ (self.config_client.
+ delete_global_system_config),
+ new_config['uuid'])
+ return new_config
+
+ def _create_alarm(self, global_system_config):
+ post_body = {
+ 'fq_name': [global_system_config,
+ data_utils.rand_name('alarm')],
+ 'alarm_severity': 1,
+ 'parent_type': 'global-system-config',
+ 'uve_keys': {
+ 'uve_key': ['analytics_node']
+ },
+ 'alarm_rules': {
+ 'or_list': [{
+ 'and_list': [{
+ 'operation': '!=',
+ 'operand1': 'NodeStatus.process_info.process_state',
+ 'operand2': {
+ 'json_value': '"PROCESS_STATE_RUNNING"'
+ }
+ }]
+ }]
+ }
+ }
+ resp_body = self.alarm_client.create_alarms(
+ **post_body)
+ alarm_uuid = resp_body['alarm']['uuid']
+ self.addCleanup(self._try_delete_resource,
+ self.alarm_client.delete_alarm,
+ alarm_uuid)
+ return alarm_uuid
+
+ def _update_alarm(self, alarm_uuid):
+ put_body = {
+ 'alarm_severity': 2
+ }
+ self.alarm_client.update_alarm(alarm_uuid, **put_body)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="list_alarms")
+ @idempotent_id('dc7d19dd-dd5e-4ec8-bf0c-c6d9d83a60a8')
+ def test_list_alarms(self):
+ """
+ test method for list alarms
+ """
+ with self.rbac_utils.override_role(self):
+ self.alarm_client.list_alarms()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="create_alarms")
+ @idempotent_id('7fe55d0c-e54a-4bb7-95a6-9c53f9e9c4bf')
+ def test_create_alarms(self):
+ """
+ test method for create alarms
+ """
+ # Create global system config
+ global_system_config = self._create_global_system_config()['name']
+ with self.rbac_utils.override_role(self):
+ self._create_alarm(global_system_config)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="show_alarm")
+ @idempotent_id('ab0ccbe4-7bfe-4176-890a-d438ee04290d')
+ def test_show_alarm(self):
+ """
+ test method for show alarms
+ """
+ # Create global system config
+ global_system_config = self._create_global_system_config()['name']
+ alarm_uuid = self._create_alarm(global_system_config)
+ with self.rbac_utils.override_role(self):
+ self.alarm_client.show_alarm(alarm_uuid)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="update_alarm")
+ @idempotent_id('ab331cca-ee53-4106-9b30-7319bfb1bea7')
+ def test_update_alarm(self):
+ """
+ test method for update alarms
+ """
+ # Create global system config
+ global_system_config = self._create_global_system_config()['name']
+ alarm_uuid = self._create_alarm(global_system_config)
+ with self.rbac_utils.override_role(self):
+ self._update_alarm(alarm_uuid)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="delete_alarm")
+ @idempotent_id('84fadb14-77c0-4f21-b5b2-1da7a2fd27e6')
+ def test_delete_alarm(self):
+ """
+ test method for delete alarms
+ """
+ # Create global system config
+ global_system_config = self._create_global_system_config()['name']
+ alarm_uuid = self._create_alarm(global_system_config)
+ with self.rbac_utils.override_role(self):
+ self.alarm_client.delete_alarm(alarm_uuid)
diff --git a/tungsten_tempest_plugin/tests/api/contrail/test_alias_ip.py b/tungsten_tempest_plugin/tests/api/contrail/test_alias_ip.py
new file mode 100644
index 0000000..6db7ad9
--- /dev/null
+++ b/tungsten_tempest_plugin/tests/api/contrail/test_alias_ip.py
@@ -0,0 +1,235 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest test-case to test Alias IP and IP pools objects using RBAC roles
+"""
+
+from tungsten_tempest_plugin.tests.api.contrail import rbac_base
+
+from patrole_tempest_plugin import rbac_rule_validation
+
+from tempest import config
+from tempest.lib.common.utils import data_utils
+from tempest.lib.decorators import idempotent_id
+
+CONF = config.CONF
+
+
+class AliasIPsTest(rbac_base.BaseContrailTest):
+ """
+ Test class to test Alias IP and IP pools objects using RBAC roles
+ """
+
+ @classmethod
+ def resource_setup(cls):
+ super(AliasIPsTest, cls).resource_setup()
+ # Create project
+ project_name = data_utils.rand_name('test-project')
+ project_fq_name = ['default-domain', project_name]
+ cls.project = cls.project_client.create_projects(
+ parent_type='domain',
+ fq_name=project_fq_name)['project']
+
+ # Create network ipam
+ ipam_name = data_utils.rand_name('test-ipam')
+ ipam_fq_name = ['default-domain', cls.project['name'], ipam_name]
+ subnet_info = [{'subnet': {'ip_prefix': '2.2.3.0',
+ 'ip_prefix_len': 24}}]
+ cls.ipam = cls.network_ipams_client.create_network_ipams(
+ parent_type='project',
+ fq_name=ipam_fq_name)['network-ipam']
+
+ # Create network
+ net_name = data_utils.rand_name('test-net')
+ net_fq_name = ['default-domain', cls.project['name'], net_name]
+ net_ipam_refs = [
+ {
+ 'to': cls.ipam['fq_name'],
+ 'href': cls.ipam['href'],
+ 'uuid': cls.ipam['uuid'],
+ 'attr': {
+ 'ipam_subnets': subnet_info
+ }
+ }
+ ]
+ cls.network = cls.vn_client.create_virtual_networks(
+ parent_type='project',
+ fq_name=net_fq_name,
+ network_ipam_refs=net_ipam_refs)['virtual-network']
+
+ @classmethod
+ def resource_cleanup(cls):
+ cls._try_delete_resource(cls.vn_client.delete_virtual_network,
+ cls.network['uuid'])
+ cls._try_delete_resource(cls.network_ipams_client.delete_network_ipam,
+ cls.ipam['uuid'])
+ cls._try_delete_resource(cls.project_client.delete_project,
+ cls.project['uuid'])
+ super(AliasIPsTest, cls).resource_cleanup()
+
+ def _create_alias_ip_pools(self):
+ alias_ip_pool_name = data_utils.rand_name('test-alias-ip-pool')
+ alias_ip_pool_fq_name = ['default-domain', self.project['name'],
+ self.network['name'], alias_ip_pool_name]
+ new_alias_ip_pool = self.alias_ip_client.create_alias_ip_pools(
+ fq_name=alias_ip_pool_fq_name,
+ parent_type='virtual-network')['alias-ip-pool']
+
+ self.addCleanup(self._try_delete_resource,
+ self.alias_ip_client.delete_alias_ip_pool,
+ new_alias_ip_pool['uuid'])
+ return new_alias_ip_pool
+
+ def _create_alias_ips(self, alias_ip_pool, address):
+ alias_ip_name = data_utils.rand_name('test-alias-ip')
+ alias_ip_fq_name = alias_ip_pool['fq_name']
+ alias_ip_fq_name.append(alias_ip_name)
+ alias_ip_project_ref = [
+ {
+ 'to': self.project['fq_name'],
+ 'href': self.project['href'],
+ 'uuid': self.project['uuid'],
+ }
+ ]
+ new_alias_ip = self.alias_ip_client.create_alias_ips(
+ fq_name=alias_ip_fq_name,
+ parent_type='alias-ip-pool',
+ project_refs=alias_ip_project_ref,
+ alias_ip_address=address)['alias-ip']
+ self.addCleanup(self._try_delete_resource,
+ self.alias_ip_client.delete_alias_ip,
+ new_alias_ip['uuid'])
+ return new_alias_ip
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="list_alias_ips")
+ @idempotent_id('899d6824-0755-41ef-adef-03eb1858bcb0')
+ def test_list_alias_ips(self):
+ """
+ test method for list alias IP
+ """
+ with self.rbac_utils.override_role(self):
+ self.alias_ip_client.list_alias_ips()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="create_alias_ips")
+ @idempotent_id('bc9aae29-22a8-4eed-a31f-c0ded300e3a3')
+ def test_create_alias_ips(self):
+ """
+ test method for create alias IP
+ """
+ new_alias_ip_pool = self._create_alias_ip_pools()
+ with self.rbac_utils.override_role(self):
+ self._create_alias_ips(new_alias_ip_pool, '2.2.3.1')
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="show_alias_ip")
+ @idempotent_id('d20318b1-c204-44e7-a44c-66f6a1fbe7a0')
+ def test_show_alias_ip(self):
+ """
+ test method for show alias IP
+ """
+ new_alias_ip_pool = self._create_alias_ip_pools()
+ new_alias_ip = self._create_alias_ips(new_alias_ip_pool, '2.2.3.2')
+ with self.rbac_utils.override_role(self):
+ self.alias_ip_client.show_alias_ip(
+ new_alias_ip['uuid'])
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="update_alias_ip")
+ @idempotent_id('c237b18f-d899-4b80-8e9b-068244a24612')
+ def test_update_alias_ip(self):
+ """
+ test method for update alias IP
+ """
+ new_alias_ip_pool = self._create_alias_ip_pools()
+ new_alias_ip = self._create_alias_ips(new_alias_ip_pool, '2.2.3.3')
+ update_name = data_utils.rand_name('test')
+ with self.rbac_utils.override_role(self):
+ self.alias_ip_client.update_alias_ip(
+ new_alias_ip['uuid'],
+ display_name=update_name)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="delete_alias_ip")
+ @idempotent_id('456c641c-9066-4125-8dec-d1529ad8f1ba')
+ def test_delete_alias_ip(self):
+ """
+ test method for delete alias IP
+ """
+ new_alias_ip_pool = self._create_alias_ip_pools()
+ new_alias_ip = self._create_alias_ips(new_alias_ip_pool, '2.2.3.4')
+ with self.rbac_utils.override_role(self):
+ self.alias_ip_client.delete_alias_ip(
+ new_alias_ip['uuid'])
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="list_alias_ip_pools")
+ @idempotent_id('ffe85f35-589a-4b90-a1d3-6aed92a85954')
+ def test_list_alias_ip_pools(self):
+ """
+ est method for list alias IP pools
+ """
+ with self.rbac_utils.override_role(self):
+ self.alias_ip_client.list_alias_ip_pools()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="create_alias_ip_pools")
+ @idempotent_id('83abd2c0-d46a-4337-87d0-31cdb86e4226')
+ def test_create_alias_ip_pools(self):
+ """
+ test method for create alias IP pool
+ """
+ with self.rbac_utils.override_role(self):
+ self._create_alias_ip_pools()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="show_alias_ip_pool")
+ @idempotent_id('a1cbe111-ccba-4fa4-ba59-7d1ee08a15db')
+ def test_show_alias_ip_pool(self):
+ """
+ test method for show alias IP pool
+ """
+ new_alias_ip_pool = self._create_alias_ip_pools()
+ with self.rbac_utils.override_role(self):
+ self.alias_ip_client.show_alias_ip_pool(
+ new_alias_ip_pool['uuid'])
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="update_alias_ip_pool")
+ @idempotent_id('7f3448d7-22f1-4808-b3eb-15eeb3f079aa')
+ def test_update_alias_ip_pool(self):
+ """
+ test method for update alias IP pool
+ """
+ new_alias_ip_pool = self._create_alias_ip_pools()
+ update_name = data_utils.rand_name('test')
+ with self.rbac_utils.override_role(self):
+ self.alias_ip_client.update_alias_ip_pool(
+ new_alias_ip_pool['uuid'],
+ display_name=update_name)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="delete_alias_ip_pool")
+ @idempotent_id('f59ea4fb-d10f-40c8-a8fa-dcd948ca89c8')
+ def test_delete_alias_ip_pool(self):
+ """
+ test method for delete alias IP pool
+ """
+ new_alias_ip_pool = self._create_alias_ip_pools()
+ with self.rbac_utils.override_role(self):
+ self.alias_ip_client.delete_alias_ip_pool(
+ new_alias_ip_pool['uuid'])
diff --git a/tungsten_tempest_plugin/tests/api/contrail/test_analytics_node.py b/tungsten_tempest_plugin/tests/api/contrail/test_analytics_node.py
new file mode 100644
index 0000000..96090ff
--- /dev/null
+++ b/tungsten_tempest_plugin/tests/api/contrail/test_analytics_node.py
@@ -0,0 +1,129 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest test-case to test analytics node objects using RBAC roles
+"""
+
+from oslo_log import log as logging
+
+from tungsten_tempest_plugin.tests.api.contrail import rbac_base
+
+from patrole_tempest_plugin import rbac_rule_validation
+
+from tempest import config
+from tempest.lib.common.utils import data_utils
+from tempest.lib.decorators import idempotent_id
+
+CONF = config.CONF
+LOG = logging.getLogger(__name__)
+
+
+class ContrailAnalyticsNodeTest(rbac_base.BaseContrailTest):
+
+ """
+ Test class to test analytics node objects using RBAC roles
+ """
+
+ def _create_global_system_config(self):
+ config_name = data_utils.rand_name('test-config')
+ parent_type = 'config-root'
+ config_fq_name = [config_name]
+ new_config = \
+ self.config_client.create_global_system_configs(
+ parent_type=parent_type,
+ display_name=config_name,
+ fq_name=config_fq_name)['global-system-config']
+ self.addCleanup(self._try_delete_resource,
+ (self.config_client.
+ delete_global_system_config),
+ new_config['uuid'])
+ return new_config
+
+ def _create_analytics_node(self, global_system_config):
+ node_name = data_utils.rand_name('analytics-node')
+ post_data = {
+ 'fq_name': [global_system_config, node_name],
+ 'parent_type': 'global-system-config'
+ }
+ new_node = self.analytics_node_client.create_analytics_nodes(
+ **post_data)['analytics-node']
+ self.addCleanup(self._try_delete_resource,
+ self.analytics_node_client.delete_analytics_node,
+ new_node['uuid'])
+ return new_node
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="list_analytics_nodes")
+ @idempotent_id('d3002e37-4b42-446d-b144-1b53f0dadfd3')
+ def test_list_analytics_nodes(self):
+ """
+ test method for list analytics nodes
+ """
+ with self.rbac_utils.override_role(self):
+ self.analytics_node_client.list_analytics_nodes()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="show_analytics_node")
+ @idempotent_id('b51043fd-77ba-4312-b96f-569ed5153338')
+ def test_show_analytics_node(self):
+ """
+ test method for show analytics nodes
+ """
+ # create global system config
+ global_system_config = self._create_global_system_config()['name']
+ new_node = self._create_analytics_node(global_system_config)
+ with self.rbac_utils.override_role(self):
+ self.analytics_node_client.show_analytics_node(new_node['uuid'])
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="create_analytics_nodes")
+ @idempotent_id('c57482c9-fcb4-4f41-95b0-7f0ffeee3dc3')
+ def test_create_analytics_nodes(self):
+ """
+ test method for create analytics nodes
+ """
+ # create global system config
+ global_system_config = self._create_global_system_config()['name']
+ with self.rbac_utils.override_role(self):
+ self._create_analytics_node(global_system_config)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="update_analytics_node")
+ @idempotent_id('ff50a2df-6283-409e-ab03-c13b63acc8a0')
+ def test_update_analytics_node(self):
+ """
+ test method for update analytics nodes
+ """
+ # create global system config
+ global_system_config = self._create_global_system_config()['name']
+ new_node = self._create_analytics_node(global_system_config)
+ update_name = data_utils.rand_name('updated_node')
+ with self.rbac_utils.override_role(self):
+ self.analytics_node_client.update_analytics_node(
+ new_node['uuid'], display_name=update_name)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="delete_analytics_node")
+ @idempotent_id('972f997a-c89f-4227-8ae9-5a2335ec0b0a')
+ def test_delete_analytics_node(self):
+ """
+ test method for delete analytics nodes
+ """
+ # create global system config
+ global_system_config = self._create_global_system_config()['name']
+ new_node = self._create_analytics_node(global_system_config)
+ with self.rbac_utils.override_role(self):
+ self.analytics_node_client.delete_analytics_node(new_node['uuid'])
diff --git a/tungsten_tempest_plugin/tests/api/contrail/test_attachments_client.py b/tungsten_tempest_plugin/tests/api/contrail/test_attachments_client.py
new file mode 100644
index 0000000..ef10c00
--- /dev/null
+++ b/tungsten_tempest_plugin/tests/api/contrail/test_attachments_client.py
@@ -0,0 +1,178 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest test-case to test attachment clients objects using RBAC roles
+"""
+
+
+from tungsten_tempest_plugin.tests.api.contrail import rbac_base
+
+from patrole_tempest_plugin import rbac_rule_validation
+
+from tempest import config
+from tempest.lib.common.utils import data_utils
+from tempest.lib.decorators import idempotent_id
+
+CONF = config.CONF
+
+
+class AttachmentsClientTest(rbac_base.BaseContrailTest):
+
+ """
+ Test class to test attachment client objects using RBAC roles
+ """
+
+ def _create_provider_attachments(self):
+ provider_name = data_utils.rand_name('test-provider-attachment')
+ fq_name = [provider_name]
+ post_body = {'display_name': provider_name, 'fq_name': fq_name}
+ new_provider = \
+ self.attachments_client.create_provider_attachments(
+ **post_body)['provider-attachment']
+ self.addCleanup(self._try_delete_resource,
+ (self.attachments_client.
+ delete_provider_attachment),
+ new_provider['uuid'])
+ return new_provider
+
+ def _create_customer_attachments(self):
+ customer_name = data_utils.rand_name('test-customer-attachment')
+ customer_fq_name = [customer_name]
+ new_customer = \
+ self.attachments_client.create_customer_attachments(
+ display_name=customer_name,
+ fq_name=customer_fq_name)['customer-attachment']
+ self.addCleanup(self._try_delete_resource,
+ (self.attachments_client.
+ delete_customer_attachment),
+ new_customer['uuid'])
+ return new_customer
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="list_provider_attachments")
+ @idempotent_id('961dbf54-ae4f-42e8-9d27-69fa7df39013')
+ def test_list_provider_attachments(self):
+ """
+ test method for list provider attachment objects
+ """
+ with self.rbac_utils.override_role(self):
+ self.attachments_client.list_provider_attachments()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="create_provider_attachments")
+ @idempotent_id('73ad032e-3e81-4dcc-be55-1987484207cd')
+ def test_create_providerattach(self):
+ """
+ test method for create provider attachment objects
+ """
+ with self.rbac_utils.override_role(self):
+ self._create_provider_attachments()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="show_provider_attachment")
+ @idempotent_id('7b5278bc-dd79-495a-9f74-448c04f52bd2')
+ def test_show_provider_attachment(self):
+ """
+ test method for delete provider attachment objects
+ """
+ new_provider = self._create_provider_attachments()
+ with self.rbac_utils.override_role(self):
+ self.attachments_client.show_provider_attachment(
+ new_provider['uuid'])
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="update_provider_attachment")
+ @idempotent_id('3516ff99-eddf-4932-afa4-433a43a0e5ac')
+ def test_update_provider_attachment(self):
+ """
+ test method for update provider attachment objects
+ """
+ new_provider = self._create_provider_attachments()
+ update_name = data_utils.rand_name('test')
+ with self.rbac_utils.override_role(self):
+ self.attachments_client.update_provider_attachment(
+ new_provider['uuid'],
+ display_name=update_name)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="delete_provider_attachment")
+ @idempotent_id('234d5505-2abf-418b-b43b-ea6f5a724fd3')
+ def test_delete_provider_attachment(self):
+ """
+ test method for delete provider attachment objects
+ """
+ new_provider = self._create_provider_attachments()
+ with self.rbac_utils.override_role(self):
+ self.attachments_client.delete_provider_attachment(
+ new_provider['uuid'])
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="list_customer_attachments")
+ @idempotent_id('3eca8fd8-ec3c-4a0e-8f62-b15d28796b7f')
+ def test_list_customer_attachments(self):
+ """
+ test method for list customer attachment objects
+ """
+ with self.rbac_utils.override_role(self):
+ self.attachments_client.list_customer_attachments()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="create_customer_attachments")
+ @idempotent_id('53f93053-554c-4202-b763-0230d9a0553a')
+ def test_create_customerattachments(self):
+ """
+ test method for create customer attachment objects
+ """
+ with self.rbac_utils.override_role(self):
+ self._create_customer_attachments()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="show_customer_attachment")
+ @idempotent_id('c6671540-695c-4cba-bcee-4a5d1cddd412')
+ def test_show_customer_attachment(self):
+ """
+ test method for show customer attachment objects
+ """
+ new_customer = self._create_customer_attachments()
+ with self.rbac_utils.override_role(self):
+ self.attachments_client.show_customer_attachment(
+ new_customer['uuid'])
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="update_customer_attachment")
+ @idempotent_id('50419cca-dd03-4d02-9c06-88446647fcba')
+ def test_update_customer_attachment(self):
+ """
+ test method for update customer attachment objects
+ """
+ new_customer = self._create_customer_attachments()
+ update_name = data_utils.rand_name('test')
+ with self.rbac_utils.override_role(self):
+ self.attachments_client.update_customer_attachment(
+ new_customer['uuid'],
+ display_name=update_name)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="delete_customer_attachment")
+ @idempotent_id('5385c275-8e86-4739-9cb6-d1e0ed522807')
+ def test_delete_customer_attachment(self):
+ """
+ test method for delete customer attachment objects
+ """
+ new_customer = self._create_customer_attachments()
+ with self.rbac_utils.override_role(self):
+ self.attachments_client.delete_customer_attachment(
+ new_customer['uuid'])
diff --git a/tungsten_tempest_plugin/tests/api/contrail/test_bgp_as_a_service.py b/tungsten_tempest_plugin/tests/api/contrail/test_bgp_as_a_service.py
new file mode 100644
index 0000000..723dce8
--- /dev/null
+++ b/tungsten_tempest_plugin/tests/api/contrail/test_bgp_as_a_service.py
@@ -0,0 +1,103 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest test-case to test BGP as a Service objects using RBAC roles
+"""
+
+from tungsten_tempest_plugin.tests.api.contrail import rbac_base
+
+from patrole_tempest_plugin import rbac_rule_validation
+
+from tempest import config
+from tempest.lib.common.utils import data_utils
+from tempest.lib.decorators import idempotent_id
+
+CONF = config.CONF
+
+
+class BGPAsAServicesTest(rbac_base.BaseContrailTest):
+
+ """
+ Test class to test BGP as a Service objects using RBAC roles
+ """
+
+ def _create_bgp_as_a_services(self):
+ bgp_name = data_utils.rand_name('test-bgp')
+ bgp_fq_name = ['default-domain', self.tenant_name, bgp_name]
+ new_bgp = self.bgp_as_a_service_client.create_bgp_as_a_services(
+ parent_type='project',
+ fq_name=bgp_fq_name)['bgp-as-a-service']
+ self.addCleanup(self._try_delete_resource,
+ self.bgp_as_a_service_client.delete_bgp_as_a_service,
+ new_bgp['uuid'])
+ return new_bgp
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="list_bgp_as_a_services")
+ @idempotent_id('d3153cd0-379e-4e62-9780-ef237e567fc5')
+ def test_list_bgp_as_a_services(self):
+ """
+ test method for list bgp as a service objects
+ """
+ with self.rbac_utils.override_role(self):
+ self.bgp_as_a_service_client.list_bgp_as_a_services()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="create_bgp_as_a_services")
+ @idempotent_id('a039f0c4-b53a-492b-a5c5-fbdf046afcf4')
+ def test_create_bgp_as_a_services(self):
+ """
+ test method for create bgp as a service objects
+ """
+ with self.rbac_utils.override_role(self):
+ self._create_bgp_as_a_services()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="show_bgp_as_a_service")
+ @idempotent_id('c2fae8b4-929c-4d2f-914d-76a7414a56dc')
+ def test_show_bgp_as_a_service(self):
+ """
+ test method for show bgp as a service objects
+ """
+ new_bgp = self._create_bgp_as_a_services()
+ with self.rbac_utils.override_role(self):
+ self.bgp_as_a_service_client.show_bgp_as_a_service(
+ new_bgp['uuid'])
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="delete_bgp_as_a_service")
+ @idempotent_id('78c8389a-7bb5-4027-bae1-923af3d6e77c')
+ def test_delete_bgp_as_a_service(self):
+ """
+ test method for delete bgp as a service objects
+ """
+ new_bgp = self._create_bgp_as_a_services()
+ with self.rbac_utils.override_role(self):
+ self.bgp_as_a_service_client.delete_bgp_as_a_service(
+ new_bgp['uuid'])
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="update_bgp_as_a_service")
+ @idempotent_id('38ba2ecb-71e2-4a2f-be43-e82491dffa05')
+ def test_update_bgp_as_a_service(self):
+ """
+ test method for update bgp as a service objects
+ """
+ new_bgp = self._create_bgp_as_a_services()
+ with self.rbac_utils.override_role(self):
+ self.bgp_as_a_service_client.update_bgp_as_a_service(
+ new_bgp['uuid'],
+ display_name=data_utils.rand_name('test-bgp'))
diff --git a/tungsten_tempest_plugin/tests/api/contrail/test_config_client.py b/tungsten_tempest_plugin/tests/api/contrail/test_config_client.py
new file mode 100644
index 0000000..ea39ef2
--- /dev/null
+++ b/tungsten_tempest_plugin/tests/api/contrail/test_config_client.py
@@ -0,0 +1,277 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest test-case to test config objects using RBAC roles
+"""
+
+import random
+
+from oslo_log import log as logging
+
+from tungsten_tempest_plugin.tests.api.contrail import rbac_base
+
+from patrole_tempest_plugin import rbac_rule_validation
+
+from tempest import config
+from tempest.lib.common.utils import data_utils
+from tempest.lib.decorators import idempotent_id
+
+CONF = config.CONF
+LOG = logging.getLogger(__name__)
+
+
+class ConfigNodeTest(rbac_base.BaseContrailTest):
+
+ """
+ Test class to test config node objects using RBAC roles
+ """
+
+ @staticmethod
+ def _random_ip_generator():
+ random_ip = ".".join(map(str, (random.randint(0, 255)
+ for _ in range(4))))
+ return random_ip
+
+ def _create_config_node(self):
+ config_node_ip_address = self._random_ip_generator()
+ display_name = data_utils.rand_name('config_node')
+ fq_name = [display_name]
+ config_node = self.config_client.create_config_nodes(
+ config_node_ip_address=config_node_ip_address,
+ display_name=display_name, fq_name=fq_name)
+ config_node_id = config_node['config-node']['uuid']
+ if config_node_id:
+ self.addCleanup(self._try_delete_resource,
+ self.config_client.delete_config_node,
+ config_node_id)
+ return config_node
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="list_config_nodes")
+ @idempotent_id('b560e060-e4f0-45b0-93e2-55f0cb201e06')
+ def test_list_config_nodes(self):
+ """
+ test method for list config node objects
+ """
+ with self.rbac_utils.override_role(self):
+ self.config_client.list_config_nodes()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="create_config_nodes")
+ @idempotent_id('a8d20d0d-dc5a-4cae-87c5-7f6914c3701e')
+ def test_create_config_nodes(self):
+ """
+ test method for create config node objects
+ """
+ with self.rbac_utils.override_role(self):
+ self._create_config_node()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="delete_config_node")
+ @idempotent_id('16573a85-57ab-418c-bb23-5dd936e7be90')
+ def test_delete_config_node(self):
+ """
+ test method for delete config node objects
+ """
+ config_node = self._create_config_node()
+ config_node_uuid = config_node['config-node']['uuid']
+ with self.rbac_utils.override_role(self):
+ self.config_client.delete_config_node(
+ config_node_uuid)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="show_config_node")
+ @idempotent_id('a5b17108-4fa3-4d09-b861-e2857aab8f80')
+ def test_show_config_node(self):
+ """
+ test method for show config node objects
+ """
+ config_node = self._create_config_node()
+ config_node_uuid = config_node['config-node']['uuid']
+ with self.rbac_utils.override_role(self):
+ self.config_client.show_config_node(config_node_uuid)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="update_config_node")
+ @idempotent_id('8f70d2c0-594b-4a94-ab15-88bd8a2e62e5')
+ def test_update_config_node(self):
+ """
+ test method for update config node objects
+ """
+ config_node = self._create_config_node()
+ config_node_uuid = config_node['config-node']['uuid']
+ updated_name = data_utils.rand_name('new_config_node')
+ with self.rbac_utils.override_role(self):
+ self.config_client.update_config_node(
+ config_node_uuid, display_name=updated_name)
+
+
+class ConfigRootTest(rbac_base.BaseContrailTest):
+
+ """
+ Test class to test config root objects using RBAC roles
+ """
+
+ def _create_config_root(self):
+ display_name = data_utils.rand_name('config_root')
+ fq_name = [display_name]
+ config_root = self.config_client.create_config_roots(
+ display_name=display_name, fq_name=fq_name)
+ config_root_uuid = config_root['config-root']['uuid']
+ if config_root_uuid:
+ self.addCleanup(self._try_delete_resource,
+ self.config_client.delete_config_root,
+ config_root_uuid)
+ return config_root
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="create_config_roots")
+ @idempotent_id('291b28ea-d0d8-47cd-ac76-1f980047cb76')
+ def test_create_config_roots(self):
+ """
+ test method for create config root service objects
+ """
+ with self.rbac_utils.override_role(self):
+ self._create_config_root()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="delete_config_root")
+ @idempotent_id('bd04c0fb-3deb-4904-ad2c-1a10933c30dd')
+ def test_delete_config_root(self):
+ """
+ test method for delete config root service objects
+ """
+ config_root = self._create_config_root()
+ config_root_uuid = config_root['config-root']['uuid']
+ with self.rbac_utils.override_role(self):
+ self.config_client.delete_config_root(
+ config_root_uuid)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="show_config_root")
+ @idempotent_id('fba2c419-9a83-4d88-9a26-84770544bb3f')
+ def test_show_config_root(self):
+ """
+ test method for show config root service objects
+ """
+ config_root = self._create_config_root()
+ config_root_uuid = config_root['config-root']['uuid']
+ with self.rbac_utils.override_role(self):
+ self.config_client.show_config_root(config_root_uuid)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="update_config_root")
+ @idempotent_id('bfcc074f-5e1c-4b45-8a2a-857239f8acb0')
+ def test_update_config_root(self):
+ """
+ test method for update config root service objects
+ """
+ config_root = self._create_config_root()
+ config_root_uuid = config_root['config-root']['uuid']
+ updated_name = data_utils.rand_name('new_config_root')
+ with self.rbac_utils.override_role(self):
+ self.config_client.update_config_root(
+ config_root_uuid, display_name=updated_name)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="list_config_roots")
+ @idempotent_id('316e7425-8fb0-41b4-9080-a76697abbafa')
+ def test_list_config_roots(self):
+ """
+ test method for list config root service objects
+ """
+ with self.rbac_utils.override_role(self):
+ self.config_client.list_config_roots()
+
+
+class GlobalSystemConfigTest(rbac_base.BaseContrailTest):
+
+ """
+ Test class to test config node objects using RBAC roles
+ """
+
+ def _create_global_system_config(self):
+ config_name = data_utils.rand_name('test-config')
+ parent_type = 'config-root'
+ config_fq_name = [config_name]
+ new_config = \
+ self.config_client.create_global_system_configs(
+ parent_type=parent_type,
+ display_name=config_name,
+ fq_name=config_fq_name)['global-system-config']
+ self.addCleanup(self._try_delete_resource,
+ (self.config_client.
+ delete_global_system_config),
+ new_config['uuid'])
+ return new_config
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="list_global_system_configs")
+ @idempotent_id('d1d189a7-14c1-49c5-b180-cd42ed2ca123')
+ def test_list_global_system_configs(self):
+ """
+ test method for list global system config service objects
+ """
+ with self.rbac_utils.override_role(self):
+ self.config_client.list_global_system_configs()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="create_global_system_configs")
+ @idempotent_id('e0ba6a20-3e28-47ac-bf95-9a848fcee49a')
+ def test_create_global_sys_configs(self):
+ """
+ test method for create global system config service objects
+ """
+ with self.rbac_utils.override_role(self):
+ self._create_global_system_config()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="show_global_system_config")
+ @idempotent_id('4b9f9131-cb34-4b7d-9d06-c6aca85cce3a')
+ def test_show_global_system_config(self):
+ """
+ test method for show global system config service objects
+ """
+ new_config = self._create_global_system_config()
+ with self.rbac_utils.override_role(self):
+ self.config_client.show_global_system_config(
+ new_config['uuid'])
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="update_global_system_config")
+ @idempotent_id('4f90dc83-da59-45a4-8ab6-b387bd6c2df4')
+ def test_update_global_sys_config(self):
+ """
+ test method for update global system config service objects
+ """
+ new_config = self._create_global_system_config()
+ update_name = data_utils.rand_name('test')
+ with self.rbac_utils.override_role(self):
+ self.config_client.update_global_system_config(
+ new_config['uuid'],
+ display_name=update_name)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="delete_global_system_config")
+ @idempotent_id('fce1653c-e657-4a1e-8ced-7e02d297d6c9')
+ def test_delete_global_sys_config(self):
+ """
+ test method for delete global system config service objects
+ """
+ new_config = self._create_global_system_config()
+ with self.rbac_utils.override_role(self):
+ self.config_client.delete_global_system_config(
+ new_config['uuid'])
diff --git a/tungsten_tempest_plugin/tests/api/contrail/test_database.py b/tungsten_tempest_plugin/tests/api/contrail/test_database.py
new file mode 100644
index 0000000..e9c6b93
--- /dev/null
+++ b/tungsten_tempest_plugin/tests/api/contrail/test_database.py
@@ -0,0 +1,142 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest test-case to test database objects using RBAC roles
+"""
+
+from oslo_log import log as logging
+
+from tungsten_tempest_plugin.tests.api.contrail import rbac_base
+
+from patrole_tempest_plugin import rbac_rule_validation
+
+from tempest import config
+from tempest.lib.common.utils import data_utils
+from tempest.lib.decorators import idempotent_id
+
+CONF = config.CONF
+LOG = logging.getLogger(__name__)
+
+
+class ContrailDatabaseTest(rbac_base.BaseContrailTest):
+
+ """
+ Test class to test database objects using RBAC roles
+ """
+
+ def _create_global_system_config(self):
+ config_name = data_utils.rand_name('test-config')
+ parent_type = 'config-root'
+ config_fq_name = [config_name]
+ new_config = \
+ self.config_client.create_global_system_configs(
+ parent_type=parent_type,
+ display_name=config_name,
+ fq_name=config_fq_name)['global-system-config']
+ self.addCleanup(self._try_delete_resource,
+ (self.config_client.
+ delete_global_system_config),
+ new_config['uuid'])
+ return new_config
+
+ def _delete_database_node(self, db_node_id):
+ return self.db_client.delete_database_node(db_node_id)
+
+ def _create_database_node(self, global_system_config):
+ name = data_utils.rand_name('database')
+ fq_name = [global_system_config, name]
+ database_node_ip_address = '1.1.1.1'
+ parent_type = 'global-system-config'
+ db_node = self.db_client.create_databse_nodes(
+ display_name=name,
+ database_node_ip_address=database_node_ip_address,
+ fq_name=fq_name,
+ parent_type=parent_type)['database-node']
+
+ self.addCleanup(self._try_delete_resource,
+ self._delete_database_node,
+ db_node['uuid'])
+ return db_node
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="list_database_nodes")
+ @idempotent_id('5ae6f965-6161-443f-b19e-dfa7b364c533')
+ def test_list_database_nodes(self):
+ """
+ test method for list database objects
+ """
+ # Create global system config
+ global_system_config = self._create_global_system_config()['name']
+ self._create_database_node(global_system_config)
+ with self.rbac_utils.override_role(self):
+ self.db_client.list_database_nodes()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="show_database_node")
+ @idempotent_id('4a07d9a8-7b99-43bd-b628-06c023993aab')
+ def test_show_database_node(self):
+ """
+ test method for show database objects
+ """
+ # Create global system config
+ global_system_config = self._create_global_system_config()['name']
+ db_node = self._create_database_node(global_system_config)
+ db_node_id = db_node['uuid']
+ with self.rbac_utils.override_role(self):
+ self.db_client.show_database_node(db_node_id)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="create_database_nodes")
+ @idempotent_id('b9aa9c6b-9381-44f0-94fb-e4523bf2a87e')
+ def test_create_database_nodes(self):
+ """
+ test method for update database objects
+ """
+ # Create global system config
+ global_system_config = self._create_global_system_config()['name']
+ with self.rbac_utils.override_role(self):
+ self._create_database_node(global_system_config)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="update_database_node")
+ @idempotent_id('6e59f393-0e55-4327-871e-7f0ad53f2e17')
+ def test_update_database_node(self):
+ """
+ test method for update database objects
+ """
+ # Create global system config
+ global_system_config = self._create_global_system_config()['name']
+ db_node = self._create_database_node(global_system_config)
+ db_node_id = db_node['uuid']
+ display_name = data_utils.rand_name('DatabaseNew')
+ with self.rbac_utils.override_role(self):
+ self.db_client.update_database_node(
+ db_node_id=db_node_id,
+ display_name=display_name)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="delete_database_node")
+ @idempotent_id('0cbc5a52-d7e7-4a1c-a85d-6bf44012d99b')
+ def test_delete_database_node(self):
+ """
+ test method for delete database objects
+ """
+ # Create global system config
+ global_system_config = self._create_global_system_config()['name']
+ db_node = self._create_database_node(global_system_config)
+ db_node_id = db_node['uuid']
+ with self.rbac_utils.override_role(self):
+ self._delete_database_node(db_node_id)
diff --git a/tungsten_tempest_plugin/tests/api/contrail/test_discovery_service_assignment.py b/tungsten_tempest_plugin/tests/api/contrail/test_discovery_service_assignment.py
new file mode 100644
index 0000000..cd1fc85
--- /dev/null
+++ b/tungsten_tempest_plugin/tests/api/contrail/test_discovery_service_assignment.py
@@ -0,0 +1,103 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest test-case to test discovery service assignment objects using RBAC roles
+"""
+
+from tungsten_tempest_plugin.tests.api.contrail import rbac_base
+
+from patrole_tempest_plugin import rbac_rule_validation
+
+from tempest import config
+from tempest.lib.common.utils import data_utils
+from tempest.lib.decorators import idempotent_id
+
+CONF = config.CONF
+
+
+class DiscoveryServiceAssignmentTest(rbac_base.BaseContrailTest):
+
+ """
+ Test class to test discovery service assignment objects using RBAC roles
+ """
+
+ def _create_discovery_service_assignments(self):
+ dsa_name = [data_utils.rand_name('test-dsa')]
+ new_dsa = self.dsa_client.create_ds_assignments(
+ fq_name=dsa_name)['discovery-service-assignment']
+
+ self.addCleanup(self._try_delete_resource,
+ self.dsa_client.delete_ds_assignment,
+ new_dsa['uuid'])
+ return new_dsa
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="list_discovery_service_assignments")
+ @idempotent_id('9ac1e4ca-8983-403f-b644-7758935f2f36')
+ def test_list_discovery_service(self):
+ """
+ test method for list discovery service assignment objects
+ """
+ with self.rbac_utils.override_role(self):
+ self.dsa_client.list_ds_assignments()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="create_discovery_service_assignments")
+ @idempotent_id('40ad1208-a039-4809-8516-41b4dfcbd00c')
+ def test_create_discovery_service(self):
+ """
+ test method for create discovery service assignment objects
+ """
+ with self.rbac_utils.override_role(self):
+ self._create_discovery_service_assignments()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="show_discovery_service_assignment")
+ @idempotent_id('63660fe9-22b8-456c-a757-a7da1abfbce8')
+ def test_show_discovery_service(self):
+ """
+ test method for show discovery service assignment objects
+ """
+ new_dsa = self._create_discovery_service_assignments()
+ with self.rbac_utils.override_role(self):
+ self.dsa_client.show_ds_assignment(new_dsa['uuid'])
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="update_discovery_service_assignment")
+ @idempotent_id('71ce1404-965b-4670-abb7-5b6fea3b24b7')
+ def test_update_discovery_service(self):
+ """
+ test method for update discovery service assignment objects
+ """
+ new_dsa = self._create_discovery_service_assignments()
+ update_name = data_utils.rand_name('test')
+ with self.rbac_utils.override_role(self):
+ self.dsa_client.update_ds_assignment(
+ new_dsa['uuid'],
+ fq_name=new_dsa['fq_name'],
+ display_name=update_name)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="delete_discovery_service_assignment")
+ @idempotent_id('e7ff845d-2140-4eb0-9720-26370459723b')
+ def test_delete_discovery_service(self):
+ """
+ test method for delete discovery service assignment objects
+ """
+ new_dsa = self._create_discovery_service_assignments()
+ with self.rbac_utils.override_role(self):
+ self.dsa_client.delete_ds_assignment(
+ new_dsa['uuid'])
diff --git a/tungsten_tempest_plugin/tests/api/contrail/test_domain.py b/tungsten_tempest_plugin/tests/api/contrail/test_domain.py
new file mode 100644
index 0000000..d77ba98
--- /dev/null
+++ b/tungsten_tempest_plugin/tests/api/contrail/test_domain.py
@@ -0,0 +1,110 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest test-case to test domain objects using RBAC roles
+"""
+
+from oslo_log import log as logging
+
+from tungsten_tempest_plugin.tests.api.contrail import rbac_base
+
+from patrole_tempest_plugin import rbac_rule_validation
+
+from tempest import config
+from tempest.lib.common.utils import data_utils
+from tempest.lib.decorators import idempotent_id
+
+CONF = config.CONF
+LOG = logging.getLogger(__name__)
+
+
+class DomainContrailTest(rbac_base.BaseContrailTest):
+
+ """
+ Test class to test domain objects using RBAC roles
+ """
+
+ def _create_domains(self):
+ fq_name = data_utils.rand_name('domain')
+ post_body = {
+ 'fq_name': [fq_name]
+ }
+ resp_body = self.domain_client.create_domains(
+ **post_body)
+ domain_uuid = resp_body['domain']['uuid']
+ self.addCleanup(self._try_delete_resource,
+ self.domain_client.delete_domain,
+ domain_uuid)
+ return domain_uuid
+
+ def _update_domain(self, domain_uuid):
+ put_body = {
+ 'display_name': data_utils.rand_name('domain')
+ }
+ self.domain_client.update_domain(domain_uuid, **put_body)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="list_domains")
+ @idempotent_id('fa02e27b-f661-4186-a522-69e8fcb6abf9')
+ def test_list_domains(self):
+ """
+ test method for list domain objects
+ """
+ with self.rbac_utils.override_role(self):
+ self.domain_client.list_domains()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="create_domains")
+ @idempotent_id('3f18be91-c37b-4e17-bf5e-b704d993f738')
+ def test_create_domains(self):
+ """
+ test method for create domain objects
+ """
+ with self.rbac_utils.override_role(self):
+ self._create_domains()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="show_domain")
+ @idempotent_id('e79f8581-ba9f-420a-aa26-f1cb51cf4bbf')
+ def test_show_domain(self):
+ """
+ test method for show domain objects
+ """
+ domain_uuid = self._create_domains()
+ with self.rbac_utils.override_role(self):
+ self.domain_client.show_domain(domain_uuid)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="update_domain")
+ @idempotent_id('fdf72539-20b5-4bdb-b22b-70c86fbb52a4')
+ def test_update_domain(self):
+ """
+ test method for update domain objects
+ """
+ domain_uuid = self._create_domains()
+ with self.rbac_utils.override_role(self):
+ self._update_domain(domain_uuid)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="delete_domain")
+ @idempotent_id('abaad2b0-6bde-40b8-b257-20ca805c1dca')
+ def test_delete_domain(self):
+ """
+ test method for delete domain objects
+ """
+ domain_uuid = self._create_domains()
+ with self.rbac_utils.override_role(self):
+ self.domain_client.delete_domain(domain_uuid)
diff --git a/tungsten_tempest_plugin/tests/api/contrail/test_dsa_rule.py b/tungsten_tempest_plugin/tests/api/contrail/test_dsa_rule.py
new file mode 100644
index 0000000..c234e94
--- /dev/null
+++ b/tungsten_tempest_plugin/tests/api/contrail/test_dsa_rule.py
@@ -0,0 +1,128 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest test-case to test dsa rules objects using RBAC roles
+"""
+
+from oslo_log import log as logging
+
+from tungsten_tempest_plugin.tests.api.contrail import rbac_base
+
+from patrole_tempest_plugin import rbac_rule_validation
+
+from tempest import config
+from tempest.lib.common.utils import data_utils
+from tempest.lib.decorators import idempotent_id
+
+CONF = config.CONF
+LOG = logging.getLogger(__name__)
+
+
+class ContrailDSARuleTest(rbac_base.BaseContrailTest):
+
+ """
+ Test class to test DSA rule objects using RBAC roles
+ """
+
+ def _create_discovery_service_assignments(self):
+ dsa_name = [data_utils.rand_name('test-dsa')]
+ new_dsa = self.dsa_client.create_ds_assignments(
+ fq_name=dsa_name)['discovery-service-assignment']
+
+ self.addCleanup(self._try_delete_resource,
+ self.dsa_client.delete_ds_assignment,
+ new_dsa['uuid'])
+ return new_dsa
+
+ def _create_dsa_rules(self, discovery_service_assignment):
+ rule_name = data_utils.rand_name('dsa-rule')
+ post_data = {
+ 'fq_name': [discovery_service_assignment, rule_name],
+ 'parent_type': 'discovery-service-assignment'
+ }
+ new_rule = self.dsa_rule_client.create_dsa_rules(
+ **post_data)['dsa-rule']
+ self.addCleanup(self._try_delete_resource,
+ self.dsa_rule_client.delete_dsa_rule,
+ new_rule['uuid'])
+ return new_rule
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="list_dsa_rules")
+ @idempotent_id('3227673b-96fc-4d26-ab0b-109347e9e9c2')
+ def test_list_dsa_rules(self):
+ """
+ test method for list dsa rules objects
+ """
+ with self.rbac_utils.override_role(self):
+ self.dsa_rule_client.list_dsa_rules()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="show_dsa_rule")
+ @idempotent_id('0f90ea4f-c050-4c31-93a7-1e0c58df914e')
+ def test_show_dsa_rule(self):
+ """
+ test method for show dsa rules objects
+ """
+ # create discover service assignment
+ discovery_service_assignment = \
+ self._create_discovery_service_assignments()['name']
+ new_rule = self._create_dsa_rules(discovery_service_assignment)
+ with self.rbac_utils.override_role(self):
+ self.dsa_rule_client.show_dsa_rule(new_rule['uuid'])
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="create_dsa_rules")
+ @idempotent_id('c3774ca3-45d0-4ca8-a6b3-f895441b1d0e')
+ def test_create_dsa_rules(self):
+ """
+ test method for create dsa rules objects
+ """
+ # create discover service assignment
+ discovery_service_assignment = \
+ self._create_discovery_service_assignments()['name']
+ with self.rbac_utils.override_role(self):
+ self._create_dsa_rules(discovery_service_assignment)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="update_dsa_rule")
+ @idempotent_id('5cfe7e8e-d91c-4183-8e6c-733e826707be')
+ def test_update_dsa_rule(self):
+ """
+ test method for update dsa rules objects
+ """
+ # create discover service assignment
+ discovery_service_assignment = \
+ self._create_discovery_service_assignments()['name']
+ new_rule = self._create_dsa_rules(discovery_service_assignment)
+ update_name = data_utils.rand_name('updated_rule')
+ with self.rbac_utils.override_role(self):
+ self.dsa_rule_client.update_dsa_rule(
+ new_rule['uuid'], display_name=update_name)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="delete_dsa_rule")
+ @idempotent_id('d3b869db-fa49-48f0-861a-08efd9879b15')
+ def test_delete_dsa_rule(self):
+ """
+ test method for delete dsa rules objects
+ """
+ # create discover service assignment
+ discovery_service_assignment = \
+ self._create_discovery_service_assignments()['name']
+ new_rule = self._create_dsa_rules(discovery_service_assignment)
+ with self.rbac_utils.override_role(self):
+ self.dsa_rule_client.delete_dsa_rule(new_rule['uuid'])
diff --git a/tungsten_tempest_plugin/tests/api/contrail/test_floating_ip.py b/tungsten_tempest_plugin/tests/api/contrail/test_floating_ip.py
new file mode 100644
index 0000000..16813a0
--- /dev/null
+++ b/tungsten_tempest_plugin/tests/api/contrail/test_floating_ip.py
@@ -0,0 +1,266 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest test-case to test floating IP objects using RBAC roles
+"""
+
+from oslo_log import log as logging
+
+from tungsten_tempest_plugin.tests.api.contrail import rbac_base
+
+from patrole_tempest_plugin import rbac_rule_validation
+
+from tempest import config
+from tempest.lib.common.utils import data_utils
+from tempest.lib.decorators import idempotent_id
+
+CONF = config.CONF
+LOG = logging.getLogger(__name__)
+
+
+class BaseFloatingIpTest(rbac_base.BaseContrailTest):
+
+ """
+ Base class to test floating IP objects using RBAC roles
+ """
+
+ @classmethod
+ def resource_setup(cls):
+ super(BaseFloatingIpTest, cls).resource_setup()
+
+ # Create subnet using ipam
+ ipam_name = data_utils.rand_name('rbac-fip-ipam')
+ fq_name_ipam = ['default-domain',
+ cls.tenant_name,
+ ipam_name]
+
+ ip_cidr = CONF.network.project_network_cidr
+ ip_prefix, ip_prefix_len = ip_cidr.split('/')
+ subnet_ip_prefix = {'ip_prefix': ip_prefix,
+ 'ip_prefix_len': int(ip_prefix_len)}
+ ipam_post_body = {'parent_type': 'project', 'fq_name': fq_name_ipam}
+
+ body = cls.network_ipams_client.create_network_ipams(**ipam_post_body)
+ cls.ipam = body['network-ipam']
+
+ # Create network
+ net_name = data_utils.rand_name('rbac-pool-network')
+ fq_name = ['default-domain', cls.tenant_name, net_name]
+
+ post_body = {'parent_type': 'project',
+ 'router_external': True,
+ 'fq_name': fq_name,
+ 'network_ipam_refs': [
+ {
+ 'to': cls.ipam['fq_name'],
+ 'href': cls.ipam['href'],
+ 'uuid': cls.ipam['uuid'],
+ 'attr': {
+ 'ipam_subnets': [{'subnet': subnet_ip_prefix}]
+ }
+ }
+ ],
+ 'virtual_network_properties': {
+ 'forwarding_mode': 'l3'
+ }
+ }
+ body = cls.vn_client.create_virtual_networks(**post_body)
+ cls.network = body['virtual-network']
+
+ @classmethod
+ def resource_cleanup(cls):
+ cls._try_delete_resource(cls.vn_client.delete_virtual_network,
+ cls.network['uuid'])
+ cls._try_delete_resource(cls.network_ipams_client.delete_network_ipam,
+ cls.ipam['uuid'])
+ super(BaseFloatingIpTest, cls).resource_cleanup()
+
+
+class FloatingIpPoolTest(BaseFloatingIpTest):
+
+ """
+ Test class to test Floating IP pool objects using RBAC roles
+ """
+
+ def _create_floating_ip_pool(self):
+ pool_name = data_utils.rand_name('rbac-fip-pool')
+ fq_name = ['default-domain', self.tenant_name,
+ self.network['name'], pool_name]
+
+ post_body = {'display_name': pool_name,
+ 'parent_type': 'virtual-network',
+ 'fq_name': fq_name}
+
+ body = self.fip_client.create_floating_ip_pools(**post_body)
+ fip_pool = body['floating-ip-pool']
+
+ self.addCleanup(self._try_delete_resource,
+ self.fip_client.delete_floating_ip_pool,
+ fip_pool['uuid'])
+
+ return fip_pool
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="create_floating_ip_pools")
+ @idempotent_id('a83ca5e8-be4b-4161-869c-f981a724cf82')
+ def test_create_floating_ip_pools(self):
+ """
+ test method for create floating IP pool objects
+ """
+ with self.rbac_utils.override_role(self):
+ self._create_floating_ip_pool()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="list_floating_ip_pools")
+ @idempotent_id('9d20e78d-0463-4a0e-b30c-40770bee35bc')
+ def test_list_floating_ip_pools(self):
+ """
+ test method for list floating IP pool objects
+ """
+ self._create_floating_ip_pool()
+ with self.rbac_utils.override_role(self):
+ self.fip_client.list_floating_ip_pools()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="show_floating_ip_pool")
+ @idempotent_id('1ec3124c-c15c-4ee6-b2de-2feed9599e38')
+ def test_show_floating_ip_pool(self):
+ """
+ test method for show floating IP pool objects
+ """
+ uuid = self._create_floating_ip_pool()['uuid']
+ with self.rbac_utils.override_role(self):
+ self.fip_client.show_floating_ip_pool(uuid)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="update_floating_ip_pool")
+ @idempotent_id('6563f2e7-ae6b-483b-8c07-0111efc86817')
+ def test_update_floating_ip_pool(self):
+ """
+ test method for update floating IP pool objects
+ """
+ uuid = self._create_floating_ip_pool()['uuid']
+ with self.rbac_utils.override_role(self):
+ self.fip_client.update_floating_ip_pool(
+ uuid,
+ display_name='rbac-fip-pool-new-name')
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="delete_floating_ip_pool")
+ @idempotent_id('c4b449ae-2f12-49cf-9dec-2b21c143aff6')
+ def test_delete_floating_ip_pool(self):
+ """
+ test method for delete floating IP pool objects
+ """
+ uuid = self._create_floating_ip_pool()['uuid']
+ with self.rbac_utils.override_role(self):
+ self.fip_client.delete_floating_ip_pool(uuid)
+
+
+class FloatingIpTest(BaseFloatingIpTest):
+
+ """
+ Test class to test floating IP objects using RBAC roles
+ """
+
+ @classmethod
+ def resource_setup(cls):
+ super(FloatingIpTest, cls).resource_setup()
+ # Create Floating IP pool for the network
+ pool_name = data_utils.rand_name('rbac-fip-pool')
+ fq_name = ['default-domain', cls.tenant_name,
+ cls.network['name'], pool_name]
+ post_body = {'parent_type': 'virtual-network', 'fq_name': fq_name}
+ body = cls.fip_client.create_floating_ip_pools(**post_body)
+ cls.fip_pool = body['floating-ip-pool']
+
+ @classmethod
+ def resource_cleanup(cls):
+ cls._try_delete_resource(cls.fip_client.delete_floating_ip_pool,
+ cls.fip_pool['uuid'])
+ super(FloatingIpTest, cls).resource_cleanup()
+
+ def _create_floating_ip(self):
+ fip_name = data_utils.rand_name('rbac-fip')
+ fq_name = ['default-domain', self.tenant_name, self.network['name'],
+ self.fip_pool['name'], fip_name]
+ project_refs = {'to': ['default-domain', self.tenant_name]}
+ post_body = {'display_name': fip_name,
+ 'parent_type': 'floating-ip-pool',
+ 'fq_name': fq_name,
+ 'project_refs': [project_refs]}
+ body = self.fip_client.create_floating_ips(**post_body)
+ fip = body['floating-ip']
+ self.addCleanup(self._try_delete_resource,
+ self.fip_client.delete_floating_ip,
+ fip['uuid'])
+ return fip
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="create_floating_ips")
+ @idempotent_id('ff05f70f-9db9-43cb-a5ce-38cbbef2c430')
+ def test_create_floating_ips(self):
+ """
+ test method for create floating IP objects
+ """
+ with self.rbac_utils.override_role(self):
+ self._create_floating_ip()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="list_floating_ips")
+ @idempotent_id('e56046f9-32f9-41ce-9c1b-b982997ac347')
+ def test_list_floating_ips(self):
+ """
+ test method for list floating IP objects
+ """
+ self._create_floating_ip()
+ with self.rbac_utils.override_role(self):
+ self.fip_client.list_floating_ips()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="show_floating_ip")
+ @idempotent_id('293f2c26-4101-4a2f-86d4-feb2878bd511')
+ def test_show_floating_ip(self):
+ """
+ test method for show floating IP objects
+ """
+ uuid = self._create_floating_ip()['uuid']
+ with self.rbac_utils.override_role(self):
+ self.fip_client.show_floating_ip(uuid)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="update_floating_ip")
+ @idempotent_id('a09283c9-73d3-42f7-876d-f33040686d6d')
+ def test_update_floating_ip(self):
+ """
+ test method for update floating IP objects
+ """
+ uuid = self._create_floating_ip()['uuid']
+ with self.rbac_utils.override_role(self):
+ self.fip_client.update_floating_ip(
+ uuid,
+ display_name='rbac-fip-new-name')
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="delete_floating_ip")
+ @idempotent_id('a26f162f-da56-4153-aed6-bffccba92bc7')
+ def test_delete_floating_ip(self):
+ """
+ test method for delete floating IP objects
+ """
+ uuid = self._create_floating_ip()['uuid']
+ with self.rbac_utils.override_role(self):
+ self.fip_client.delete_floating_ip(uuid)
diff --git a/tungsten_tempest_plugin/tests/api/contrail/test_forwarding_class.py b/tungsten_tempest_plugin/tests/api/contrail/test_forwarding_class.py
new file mode 100644
index 0000000..ba805d0
--- /dev/null
+++ b/tungsten_tempest_plugin/tests/api/contrail/test_forwarding_class.py
@@ -0,0 +1,167 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest test-case to test forwarding class objects using RBAC roles
+"""
+
+from oslo_log import log as logging
+
+from tungsten_tempest_plugin.tests.api.contrail import rbac_base
+
+from patrole_tempest_plugin import rbac_rule_validation
+
+from tempest import config
+from tempest.lib.common.utils import data_utils
+from tempest.lib.decorators import idempotent_id
+
+CONF = config.CONF
+LOG = logging.getLogger(__name__)
+
+
+class ContrailForwardingClassTest(rbac_base.BaseContrailTest):
+
+ """
+ Test class to test Forwarding class objects using RBAC roles
+ """
+
+ def _create_global_system_config(self):
+ config_name = data_utils.rand_name('test-config')
+ parent_type = 'config-root'
+ config_fq_name = [config_name]
+ new_config = \
+ self.config_client.create_global_system_configs(
+ parent_type=parent_type,
+ display_name=config_name,
+ fq_name=config_fq_name)['global-system-config']
+ self.addCleanup(self._try_delete_resource,
+ (self.config_client.
+ delete_global_system_config),
+ new_config['uuid'])
+ return new_config
+
+ def _create_qos_global_configs(self, global_system_config):
+ name = data_utils.rand_name('test-rbac-qos-global-config')
+ parent_type = 'global-system-config'
+ fq_name = [global_system_config, name]
+ qos_global_config = self.qos_client.create_global_qos_configs(
+ fq_name=fq_name,
+ parent_type=parent_type)['global-qos-config']
+
+ self.addCleanup(self._try_delete_resource,
+ self.qos_client.delete_global_qos_config,
+ qos_global_config['uuid'])
+ return qos_global_config
+
+ def _create_forwarding_class(self,
+ global_system_config,
+ global_qos_config):
+ display_name = data_utils.rand_name('forwarding-class')
+ parent_type = 'global-qos-config'
+ fq_name = [global_system_config, global_qos_config, "1"]
+ forwarding_class_id = data_utils.rand_int_id(1, 200)
+ post_data = {
+ 'fq_name': fq_name,
+ 'parent_type': parent_type,
+ 'display_name': display_name,
+ 'forwarding_class_id': forwarding_class_id
+ }
+ new_fclass = self.forwarding_class_client.create_forwarding_classs(
+ **post_data)['forwarding-class']
+ self.addCleanup(self._try_delete_resource,
+ self.forwarding_class_client.delete_forwarding_class,
+ new_fclass['uuid'])
+ return new_fclass
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="list_forwarding_classs")
+ @idempotent_id('807a66fd-d4a4-472c-a13d-7ba590509e6e')
+ def test_list_forwarding_classs(self):
+ """
+ test method for list forwarding classes objects
+ """
+ with self.rbac_utils.override_role(self):
+ self.forwarding_class_client.list_forwarding_classs()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="show_forwarding_class")
+ @idempotent_id('8ef21f71-72a4-4de9-af93-6e759aa463c0')
+ def test_show_forwarding_class(self):
+ """
+ test method for show forwarding classes objects
+ """
+ # Create global system config
+ global_system_config = self._create_global_system_config()['name']
+ # Create a global qos config
+ global_qos_config = \
+ self._create_qos_global_configs(global_system_config)['name']
+ new_fclass = self._create_forwarding_class(global_system_config,
+ global_qos_config)
+ with self.rbac_utils.override_role(self):
+ self.forwarding_class_client.show_forwarding_class(
+ new_fclass['uuid'])
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="create_forwarding_classs")
+ @idempotent_id('d098859c-ad36-4385-8fb0-c00934a99b6f')
+ def test_create_forwarding_classs(self):
+ """
+ test method for create forwarding classes objects
+ """
+ # Create global system config
+ global_system_config = self._create_global_system_config()['name']
+ # Create a global qos config
+ global_qos_config = \
+ self._create_qos_global_configs(global_system_config)['name']
+ with self.rbac_utils.override_role(self):
+ self._create_forwarding_class(global_system_config,
+ global_qos_config)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="update_forwarding_class")
+ @idempotent_id('589dc03d-a25d-48be-9d9c-d3f92ff2cfc6')
+ def test_update_forwarding_class(self):
+ """
+ test method for update forwarding classes objects
+ """
+ # Create global system config
+ global_system_config = self._create_global_system_config()['name']
+ # Create a global qos config
+ global_qos_config = \
+ self._create_qos_global_configs(global_system_config)['name']
+ new_fclass = self._create_forwarding_class(global_system_config,
+ global_qos_config)
+ update_name = data_utils.rand_name('updated_fclass')
+ with self.rbac_utils.override_role(self):
+ self.forwarding_class_client.update_forwarding_class(
+ new_fclass['uuid'], display_name=update_name)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="delete_forwarding_class")
+ @idempotent_id('a0348ffc-68c5-4d94-ba03-d08483503ced')
+ def test_delete_forwarding_class(self):
+ """
+ test method for delete forwarding classes objects
+ """
+ # Create global system config
+ global_system_config = self._create_global_system_config()['name']
+ # Create a global qos config
+ global_qos_config = \
+ self._create_qos_global_configs(global_system_config)['name']
+ new_fclass = self._create_forwarding_class(global_system_config,
+ global_qos_config)
+ with self.rbac_utils.override_role(self):
+ self.forwarding_class_client.delete_forwarding_class(
+ new_fclass['uuid'])
diff --git a/tungsten_tempest_plugin/tests/api/contrail/test_fqname_id.py b/tungsten_tempest_plugin/tests/api/contrail/test_fqname_id.py
new file mode 100644
index 0000000..f2d91c0
--- /dev/null
+++ b/tungsten_tempest_plugin/tests/api/contrail/test_fqname_id.py
@@ -0,0 +1,76 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest test-case to test fqname ID objects using RBAC roles
+"""
+
+from oslo_log import log as logging
+
+from tungsten_tempest_plugin.tests.api.contrail import rbac_base
+
+from patrole_tempest_plugin import rbac_rule_validation
+
+from tempest import config
+from tempest.lib.common.utils import data_utils
+from tempest.lib.decorators import idempotent_id
+
+CONF = config.CONF
+LOG = logging.getLogger(__name__)
+
+
+class FqnameIdTest(rbac_base.BaseContrailTest):
+
+ """
+ Test class to test Fqname ID objects using RBAC roles
+ """
+
+ @classmethod
+ def resource_setup(cls):
+ super(FqnameIdTest, cls).resource_setup()
+ # Create network to test fqname and uuid conversion
+ net_name = data_utils.rand_name('rbac-fq-network')
+ fq_name = ['default-domain', cls.tenant_name, net_name]
+ post_body = {'parent_type': 'project', 'fq_name': fq_name}
+ body = cls.vn_client.create_virtual_networks(**post_body)
+ cls.network = body['virtual-network']
+ cls.type = 'virtual-network'
+
+ @classmethod
+ def resource_cleanup(cls):
+ cls._try_delete_resource(cls.vn_client.delete_virtual_network,
+ cls.network['uuid'])
+ super(FqnameIdTest, cls).resource_cleanup()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="fqname_to_id")
+ @idempotent_id('1fc1350b-3146-49bc-9af5-a61a98b55541')
+ def test_fqname_to_id(self):
+ """
+ test method for fqname to id rules objects
+ """
+ with self.rbac_utils.override_role(self):
+ self.fq_client.fqname_to_id(fq_name=self.network['fq_name'],
+ type=self.type)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="id_to_fqname")
+ @idempotent_id('ecdd77d7-8508-4639-86cd-b97907b363ff')
+ def test_id_to_fqname(self):
+ """
+ test method for id to fqname rules objects
+ """
+ with self.rbac_utils.override_role(self):
+ self.fq_client.id_to_fqname(uuid=self.network['uuid'])
diff --git a/tungsten_tempest_plugin/tests/api/contrail/test_instance_ip.py b/tungsten_tempest_plugin/tests/api/contrail/test_instance_ip.py
new file mode 100644
index 0000000..c5d6b48
--- /dev/null
+++ b/tungsten_tempest_plugin/tests/api/contrail/test_instance_ip.py
@@ -0,0 +1,162 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest test-case to test instance IP objects using RBAC roles
+"""
+
+from oslo_log import log as logging
+
+from tungsten_tempest_plugin.tests.api.contrail import rbac_base
+
+from patrole_tempest_plugin import rbac_rule_validation
+
+from tempest import config
+from tempest.lib.common.utils import data_utils
+from tempest.lib.decorators import idempotent_id
+
+CONF = config.CONF
+LOG = logging.getLogger(__name__)
+
+
+class InstanceIPTest(rbac_base.BaseContrailTest):
+
+ """
+ Test class to test instance IP objects using RBAC roles
+ """
+
+ @classmethod
+ def resource_setup(cls):
+ super(InstanceIPTest, cls).resource_setup()
+ # Create network ipam
+ ipam_name = data_utils.rand_name('rbac-iip-ipam')
+ fq_name_ipam = ['default-domain',
+ cls.tenant_name,
+ ipam_name]
+ subnet_ip_prefix = {'ip_prefix': '1.2.3.0', 'ip_prefix_len': 24}
+ ipam_post_body = {'display_name': ipam_name,
+ 'fq_name': fq_name_ipam,
+ 'parent_type': 'project'}
+ body = cls.network_ipams_client.create_network_ipams(**ipam_post_body)
+ cls.ipam = body['network-ipam']
+
+ # Create network
+ net_name = data_utils.rand_name('rbac-iip-network')
+ fq_name = ['default-domain', cls.tenant_name, net_name]
+ post_body = {'parent_type': 'project',
+ 'router_external': True,
+ 'fq_name': fq_name,
+ 'network_ipam_refs': [
+ {
+ 'to': cls.ipam['fq_name'],
+ 'href': cls.ipam['href'],
+ 'uuid': cls.ipam['uuid'],
+ 'attr': {
+ 'ipam_subnets': [{'subnet': subnet_ip_prefix}]
+ }
+ }
+ ],
+ 'virtual_network_properties': {
+ 'forwarding_mode': 'l3'
+ }
+ }
+ body = cls.vn_client.create_virtual_networks(**post_body)
+ cls.network = body['virtual-network']
+
+ @classmethod
+ def resource_cleanup(cls):
+ cls._try_delete_resource(cls.vn_client.delete_virtual_network,
+ cls.network['uuid'])
+ cls._try_delete_resource(cls.network_ipams_client.delete_network_ipam,
+ cls.ipam['uuid'])
+ super(InstanceIPTest, cls).resource_cleanup()
+
+ def _create_instance_ip(self):
+ iip_name = data_utils.rand_name('rbac-iip')
+ virtual_network_refs = [
+ {
+ 'to': self.network['fq_name'],
+ 'href': self.network['href'],
+ 'uuid': self.network['uuid']
+ }
+ ]
+ post_body = {
+ 'display_name': iip_name,
+ 'fq_name': [iip_name],
+ 'virtual_network_refs': virtual_network_refs,
+ 'instance_ip_address': '1.2.3.50'
+ }
+ body = self.iip_client.create_instance_ips(**post_body)
+ iip = body['instance-ip']
+ self.addCleanup(self._try_delete_resource,
+ self.iip_client.delete_instance_ip,
+ iip['uuid'])
+ return iip
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="list_instance_ips")
+ @idempotent_id('31db3b3f-c40b-4f7f-bb8b-0a110f099553')
+ def test_list_instance_ips(self):
+ """
+ test method for list instance IP objects
+ """
+ self._create_instance_ip()
+ with self.rbac_utils.override_role(self):
+ self.iip_client.list_instance_ips()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="create_instance_ips")
+ @idempotent_id('78f5cd4d-345d-4d87-8b8b-4d5d3fec4a12')
+ def test_create_instance_ips(self):
+ """
+ test method for create instance IP objects
+ """
+ with self.rbac_utils.override_role(self):
+ self._create_instance_ip()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="show_instance_ip")
+ @idempotent_id('276f3838-d9cb-4432-bbb4-db31c4c1db5c')
+ def test_show_instance_ip(self):
+ """
+ test method for update instance IP objects
+ """
+ uuid = self._create_instance_ip()['uuid']
+ with self.rbac_utils.override_role(self):
+ self.iip_client.show_instance_ip(uuid)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="update_instance_ip")
+ @idempotent_id('b85975a5-176f-44b1-a615-b6f0a39a7708')
+ def test_update_instance_ip(self):
+ """
+ test method for update instance IP objects
+ """
+ uuid = self._create_instance_ip()['uuid']
+ with self.rbac_utils.override_role(self):
+ self.iip_client.update_instance_ip(
+ uuid,
+ display_name='rbac-iip-new-name')
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="delete_instance_ip")
+ @idempotent_id('d9c1d400-1dfb-4adb-8d97-0e8b498226b7')
+ def test_delete_instance_ip(self):
+ """
+ test method for delete instance IP objects
+ """
+ uuid = self._create_instance_ip()['uuid']
+ with self.rbac_utils.override_role(self):
+ self.iip_client.delete_instance_ip(uuid)
diff --git a/tungsten_tempest_plugin/tests/api/contrail/test_interfaces.py b/tungsten_tempest_plugin/tests/api/contrail/test_interfaces.py
new file mode 100644
index 0000000..32a9703
--- /dev/null
+++ b/tungsten_tempest_plugin/tests/api/contrail/test_interfaces.py
@@ -0,0 +1,230 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest test-case to test interfaces objects using RBAC roles
+"""
+
+from oslo_log import log as logging
+
+from tungsten_tempest_plugin.tests.api.contrail import rbac_base
+
+from patrole_tempest_plugin import rbac_rule_validation
+
+from tempest import config
+from tempest.lib.common.utils import data_utils
+from tempest.lib.decorators import idempotent_id
+
+CONF = config.CONF
+LOG = logging.getLogger(__name__)
+
+
+class InterfacesTest(rbac_base.BaseContrailTest):
+
+ """
+ Test class to test interfaces objects using RBAC roles
+ """
+
+ router_name = data_utils.rand_name('rbac-physical-router')
+ physical_if_name = data_utils.rand_name('rbac-physical-interface')
+ logical_if_name = data_utils.rand_name('rbac-logical-interface')
+
+ def _create_global_system_config(self):
+ config_name = data_utils.rand_name('test-config')
+ parent_type = 'config-root'
+ config_fq_name = [config_name]
+ new_config = \
+ self.config_client.create_global_system_configs(
+ parent_type=parent_type,
+ display_name=config_name,
+ fq_name=config_fq_name)['global-system-config']
+ self.addCleanup(self._try_delete_resource,
+ (self.config_client.
+ delete_global_system_config),
+ new_config['uuid'])
+ return new_config
+
+ def _create_physical_router(self):
+ self.global_system_config = self._create_global_system_config()['name']
+
+ fq_name = [self.global_system_config, self.router_name]
+ post_body = {'parent_type': 'global-system-config', 'fq_name': fq_name}
+
+ router = self.router_client.create_physical_routers(
+ **post_body)['physical-router']
+ self.addCleanup(self._try_delete_resource,
+ self.router_client.delete_physical_router,
+ router['uuid'])
+ return router
+
+ def _create_physical_interface(self):
+ fq_name = [self.global_system_config, self.router_name,
+ self.physical_if_name]
+ post_body = {'parent_type': 'physical-router', 'fq_name': fq_name}
+
+ physical_if = self.interface_client.create_physical_interfaces(
+ **post_body)['physical-interface']
+ self.addCleanup(self._try_delete_resource,
+ self.interface_client.delete_physical_interface,
+ physical_if['uuid'])
+ return physical_if
+
+ def _create_logical_interface(self):
+ fq_name = [self.global_system_config, self.router_name,
+ self.physical_if_name, self.logical_if_name]
+ post_body = {'parent_type': 'physical-interface', 'fq_name': fq_name}
+
+ logical_if = self.interface_client.create_logical_interfaces(
+ **post_body)['logical-interface']
+ self.addCleanup(self._try_delete_resource,
+ self.interface_client.delete_logical_interface,
+ logical_if['uuid'])
+ return logical_if
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="list_physical_interfaces")
+ @idempotent_id('c496a2b4-51b2-4674-a60e-483a315baccb')
+ def test_list_physical_interfaces(self):
+ """
+ test method for list physical interfaces objects
+ """
+ with self.rbac_utils.override_role(self):
+ self.interface_client.list_physical_interfaces()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="create_physical_interfaces")
+ @idempotent_id('066f53d8-3d2a-4ad6-983f-243de7c12962')
+ def test_create_physical_interfaces(self):
+ """
+ test method for create physical interfaces objects
+ """
+
+ self._create_physical_router()
+ with self.rbac_utils.override_role(self):
+ self._create_physical_interface()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="update_physical_interface")
+ @idempotent_id('91c4fc90-ed0f-42ec-87c6-ff6c2a9ab8de')
+ def test_update_physical_interface(self):
+ """
+ test method for update physical interfaces objects
+ """
+ self._create_physical_router()
+ uuid = self._create_physical_interface()['uuid']
+ # Required for Contrail 3.0.3 but not for 3.1.1
+ response = self.interface_client.show_physical_interface(uuid)
+ body = response['physical-interface']
+ owner = body['perms2']['owner']
+ with self.rbac_utils.override_role(self):
+ change_access = {"owner": owner, "owner_access": 6, "share": [],
+ "global_access": 0}
+ body = {"perms2": change_access}
+ self.interface_client.update_physical_interface(
+ uuid, **body)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="delete_physical_interface")
+ @idempotent_id('5d77ea76-be8c-49cc-8f08-72fbdaf9028f')
+ def test_delete_physical_interface(self):
+ """
+ test method for delete physical interfaces objects
+ """
+ self._create_physical_router()
+ uuid = self._create_physical_interface()['uuid']
+
+ with self.rbac_utils.override_role(self):
+ self.interface_client.delete_physical_interface(uuid)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="show_physical_interface")
+ @idempotent_id('2c75c7e7-ef34-4e24-9c2f-5a2182db33a6')
+ def test_show_physical_interface(self):
+ """
+ test method for show physical interfaces objects
+ """
+ self._create_physical_router()
+ uuid = self._create_physical_interface()['uuid']
+ with self.rbac_utils.override_role(self):
+ self.interface_client.show_physical_interface(uuid)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="list_logical_interfaces")
+ @idempotent_id('43ac3727-4a43-42d7-b52f-df75018915b9')
+ def test_list_logical_interfaces(self):
+ """
+ test method for list physical interfaces objects
+ """
+ with self.rbac_utils.override_role(self):
+ self.interface_client.list_logical_interfaces()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="create_logical_interfaces")
+ @idempotent_id('503facf2-0752-47e4-a0a4-7a3103133a61')
+ def test_create_logical_interfaces(self):
+ """
+ test method for create logical interfaces objects
+ """
+ self._create_physical_router()
+ self._create_physical_interface()
+ with self.rbac_utils.override_role(self):
+ self._create_logical_interface()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="update_logical_interface")
+ @idempotent_id('63c991f4-6aba-454c-9c49-522dc77b3f5c')
+ def test_update_logical_interface(self):
+ """
+ test method for update logical interfaces objects
+ """
+ self._create_physical_router()
+ self._create_physical_interface()
+ uuid = self._create_logical_interface()['uuid']
+ # Required for Contrail 3.0.3 but not for 3.1.1
+ response = self.interface_client.show_logical_interface(uuid)
+ body = response['logical-interface']
+ owner = body['perms2']['owner']
+ with self.rbac_utils.override_role(self):
+ change_access = {"owner": owner, "owner_access": 6, "share": [],
+ "global_access": 0}
+ body = {"perms2": change_access}
+ self.interface_client.update_logical_interface(
+ uuid, **body)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="delete_logical_interface")
+ @idempotent_id('a36743d1-3ea1-4cf5-89d8-9c0b885fa625')
+ def test_delete_logical_interface(self):
+ """
+ test method for update logical interfaces objects
+ """
+ self._create_physical_router()
+ self._create_physical_interface()
+ uuid = self._create_logical_interface()['uuid']
+ with self.rbac_utils.override_role(self):
+ self.interface_client.delete_logical_interface(uuid)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="show_logical_interface")
+ @idempotent_id('f0f7fab7-eeb9-4d29-8415-31a50180fb44')
+ def test_show_logical_interface(self):
+ """
+ test method for show logical interfaces objects
+ """
+ self._create_physical_router()
+ self._create_physical_interface()
+ uuid = self._create_logical_interface()['uuid']
+ with self.rbac_utils.override_role(self):
+ self.interface_client.show_logical_interface(uuid)
diff --git a/tungsten_tempest_plugin/tests/api/contrail/test_load_balancer.py b/tungsten_tempest_plugin/tests/api/contrail/test_load_balancer.py
new file mode 100644
index 0000000..f19c4ce
--- /dev/null
+++ b/tungsten_tempest_plugin/tests/api/contrail/test_load_balancer.py
@@ -0,0 +1,471 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest test-case to test load balancer objects using RBAC roles
+"""
+
+from oslo_log import log as logging
+
+from tungsten_tempest_plugin.tests.api.contrail import rbac_base
+
+from patrole_tempest_plugin import rbac_rule_validation
+
+from tempest import config
+from tempest.lib.common.utils import data_utils
+from tempest.lib.decorators import idempotent_id
+
+CONF = config.CONF
+LOG = logging.getLogger(__name__)
+
+
+class BaseLoadBalancerTest(rbac_base.BaseContrailTest):
+
+ """
+ Base class to test load balancer objects using RBAC roles
+ """
+
+ def _create_load_balancer(self):
+ fq_name = data_utils.rand_name('load-balancer')
+ post_body = {
+ 'parent_type': 'project',
+ 'fq_name': ['default-domain', self.tenant_name, fq_name]
+ }
+ resp_body = self.load_balancer_client.create_load_balancers(
+ **post_body)
+ lb_uuid = resp_body['loadbalancer']['uuid']
+ self.addCleanup(self._try_delete_resource,
+ self.load_balancer_client.delete_load_balancer,
+ lb_uuid)
+ return lb_uuid
+
+ def _update_load_balancer(self, lb_uuid):
+ put_body = {
+ 'display_name': data_utils.rand_name('load-balancer')
+ }
+ self.load_balancer_client.update_load_balancer(lb_uuid, **put_body)
+
+ def _create_load_balancer_health_monitor(self):
+ fq_name = data_utils.rand_name('load_balancer-health-monitor')
+ post_body = {
+ 'parent_type': 'project',
+ 'fq_name': ['default-domain', self.tenant_name, fq_name],
+ 'loadbalancer_healthmonitor_properties': {
+ 'monitor_type': 'PING',
+ 'delay': 10,
+ 'timeout': 60,
+ 'max_retries': 3
+ }
+ }
+ resp_body = self.load_balancer_client \
+ .create_lb_healthmonitors(**post_body)
+ lb_hm_uuid = resp_body['loadbalancer-healthmonitor']['uuid']
+ self.addCleanup(self._try_delete_resource,
+ self.load_balancer_client
+ .delete_lb_healthmonitor,
+ lb_hm_uuid)
+ return lb_hm_uuid
+
+ def _update_load_balancer_health_monitor(self, lb_hm_uuid):
+ display_name = data_utils.rand_name('load_balancer-health-monitor')
+ put_body = {
+ 'display_name': display_name
+ }
+
+ self.load_balancer_client.update_lb_healthmonitor(
+ lb_hm_uuid,
+ **put_body)
+
+ def _create_load_balancer_listener(self):
+ fq_name = data_utils.rand_name('load_balancer-listener')
+ post_body = {
+ 'parent_type': 'project',
+ 'fq_name': ['default-domain', self.tenant_name, fq_name]
+ }
+ resp_body = self.load_balancer_client.create_load_balancer_listeners(
+ **post_body)
+ lb_listener_uuid = resp_body['loadbalancer-listener']['uuid']
+ self.addCleanup(self._try_delete_resource,
+ self.load_balancer_client
+ .delete_load_balancer_listener,
+ lb_listener_uuid)
+ return lb_listener_uuid
+
+ def _update_load_balancer_listener(self, lb_listener_uuid):
+ put_body = {
+ 'display_name': data_utils.rand_name('load_balancer-listener')
+ }
+ self.load_balancer_client.update_load_balancer_listener(
+ lb_listener_uuid,
+ **put_body)
+
+ def _create_load_balancer_pool(self, return_object=False):
+ fq_name = data_utils.rand_name('load_balancer-pool')
+ post_body = {
+ 'parent_type': 'project',
+ 'fq_name': ['default-domain', self.tenant_name, fq_name]
+ }
+ resp_body = self.load_balancer_client.create_load_balancer_pools(
+ **post_body)
+ lb_pool_uuid = resp_body['loadbalancer-pool']['uuid']
+ self.addCleanup(self._try_delete_resource,
+ self.load_balancer_client.delete_load_balancer_pool,
+ lb_pool_uuid)
+ if return_object:
+ return resp_body['loadbalancer-pool']
+ return lb_pool_uuid
+
+ def _update_load_balancer_pool(self, lb_pool_uuid):
+ put_body = {
+ 'display_name': data_utils.rand_name('load_balancer-pool')
+ }
+ self.load_balancer_client.update_load_balancer_pool(lb_pool_uuid,
+ **put_body)
+
+ def _create_load_balancer_member(self):
+ lb_pool = self._create_load_balancer_pool(return_object=True)
+ fq_name = data_utils.rand_name('load_balancer-member')
+ post_body = {
+ 'parent_type': 'loadbalancer-pool',
+ 'fq_name': ['default-domain', self.tenant_name, lb_pool['name'],
+ fq_name]
+ }
+ resp_body = self.load_balancer_client.create_load_balancer_members(
+ **post_body)
+ lb_member_uuid = resp_body['loadbalancer-member']['uuid']
+ self.addCleanup(self._try_delete_resource,
+ self._delete_pool_and_member,
+ lb_pool['uuid'],
+ lb_member_uuid)
+ return lb_member_uuid
+
+ def _update_load_balancer_member(self, lb_member_uuid):
+ put_body = {
+ 'display_name': data_utils.rand_name('load_balancer-member')
+ }
+ self.load_balancer_client.update_load_balancer_member(lb_member_uuid,
+ **put_body)
+
+ def _delete_pool_and_member(self, lb_pool_uuid, lb_member_uuid):
+ # Used by _try_delete_resource in _create_load_balancer_member.
+ # Guarantees that child (lb member) is deleted before parent
+ # dependency (lb pool).
+ self.load_balancer_client.delete_load_balancer_member(lb_member_uuid)
+ self.load_balancer_client.delete_load_balancer_pool(lb_pool_uuid)
+
+
+class LoadBalancerContrailTest(BaseLoadBalancerTest):
+
+ """
+ Test class to test load balancer objects using RBAC roles
+ """
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="list_load_balancers")
+ @idempotent_id('5d840b6b-3974-4945-916f-dd53ba27e42f')
+ def test_list_load_balancers(self):
+ """
+ test method for list load balancer objects
+ """
+ with self.rbac_utils.override_role(self):
+ self.load_balancer_client.list_load_balancers()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="create_load_balancers")
+ @idempotent_id('6a18d506-0794-4eb9-a945-165bf146005d')
+ def test_create_load_balancers(self):
+ """
+ test method for create load balancer objects
+ """
+ with self.rbac_utils.override_role(self):
+ self._create_load_balancer()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="show_load_balancer")
+ @idempotent_id('428012aa-cd0e-4702-89d2-459046d4bd5f')
+ def test_show_load_balancer(self):
+ """
+ test method for show load balancer objects
+ """
+ lb_uuid = self._create_load_balancer()
+ with self.rbac_utils.override_role(self):
+ self.load_balancer_client.show_load_balancer(lb_uuid)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="update_load_balancer")
+ @idempotent_id('7cd3d7b2-b149-40c1-a801-a6a8a660bd24')
+ def test_update_load_balancer(self):
+ """
+ test method for update load balancer objects
+ """
+ lb_uuid = self._create_load_balancer()
+ with self.rbac_utils.override_role(self):
+ self._update_load_balancer(lb_uuid)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="delete_load_balancer")
+ @idempotent_id('b28c6b11-d1b0-45d0-8942-638b6b590702')
+ def test_delete_load_balancer(self):
+ """
+ test method for delete load balancer objects
+ """
+ lb_uuid = self._create_load_balancer()
+ with self.rbac_utils.override_role(self):
+ self.load_balancer_client.delete_load_balancer(lb_uuid)
+
+
+class LoadBalancerHealthMonitorContrailTest(BaseLoadBalancerTest):
+
+ """
+ Test class to test load balancer Health Monitor objects using RBAC roles
+ """
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="list_load_balancer_health_monitors")
+ @idempotent_id('3e3d8bdc-3621-4c5e-8130-1187f445a4e6')
+ def test_list_lb_health_monitors(self):
+ """
+ test method for list load balancer health monitor objects
+ """
+ with self.rbac_utils.override_role(self):
+ self.load_balancer_client.list_lb_healthmonitors()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="create_load_balancer_health_monitors")
+ @idempotent_id('bddb93ad-d331-4bbc-bac6-2763cae4eb2c')
+ def test_create_lb_health_monitors(self):
+ """
+ test method for create load balancer health monitor objects
+ """
+ with self.rbac_utils.override_role(self):
+ self._create_load_balancer_health_monitor()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="show_load_balancer_health_monitor")
+ @idempotent_id('30d23994-1e3a-4a76-8f18-e00d0854412a')
+ def test_show_lb_health_monitor(self):
+ """
+ test method for show load balancer health monitor objects
+ """
+ lb_hm_uuid = self._create_load_balancer_health_monitor()
+ with self.rbac_utils.override_role(self):
+ self.load_balancer_client.show_lb_healthmonitor(
+ lb_hm_uuid)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="update_load_balancer_health_monitor")
+ @idempotent_id('c32ba92c-3a69-4255-867a-1423c93faa6f')
+ def test_update_lb_health_monitor(self):
+ """
+ test method for update load balancer health monitor objects
+ """
+ lb_hm_uuid = self._create_load_balancer_health_monitor()
+ with self.rbac_utils.override_role(self):
+ self._update_load_balancer_health_monitor(lb_hm_uuid)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="delete_load_balancer_health_monitor")
+ @idempotent_id('b4d7ea9d-fd8c-433b-96fc-c24866b3f6a7')
+ def test_delete_lb_health_monitor(self):
+ """
+ test method for delete load balancer health monitor objects
+ """
+ lb_hm_uuid = self._create_load_balancer_health_monitor()
+ with self.rbac_utils.override_role(self):
+ self.load_balancer_client.delete_lb_healthmonitor(
+ lb_hm_uuid)
+
+
+class LoadBalancerListenerContrailTest(BaseLoadBalancerTest):
+
+ """
+ Base class to test load balancer Listener objects using RBAC roles
+ """
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="list_load_balancer_listeners")
+ @idempotent_id('7e02882f-0eab-41c2-b48a-bf71e083b912')
+ def test_list_lb_listeners(self):
+ """
+ test method for list load balancer listener objects
+ """
+ with self.rbac_utils.override_role(self):
+ self.load_balancer_client.list_load_balancer_listeners()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="create_load_balancer_listeners")
+ @idempotent_id('0551de87-fa4c-463f-8968-ec6f2a6098d0')
+ def test_create_lb_listeners(self):
+ """
+ test method for create load balancer listener objects
+ """
+ with self.rbac_utils.override_role(self):
+ self._create_load_balancer_listener()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="show_load_balancer_listener")
+ @idempotent_id('ade38959-9506-4262-8d3c-5ba5eb63d85f')
+ def test_show_lb_listener(self):
+ """
+ test method for show load balancer listener objects
+ """
+ lb_listener_uuid = self._create_load_balancer_listener()
+ with self.rbac_utils.override_role(self):
+ self.load_balancer_client.show_load_balancer_listener(
+ lb_listener_uuid)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="update_load_balancer_listener")
+ @idempotent_id('e529e538-da31-4159-91c2-6c0a828282a4')
+ def test_update_lb_listener(self):
+ """
+ test method for update load balancer listener objects
+ """
+ lb_listener_uuid = self._create_load_balancer_listener()
+ with self.rbac_utils.override_role(self):
+ self._update_load_balancer_listener(lb_listener_uuid)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="delete_load_balancer_listener")
+ @idempotent_id('feaf3e9a-ffd1-4327-ad7a-35f9e9e4989b')
+ def test_delete_lb_listener(self):
+ """
+ test method for delete load balancer listener objects
+ """
+ lb_listener_uuid = self._create_load_balancer_listener()
+ with self.rbac_utils.override_role(self):
+ self.load_balancer_client.delete_load_balancer_listener(
+ lb_listener_uuid)
+
+
+class LoadBalancerPoolContrailTest(BaseLoadBalancerTest):
+
+ """
+ Base class to test load balancer Pool objects using RBAC roles
+ """
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="list_load_balancer_pools")
+ @idempotent_id('3d177a9e-7067-4e9e-b4e8-0acc5887dff0')
+ def test_list_load_balancer_pools(self):
+ """
+ test method for list load balancer pool objects
+ """
+ with self.rbac_utils.override_role(self):
+ self.load_balancer_client.list_load_balancer_pools()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="create_load_balancer_pools")
+ @idempotent_id('a52c6ec7-a996-4191-9a70-7879a211a711')
+ def test_create_load_balancer_pools(self):
+ """
+ test method for create load balancer pool objects
+ """
+ with self.rbac_utils.override_role(self):
+ self._create_load_balancer_pool()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="show_load_balancer_pool")
+ @idempotent_id('7923da4e-53b1-4024-9a40-5bc91cee8e2d')
+ def test_show_load_balancer_pool(self):
+ """
+ test method for show load balancer pool objects
+ """
+ lb_pool_uuid = self._create_load_balancer_pool()
+ with self.rbac_utils.override_role(self):
+ self.load_balancer_client.show_load_balancer_pool(lb_pool_uuid)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="update_load_balancer_pool")
+ @idempotent_id('391c0c5e-c218-4c98-9b58-6d2724ec4c20')
+ def test_update_load_balancer_pool(self):
+ """
+ test method for update load balancer pool objects
+ """
+ lb_pool_uuid = self._create_load_balancer_pool()
+ with self.rbac_utils.override_role(self):
+ self._update_load_balancer_pool(lb_pool_uuid)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="delete_load_balancer_pool")
+ @idempotent_id('8b3617c0-4064-48f8-96b8-e2f996fce5c3')
+ def test_delete_load_balancer_pool(self):
+ """
+ test method for delete load balancer pool objects
+ """
+ lb_pool_uuid = self._create_load_balancer_pool()
+ with self.rbac_utils.override_role(self):
+ self.load_balancer_client.delete_load_balancer_pool(lb_pool_uuid)
+
+
+class LoadBalancerMemberContrailTest(BaseLoadBalancerTest):
+
+ """
+ Base class to test load balancer Member using RBAC roles
+ """
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="list_load_balancer_members")
+ @idempotent_id('b3c51463-8166-486a-a26e-0f7aeaa41e0f')
+ def test_list_load_balancer_members(self):
+ """
+ test method for list load balancer member objects
+ """
+ with self.rbac_utils.override_role(self):
+ self.load_balancer_client.list_load_balancer_members()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="create_load_balancer_members")
+ @idempotent_id('ad60688f-7a20-4dd5-8229-4076d85b9d55')
+ def test_create_lb_members(self):
+ """
+ test method for create load balancer member objects
+ """
+ with self.rbac_utils.override_role(self):
+ self._create_load_balancer_member()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="show_load_balancer_member")
+ @idempotent_id('917602ff-24d5-4a07-a6a6-5e5b9539bbf1')
+ def test_show_load_balancer_member(self):
+ """
+ test method for show load balancer member objects
+ """
+ lb_member_uuid = self._create_load_balancer_member()
+ with self.rbac_utils.override_role(self):
+ self.load_balancer_client.show_load_balancer_member(lb_member_uuid)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="update_load_balancer_member")
+ @idempotent_id('b1611005-5c77-4ac0-8fcc-4a035dfbaa84')
+ def test_update_lb_member(self):
+ """
+ test method for update load balancer member objects
+ """
+ lb_member_uuid = self._create_load_balancer_member()
+ with self.rbac_utils.override_role(self):
+ self._update_load_balancer_member(lb_member_uuid)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="delete_load_balancer_member")
+ @idempotent_id('dc21883a-a822-4d39-b815-4dfd6b505b0b')
+ def test_delete_lb_member(self):
+ """
+ test method for delete load balancer member objects
+ """
+ lb_member_uuid = self._create_load_balancer_member()
+ with self.rbac_utils.override_role(self):
+ self.load_balancer_client.delete_load_balancer_member(
+ lb_member_uuid)
diff --git a/tungsten_tempest_plugin/tests/api/contrail/test_namespace.py b/tungsten_tempest_plugin/tests/api/contrail/test_namespace.py
new file mode 100644
index 0000000..fcab56e
--- /dev/null
+++ b/tungsten_tempest_plugin/tests/api/contrail/test_namespace.py
@@ -0,0 +1,111 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest test-case to test namespace objects using RBAC roles
+"""
+
+
+from oslo_log import log as logging
+
+from tungsten_tempest_plugin.tests.api.contrail import rbac_base
+
+from patrole_tempest_plugin import rbac_rule_validation
+
+from tempest import config
+from tempest.lib.common.utils import data_utils
+from tempest.lib.decorators import idempotent_id
+
+CONF = config.CONF
+LOG = logging.getLogger(__name__)
+
+
+class NamespaceContrailTest(rbac_base.BaseContrailTest):
+
+ """
+ Test class to test namespace objects using RBAC roles
+ """
+
+ def _create_namespace(self):
+ fq_name = data_utils.rand_name('namespace')
+ post_body = {
+ 'parent_type': 'domain',
+ 'fq_name': ['default-domain', fq_name]
+ }
+ resp_body = self.namespace_client.create_namespaces(**post_body)
+ namespace_uuid = resp_body['namespace']['uuid']
+ self.addCleanup(self._try_delete_resource,
+ self.namespace_client.delete_namespace,
+ namespace_uuid)
+ return namespace_uuid
+
+ def _update_namespace(self, namespace_uuid):
+ put_body = {
+ 'display_name': data_utils.rand_name('namespace')
+ }
+ self.namespace_client.update_namespace(namespace_uuid, **put_body)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="list_namespaces")
+ @idempotent_id('e436390d-d669-4047-9838-421ea93e94be')
+ def test_list_namespaces(self):
+ """
+ test method for list namespace objects
+ """
+ with self.rbac_utils.override_role(self):
+ self.namespace_client.list_namespaces()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="create_namespaces")
+ @idempotent_id('503ae445-7e67-4db6-989a-af0b7f9a7e95')
+ def test_create_namespaces(self):
+ """
+ test method for create namespace objects
+ """
+ with self.rbac_utils.override_role(self):
+ self._create_namespace()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="show_namespace")
+ @idempotent_id('f916971a-7c07-4386-b887-8b78d8a1e528')
+ def test_show_namespace(self):
+ """
+ test method for show namespace objects
+ """
+ namespace_uuid = self._create_namespace()
+ with self.rbac_utils.override_role(self):
+ self.namespace_client.show_namespace(namespace_uuid)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="update_namespace")
+ @idempotent_id('3649f65a-922a-4b8a-9b8b-520c333e192e')
+ def test_update_namespace(self):
+ """
+ test method for update namespace objects
+ """
+ namespace_uuid = self._create_namespace()
+ with self.rbac_utils.override_role(self):
+ self._update_namespace(namespace_uuid)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="delete_namespace")
+ @idempotent_id('80e736bf-fc7d-4274-8173-a50c883776a9')
+ def test_delete_namespace(self):
+ """
+ test method for delete namespace objects
+ """
+ namespace_uuid = self._create_namespace()
+ with self.rbac_utils.override_role(self):
+ self.namespace_client.delete_namespace(namespace_uuid)
diff --git a/tungsten_tempest_plugin/tests/api/contrail/test_network_ipams.py b/tungsten_tempest_plugin/tests/api/contrail/test_network_ipams.py
new file mode 100644
index 0000000..9abddc6
--- /dev/null
+++ b/tungsten_tempest_plugin/tests/api/contrail/test_network_ipams.py
@@ -0,0 +1,101 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest test-case to test network ipam objects using RBAC roles
+"""
+
+from tungsten_tempest_plugin.tests.api.contrail import rbac_base
+
+from patrole_tempest_plugin import rbac_rule_validation
+
+from tempest import config
+from tempest.lib.common.utils import data_utils
+from tempest.lib.decorators import idempotent_id
+
+CONF = config.CONF
+
+
+class NetworkIpamsTest(rbac_base.BaseContrailTest):
+
+ """
+ Test class to test network ipam objects using RBAC roles
+ """
+
+ def _create_network_ipams(self):
+ ipam_name = data_utils.rand_name('test-ipam')
+ ipam_fq_name = ['default-domain', self.tenant_name, ipam_name]
+ new_ipam = self.network_ipams_client.create_network_ipams(
+ parent_type='project',
+ fq_name=ipam_fq_name)['network-ipam']
+ self.addCleanup(self._try_delete_resource,
+ self.network_ipams_client.delete_network_ipam,
+ new_ipam['uuid'])
+ return new_ipam
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="list_network_ipams")
+ @idempotent_id('9ee2c4d8-3209-4ef8-86e1-0ecea2d4c5f2')
+ def test_list_network_ipams(self):
+ """
+ test method for list n/w ipam objects
+ """
+ with self.rbac_utils.override_role(self):
+ self.network_ipams_client.list_network_ipams()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="create_network_ipams")
+ @idempotent_id('ef2415ea-0810-413a-85a0-4508c9d7af91')
+ def test_create_network_ipams(self):
+ """
+ test method for create n/w ipam objects
+ """
+ with self.rbac_utils.override_role(self):
+ self._create_network_ipams()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="show_network_ipam")
+ @idempotent_id('527b19e5-068a-44e3-b175-b504eafeec6e')
+ def test_show_network_ipam(self):
+ """
+ test method for show n/w ipam objects
+ """
+ new_ipam = self._create_network_ipams()
+ with self.rbac_utils.override_role(self):
+ self.network_ipams_client.show_network_ipam(new_ipam['uuid'])
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="delete_network_ipam")
+ @idempotent_id('118c1620-efb6-4cc6-8eb5-71bf8631d365')
+ def test_delete_network_ipam(self):
+ """
+ test method for delete n/w ipam objects
+ """
+ new_ipam = self._create_network_ipams()
+ with self.rbac_utils.override_role(self):
+ self.network_ipams_client.delete_network_ipam(new_ipam['uuid'])
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="update_network_ipam")
+ @idempotent_id('44cbe2d9-583d-4215-964a-1c321f5e8d92')
+ def test_update_network_ipam(self):
+ """
+ test method for update n/w ipam objects
+ """
+ new_ipam = self._create_network_ipams()
+ with self.rbac_utils.override_role(self):
+ self.network_ipams_client.update_network_ipam(
+ new_ipam['uuid'],
+ display_name=data_utils.rand_name('test-ipam'))
diff --git a/tungsten_tempest_plugin/tests/api/contrail/test_network_policy.py b/tungsten_tempest_plugin/tests/api/contrail/test_network_policy.py
new file mode 100644
index 0000000..10abc2a
--- /dev/null
+++ b/tungsten_tempest_plugin/tests/api/contrail/test_network_policy.py
@@ -0,0 +1,112 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest test-case to test network policy objects using RBAC roles
+"""
+
+from oslo_log import log as logging
+
+from tungsten_tempest_plugin.tests.api.contrail import rbac_base
+
+from patrole_tempest_plugin import rbac_rule_validation
+
+from tempest import config
+from tempest.lib.common.utils import data_utils
+from tempest.lib.decorators import idempotent_id
+
+CONF = config.CONF
+LOG = logging.getLogger(__name__)
+
+
+class NetworkPolicyTest(rbac_base.BaseContrailTest):
+
+ """
+ Test class to test network policy objects using RBAC roles
+ """
+
+ def _create_policy(self):
+ fq_name = data_utils.rand_name('network-policy')
+ post_body = {
+ 'parent_type': 'project',
+ 'fq_name': ["default-domain", self.tenant_name, fq_name]
+ }
+ resp_body = self.network_policy_client.create_network_policys(
+ **post_body)
+ network_policy_uuid = resp_body['network-policy']['uuid']
+ self.addCleanup(self._try_delete_resource,
+ self.network_policy_client.delete_network_policy,
+ network_policy_uuid)
+ return network_policy_uuid
+
+ def _update_policy(self, network_policy_uuid):
+ put_body = {
+ 'display_name': data_utils.rand_name('network-policy')
+ }
+ self.network_policy_client.update_network_policy(network_policy_uuid,
+ **put_body)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="list_network_policys")
+ @idempotent_id('fa2a28f3-a8bb-4908-95b9-1e11cf58b16f')
+ def test_list_policys(self):
+ """
+ test method for list n/w policy objects
+ """
+ with self.rbac_utils.override_role(self):
+ self.network_policy_client.list_network_policys()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="create_network_policys")
+ @idempotent_id('a30be228-afba-40c9-8678-ae020db68d79')
+ def test_create_network_policys(self):
+ """
+ test method for create n/w policy objects
+ """
+ with self.rbac_utils.override_role(self):
+ self._create_policy()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="show_network_policy")
+ @idempotent_id('6cefe92e-8936-49a6-bce0-12da3396e7ab')
+ def test_show_network_policy(self):
+ """
+ test method for show n/w policy objects
+ """
+ policy_uuid = self._create_policy()
+ with self.rbac_utils.override_role(self):
+ self.network_policy_client.show_network_policy(policy_uuid)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="update_network_policy")
+ @idempotent_id('1d470505-3ad4-4870-87d7-3f0b0f9fc635')
+ def test_update_network_policy(self):
+ """
+ test method for update n/w policy objects
+ """
+ policy_uuid = self._create_policy()
+ with self.rbac_utils.override_role(self):
+ self._update_policy(policy_uuid)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="delete_network_policy")
+ @idempotent_id('aae9018f-e7a2-4a75-a68e-afd6c380640e')
+ def test_delete_network_policy(self):
+ """
+ test method for delete n/w policy objects
+ """
+ policy_uuid = self._create_policy()
+ with self.rbac_utils.override_role(self):
+ self.network_policy_client.delete_network_policy(policy_uuid)
diff --git a/tungsten_tempest_plugin/tests/api/contrail/test_port_tuple.py b/tungsten_tempest_plugin/tests/api/contrail/test_port_tuple.py
new file mode 100644
index 0000000..34ee131
--- /dev/null
+++ b/tungsten_tempest_plugin/tests/api/contrail/test_port_tuple.py
@@ -0,0 +1,130 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest test-case to test port tuple objects using RBAC roles
+"""
+
+from oslo_log import log as logging
+
+from tungsten_tempest_plugin.tests.api.contrail import rbac_base
+
+from patrole_tempest_plugin import rbac_rule_validation
+
+from tempest import config
+from tempest.lib.common.utils import data_utils
+from tempest.lib.decorators import idempotent_id
+
+CONF = config.CONF
+LOG = logging.getLogger(__name__)
+
+
+class ContrailPortTupleTest(rbac_base.BaseContrailTest):
+
+ """
+ Test class to test port tuple objects using RBAC roles
+ """
+
+ @classmethod
+ def resource_setup(cls):
+ super(ContrailPortTupleTest, cls).resource_setup()
+ instance_name = data_utils.rand_name('port-tuple-service-instance')
+ domain_name = 'default-domain'
+ parent_type = 'project'
+ instance_fq_name = ['default-domain', cls.tenant_name, instance_name]
+ cls.service_instance = \
+ cls.service_client.create_service_instances(
+ domain_name=domain_name,
+ fq_name=instance_fq_name,
+ display_name=instance_name,
+ parent_type=parent_type)['service-instance']
+
+ @classmethod
+ def resource_cleanup(cls):
+ cls._try_delete_resource(cls.service_client.delete_service_instance,
+ cls.service_instance['uuid'])
+ super(ContrailPortTupleTest, cls).resource_cleanup()
+
+ def _create_port_tuple(self):
+ tuple_name = data_utils.rand_name('port-tuple')
+ fq_name = ['default-domain',
+ self.tenant_name,
+ self.service_instance['name'],
+ tuple_name]
+ post_data = {
+ 'fq_name': fq_name,
+ 'parent_type': 'service-instance',
+ }
+ new_tuple = self.port_tuple_client.create_port_tuples(
+ **post_data)['port-tuple']
+ self.addCleanup(self._try_delete_resource,
+ self.port_tuple_client.delete_port_tuple,
+ new_tuple['uuid'])
+ return new_tuple
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="list_port_tuples")
+ @idempotent_id('3789eef8-0e80-4057-b7b0-926655144beb')
+ def test_list_port_tuples(self):
+ """
+ test method for list port tuple objects
+ """
+ with self.rbac_utils.override_role(self):
+ self.port_tuple_client.list_port_tuples()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="show_port_tuple")
+ @idempotent_id('ae5a90ed-5771-4680-be6b-c7626caa3a52')
+ def test_show_port_tuple(self):
+ """
+ test method for show port tuple objects
+ """
+ new_tuple = self._create_port_tuple()
+ with self.rbac_utils.override_role(self):
+ self.port_tuple_client.show_port_tuple(new_tuple['uuid'])
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="create_port_tuples")
+ @idempotent_id('0e2283da-fe25-4204-b5b3-fef3c200d0c8')
+ def test_create_port_tuples(self):
+ """
+ test method for create port tuple objects
+ """
+ with self.rbac_utils.override_role(self):
+ self._create_port_tuple()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="update_port_tuple")
+ @idempotent_id('b16f19e2-ec8e-4107-961d-561890183dd0')
+ def test_update_port_tuple(self):
+ """
+ test method for update port tuple objects
+ """
+ new_tuple = self._create_port_tuple()
+ update_name = data_utils.rand_name('updated_tuple')
+ with self.rbac_utils.override_role(self):
+ self.port_tuple_client.update_port_tuple(
+ new_tuple['uuid'], display_name=update_name)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="delete_port_tuple")
+ @idempotent_id('3f28e8b8-f9de-437f-a398-0a11c7fcd652')
+ def test_delete_port_tuple(self):
+ """
+ test method for delete port tuple objects
+ """
+ new_tuple = self._create_port_tuple()
+ with self.rbac_utils.override_role(self):
+ self.port_tuple_client.delete_port_tuple(new_tuple['uuid'])
diff --git a/tungsten_tempest_plugin/tests/api/contrail/test_project.py b/tungsten_tempest_plugin/tests/api/contrail/test_project.py
new file mode 100644
index 0000000..30312c5
--- /dev/null
+++ b/tungsten_tempest_plugin/tests/api/contrail/test_project.py
@@ -0,0 +1,111 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest test-case to test project objects using RBAC roles
+"""
+
+from oslo_log import log as logging
+
+from tungsten_tempest_plugin.tests.api.contrail import rbac_base
+
+from patrole_tempest_plugin import rbac_rule_validation
+
+from tempest import config
+from tempest.lib.common.utils import data_utils
+from tempest.lib.decorators import idempotent_id
+
+CONF = config.CONF
+LOG = logging.getLogger(__name__)
+
+
+class ProjectContrailTest(rbac_base.BaseContrailTest):
+
+ """
+ Test class to test project objects using RBAC roles
+ """
+
+ def _create_project(self):
+ fq_name = data_utils.rand_name('project')
+ post_body = {
+ 'parent_type': 'domain',
+ 'fq_name': ['default-domain', fq_name]
+ }
+ resp_body = self.project_client.create_projects(
+ **post_body)
+ project_uuid = resp_body['project']['uuid']
+ self.addCleanup(self._try_delete_resource,
+ self.project_client.delete_project,
+ project_uuid)
+ return project_uuid
+
+ def _update_project(self, project_uuid):
+ put_body = {
+ 'display_name': data_utils.rand_name('project')
+ }
+ self.project_client.update_project(project_uuid, **put_body)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="list_projects")
+ @idempotent_id('7db819fd-ceee-4a6b-9ad7-2e837c055bdd')
+ def test_list_projects(self):
+ """
+ test method for list project objects
+ """
+ with self.rbac_utils.override_role(self):
+ self.project_client.list_projects()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="create_projects")
+ @idempotent_id('38b9b7a8-1568-417d-b0a3-e7adee88e4b9')
+ def test_create_projects(self):
+ """
+ test method for create project objects
+ """
+ with self.rbac_utils.override_role(self):
+ self._create_project()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="show_project")
+ @idempotent_id('c47e57c4-34b0-46c2-a678-83b1fe9afd25')
+ def test_show_project(self):
+ """
+ test method for show project objects
+ """
+ project_uuid = self._create_project()
+ with self.rbac_utils.override_role(self):
+ self.project_client.show_project(project_uuid)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="update_project")
+ @idempotent_id('3d4bd416-16cc-437c-9e95-f9ceda424f8b')
+ def test_update_project(self):
+ """
+ test method for update project objects
+ """
+ project_uuid = self._create_project()
+ with self.rbac_utils.override_role(self):
+ self._update_project(project_uuid)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="delete_project")
+ @idempotent_id('787ebe8b-b88d-4488-b157-f70554bdd783')
+ def test_delete_project(self):
+ """
+ test method for delete project objects
+ """
+ project_uuid = self._create_project()
+ with self.rbac_utils.override_role(self):
+ self.project_client.delete_project(project_uuid)
diff --git a/tungsten_tempest_plugin/tests/api/contrail/test_qos_config.py b/tungsten_tempest_plugin/tests/api/contrail/test_qos_config.py
new file mode 100644
index 0000000..ab6d783
--- /dev/null
+++ b/tungsten_tempest_plugin/tests/api/contrail/test_qos_config.py
@@ -0,0 +1,110 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest test-case to test QoS config objects using RBAC roles
+"""
+
+from oslo_log import log as logging
+
+from tungsten_tempest_plugin.tests.api.contrail import rbac_base
+
+from patrole_tempest_plugin import rbac_rule_validation
+
+from tempest import config
+from tempest.lib.common.utils import data_utils
+from tempest.lib.decorators import idempotent_id
+
+LOG = logging.getLogger(__name__)
+CONF = config.CONF
+
+
+class QosConfigContrailTest(rbac_base.BaseContrailTest):
+
+ """
+ Test class to test QoS config objects using RBAC roles
+ """
+
+ def _delete_qos_config(self, qos_config_id):
+ self.qos_client.delete_qos_config(qos_config_id)
+
+ def _create_qos_configs(self):
+ name = data_utils.rand_name('test-rbac-qos-config')
+ parent_type = 'project'
+ fq_name = ['default-domain', self.tenant_name, name]
+ qos_config = self.qos_client.create_qos_configs(
+ fq_name=fq_name,
+ parent_type=parent_type)['qos-config']
+ self.addCleanup(self._try_delete_resource,
+ self._delete_qos_config,
+ qos_config['uuid'])
+ return qos_config
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="list_qos_configs")
+ @idempotent_id('6bc44b34-14d4-4e0e-b45d-fe3df047879f')
+ def test_list_qos_configs(self):
+ """
+ test method for list QoS config objects
+ """
+ self._create_qos_configs()
+ with self.rbac_utils.override_role(self):
+ self.qos_client.list_qos_configs()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="create_qos_configs")
+ @idempotent_id('031b4a27-22cd-4d93-938d-ba6d0f3163ba')
+ def test_create_qos_configs(self):
+ """
+ test method for create QoS config objects
+ """
+ with self.rbac_utils.override_role(self):
+ self._create_qos_configs()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="show_qos_config")
+ @idempotent_id('a9d82b49-3492-4667-b252-ef30b0ee6eb3')
+ def test_show_qos_config(self):
+ """
+ test method for show QoS config objects
+ """
+ qos_config = self._create_qos_configs()
+ with self.rbac_utils.override_role(self):
+ self.qos_client.show_qos_config(qos_config['uuid'])
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="delete_qos_config")
+ @idempotent_id('d324a5e6-cc86-4444-91a2-74592283a7ec')
+ def test_delete_qos_config(self):
+ """
+ test method for delete QoS config objects
+ """
+ qos_config = self._create_qos_configs()
+ with self.rbac_utils.override_role(self):
+ self.qos_client.delete_qos_config(qos_config['uuid'])
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="update_qos_config")
+ @idempotent_id('7f1901a5-0cf0-40bd-98a5-f8a930b11cfe')
+ def test_update_qos_config(self):
+ """
+ test method for update QoS config objects
+ """
+ qos_config = self._create_qos_configs()
+ display_name = data_utils.rand_name('qos_config')
+ with self.rbac_utils.override_role(self):
+ self.qos_client.update_qos_config(
+ qos_config_id=qos_config['uuid'],
+ display_name=display_name)
diff --git a/tungsten_tempest_plugin/tests/api/contrail/test_qos_global_config.py b/tungsten_tempest_plugin/tests/api/contrail/test_qos_global_config.py
new file mode 100644
index 0000000..a6e8f82
--- /dev/null
+++ b/tungsten_tempest_plugin/tests/api/contrail/test_qos_global_config.py
@@ -0,0 +1,141 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest test-case to test QoS config objects using RBAC roles
+"""
+
+from oslo_log import log as logging
+
+from tungsten_tempest_plugin.tests.api.contrail import rbac_base
+
+from patrole_tempest_plugin import rbac_rule_validation
+
+from tempest import config
+from tempest.lib.common.utils import data_utils
+from tempest.lib.decorators import idempotent_id
+
+LOG = logging.getLogger(__name__)
+CONF = config.CONF
+
+
+class QosContrailTest(rbac_base.BaseContrailTest):
+
+ """
+ Test class to test QoS Config objects using RBAC roles
+ """
+
+ @classmethod
+ def resource_setup(cls):
+ super(QosContrailTest, cls).resource_setup()
+
+ def _create_global_system_config(self):
+ config_name = data_utils.rand_name('test-config')
+ parent_type = 'config-root'
+ config_fq_name = [config_name]
+ new_config = \
+ self.config_client.create_global_system_configs(
+ parent_type=parent_type,
+ display_name=config_name,
+ fq_name=config_fq_name)['global-system-config']
+ self.addCleanup(self._try_delete_resource,
+ (self.config_client.
+ delete_global_system_config),
+ new_config['uuid'])
+ return new_config
+
+ def _delete_qos_global_config(self, instance_id):
+ return self.qos_client.delete_global_qos_config(instance_id)
+
+ def _create_qos_global_configs(self, global_system_config):
+ name = data_utils.rand_name('test-rbac-qos-global-config')
+ parent_type = 'global-system-config'
+ fq_name = [global_system_config, name]
+ qos_global_config = self.qos_client.create_global_qos_configs(
+ fq_name=fq_name,
+ parent_type=parent_type)['global-qos-config']
+
+ self.addCleanup(self._try_delete_resource,
+ self._delete_qos_global_config,
+ qos_global_config['uuid'])
+ return qos_global_config
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="list_global_qos_configs")
+ @idempotent_id('74e5a7b7-f538-4be3-90a5-6862b07fb118')
+ def test_list_global_qos_configs(self):
+ """
+ test method for list global QoS objects
+ """
+ # Create global system config
+ global_system_config = self._create_global_system_config()['name']
+ self._create_qos_global_configs(global_system_config)
+ with self.rbac_utils.override_role(self):
+ self.qos_client.list_global_qos_configs()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="create_global_qos_configs")
+ @idempotent_id('d7da1ca0-7bf7-4d1b-982c-820cd37fe9fa')
+ def test_create_global_qos_configs(self):
+ """
+ test method for create global QoS objects
+ """
+ # Create global system config
+ global_system_config = self._create_global_system_config()['name']
+ with self.rbac_utils.override_role(self):
+ self._create_qos_global_configs(global_system_config)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="show_global_qos_config")
+ @idempotent_id('e3bd44e0-19a9-46e7-83d3-268dcc537ad9')
+ def test_show_global_qos_config(self):
+ """
+ test method for show global QoS objects
+ """
+ # Create global system config
+ global_system_config = self._create_global_system_config()['name']
+ test = self._create_qos_global_configs(global_system_config)
+ with self.rbac_utils.override_role(self):
+ self.qos_client.show_global_qos_config(instance_id=test['uuid'])
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="update_global_qos_config")
+ @idempotent_id('f834c4d7-bc81-4c59-bada-c4d752219a6e')
+ def test_update_global_qos_config(self):
+ """
+ test method for update global QoS objects
+ """
+ # Create global system config
+ global_system_config = self._create_global_system_config()['name']
+ qos = self._create_qos_global_configs(global_system_config)
+ display_name = data_utils.rand_name('qos_globale_config')
+ with self.rbac_utils.override_role(self):
+ self.qos_client.update_global_qos_config(
+ instance_id=qos['uuid'],
+ display_name=display_name)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="delete_global_qos_config")
+ @idempotent_id('78b9a3da-4eb1-4f4b-8a23-a8a2e733b515')
+ def test_delete_global_qos_config(self):
+ """
+ test method for delete global QoS objects
+ """
+ # Create global system config
+ global_system_config = self._create_global_system_config()['name']
+ qos_global_config = self._create_qos_global_configs(
+ global_system_config)
+ with self.rbac_utils.override_role(self):
+ self.qos_client.delete_global_qos_config(qos_global_config['uuid'])
diff --git a/tungsten_tempest_plugin/tests/api/contrail/test_qos_queue.py b/tungsten_tempest_plugin/tests/api/contrail/test_qos_queue.py
new file mode 100644
index 0000000..753a9ba
--- /dev/null
+++ b/tungsten_tempest_plugin/tests/api/contrail/test_qos_queue.py
@@ -0,0 +1,108 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest test-case to test QoS Queue using RBAC roles
+"""
+
+from oslo_log import log as logging
+
+from tungsten_tempest_plugin.tests.api.contrail import rbac_base
+
+from patrole_tempest_plugin import rbac_rule_validation
+
+from tempest import config
+from tempest.lib.common.utils import data_utils
+from tempest.lib.decorators import idempotent_id
+
+LOG = logging.getLogger(__name__)
+CONF = config.CONF
+
+
+class QosQueueContrailTest(rbac_base.BaseContrailTest):
+
+ """
+ Test class to test QoS Queue using RBAC roles
+ """
+
+ def _delete_qos_queue(self, qos_queue_id):
+ self.qos_client.delete_qos_queue(qos_queue_id)
+
+ def _create_qos_queues(self):
+ name = data_utils.rand_name('test-rbac-qos-queue')
+ fq_name = [name]
+ qos_queue = self.qos_client.create_qos_queues(
+ fq_name=fq_name)['qos-queue']
+ self.addCleanup(self._try_delete_resource,
+ self._delete_qos_queue,
+ qos_queue['uuid'])
+ return qos_queue
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="list_qos_queues")
+ @idempotent_id('3d3a4397-2afe-4bbd-be59-56a1bcc2e49d')
+ def test_list_qos_queues(self):
+ """
+ test method for listing QoS queues
+ """
+ self._create_qos_queues()
+ with self.rbac_utils.override_role(self):
+ self.qos_client.list_qos_queues()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="create_qos_queues")
+ @idempotent_id('d89c45f4-c83c-47b3-8720-7feffab4519c')
+ def test_create_qos_queues(self):
+ """
+ test method for creating QoS queues
+ """
+ with self.rbac_utils.override_role(self):
+ self._create_qos_queues()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="show_qos_queue")
+ @idempotent_id('d2773d5c-9858-4938-8a77-62cafd5034da')
+ def test_show_qos_queue(self):
+ """
+ test method for showing QoS queues
+ """
+ qos_queue = self._create_qos_queues()
+ with self.rbac_utils.override_role(self):
+ self.qos_client.show_qos_queue(qos_queue['uuid'])
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="delete_qos_queue")
+ @idempotent_id('64c828d0-6594-472b-a504-40915067c7bd')
+ def test_delete_qos_queue(self):
+ """
+ test method for deleting QoS queues
+ """
+ qos_queue = self._create_qos_queues()
+ with self.rbac_utils.override_role(self):
+ self.qos_client.delete_qos_queue(qos_queue['uuid'])
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="update_qos_queue")
+ @idempotent_id('0733ab1a-f5aa-4e70-a011-174aa203dc33')
+ def test_update_qos_queue(self):
+ """
+ test method for deleting QoS queues
+ """
+ qos_queue = self._create_qos_queues()
+ display_name = data_utils.rand_name('qos_queue')
+ with self.rbac_utils.override_role(self):
+ self.qos_client.update_qos_queue(
+ qos_queue_id=qos_queue['uuid'],
+ display_name=display_name)
diff --git a/tungsten_tempest_plugin/tests/api/contrail/test_route.py b/tungsten_tempest_plugin/tests/api/contrail/test_route.py
new file mode 100644
index 0000000..db1b53f
--- /dev/null
+++ b/tungsten_tempest_plugin/tests/api/contrail/test_route.py
@@ -0,0 +1,358 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest test-case to test route objects using RBAC roles
+"""
+
+import random
+
+from oslo_log import log as logging
+
+from tungsten_tempest_plugin.tests.api.contrail import rbac_base
+
+from patrole_tempest_plugin import rbac_rule_validation
+
+from tempest import config
+from tempest.lib.common.utils import data_utils
+from tempest.lib.decorators import idempotent_id
+
+CONF = config.CONF
+LOG = logging.getLogger(__name__)
+
+
+class ContrailRouteTableTest(rbac_base.BaseContrailTest):
+
+ """
+ Test class to test route objects using RBAC roles
+ """
+
+ def _delete_route_table(self, route_id):
+ self.route_client.delete_route_table(route_id)
+
+ def _create_route_tables(self):
+ parent_type = 'project'
+ fq_name = ['default-domain', self.tenant_name,
+ data_utils.rand_name('Route')]
+ route_table = self.route_client.create_route_tables(
+ fq_name=fq_name,
+ parent_type=parent_type)['route-table']
+ self.addCleanup(self._try_delete_resource,
+ self._delete_route_table,
+ route_table['uuid'])
+ return route_table
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="list_route_tables")
+ @idempotent_id('ca5a5d42-6e49-40e4-a5ac-de07b397b775')
+ def test_list_route_tables(self):
+ """
+ test method for list route table objects
+ """
+ self._create_route_tables()
+ with self.rbac_utils.override_role(self):
+ self.route_client.list_route_tables()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="show_route_table")
+ @idempotent_id('084a2759-991a-4ae2-bde4-8f9915966f6e')
+ def test_show_route_table(self):
+ """
+ test method for show route table objects
+ """
+ route_table = self._create_route_tables()
+ with self.rbac_utils.override_role(self):
+ self.route_client.show_route_table(route_table['uuid'])
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="create_route_tables")
+ @idempotent_id('3fab8105-c0be-4c9e-be5f-d2dce4deb921')
+ def test_create_route_tables(self):
+ """
+ test method for create route table objects
+ """
+ with self.rbac_utils.override_role(self):
+ self._create_route_tables()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="update_route_table")
+ @idempotent_id('2acee7ad-843e-40b0-b8f8-a6d90a51c6c8')
+ def test_update_route_table(self):
+ """
+ test method for update route table objects
+ """
+ route_table = self._create_route_tables()
+ display_name = data_utils.rand_name('RouteNew')
+ with self.rbac_utils.override_role(self):
+ self.route_client.update_route_table(
+ route_id=route_table['uuid'],
+ display_name=display_name)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="delete_route_table")
+ @idempotent_id('20a5086c-ec9a-43e0-ae2c-4161c0f4b280')
+ def test_delete_route_table(self):
+ """
+ test method for delete route table objects
+ """
+ route_table = self._create_route_tables()
+ with self.rbac_utils.override_role(self):
+ self._delete_route_table(route_table['uuid'])
+
+
+class ContrailInterfaceRouteTableTest(rbac_base.BaseContrailTest):
+
+ """
+ Test class to test route interface table using RBAC roles
+ """
+
+ def _delete_interface_route_table(self, route_id):
+ self.route_client.delete_interface_route_table(route_id)
+
+ def _create_interface_route_tables(self):
+ parent_type = 'project'
+ fq_name = ['default-domain',
+ self.tenant_name,
+ data_utils.rand_name('InterfaceRoute')]
+ interface_route_table = self.route_client \
+ .create_interface_route_tables(
+ fq_name=fq_name,
+ parent_type=parent_type)['interface-route-table']
+ self.addCleanup(self._try_delete_resource,
+ self._delete_interface_route_table,
+ interface_route_table['uuid'])
+ return interface_route_table
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="list_interface_route_tables")
+ @idempotent_id('b1f8f0a6-6074-4615-a439-19869a48bc49')
+ def test_list_interface_route(self):
+ """
+ test method for list route interface table objects
+ """
+ self._create_interface_route_tables()
+ with self.rbac_utils.override_role(self):
+ self.route_client.list_interface_route_tables()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="show_interface_route_table")
+ @idempotent_id('94703a28-5e33-4003-b95b-6a3cc5752fd4')
+ def test_show_interface_route(self):
+ """
+ test method for show route interface table objects
+ """
+ interface_rte_table = self._create_interface_route_tables()
+ with self.rbac_utils.override_role(self):
+ self.route_client.show_interface_route_table(
+ interface_rte_table['uuid'])
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="create_interface_route_tables")
+ @idempotent_id('b89ef437-4759-4c04-948b-d2ff9675ab07')
+ def test_create_interface_route(self):
+ """
+ test method for create route interface table objects
+ """
+ with self.rbac_utils.override_role(self):
+ self._create_interface_route_tables()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="update_interface_route_table")
+ @idempotent_id('e9346d4f-7a07-41bc-8e88-e8ae9fa309ea')
+ def test_update_interface_route(self):
+ """
+ test method for update route interface table objects
+ """
+ interface_rte_table = self._create_interface_route_tables()
+ display_name = data_utils.rand_name('InterfaceRouteNew')
+ with self.rbac_utils.override_role(self):
+ self.route_client.update_interface_route_table(
+ interface_route_id=interface_rte_table['uuid'],
+ display_name=display_name)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="delete_interface_route_table")
+ @idempotent_id('b00444a5-cb4c-45bc-b393-503e9e333e98')
+ def test_delete_interface_route(self):
+ """
+ test method for delete route interface table objects
+ """
+ interface_rte_table = self._create_interface_route_tables()
+ with self.rbac_utils.override_role(self):
+ self._delete_interface_route_table(
+ interface_rte_table['uuid'])
+
+
+class ContrailRouteTargetsTest(rbac_base.BaseContrailTest):
+
+ """
+ Test class to test route targets using RBAC roles
+ """
+
+ def _delete_route_target(self, target_id):
+ self.route_client.delete_route_target(target_id)
+
+ def _create_route_targets(self):
+ # Contrail have changed way they parse fq_name for route-target.
+ # Details: Route target must be of the format 'target:<asn>:<number>'
+ # or 'target:<ip>:<number>'
+ rand_name = "target:%s:%s" % (random.randint(10000, 99000),
+ random.randint(10000, 99000))
+ fq_name = [rand_name]
+ route_target = self.route_client.create_route_targets(
+ fq_name=fq_name)['route-target']
+ self.addCleanup(self._try_delete_resource,
+ self._delete_route_target,
+ route_target['uuid'])
+ return route_target
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="list_route_targets")
+ @idempotent_id('757efd07-8027-4a16-887a-1e42f16b4140')
+ def test_list_route_targets(self):
+ """
+ test method for list route target objects
+ """
+ self._create_route_targets()
+ with self.rbac_utils.override_role(self):
+ self.route_client.list_route_targets()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="show_route_target")
+ @idempotent_id('76c60d98-dd5e-453a-bf0e-7854f78a1a5e')
+ def test_show_route_target(self):
+ """
+ test method for show route target objects
+ """
+ target = self._create_route_targets()
+ with self.rbac_utils.override_role(self):
+ self.route_client.show_route_target(target['uuid'])
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="create_route_targets")
+ @idempotent_id('fcdb4ebc-b92d-49f2-88e9-68c93aec94be')
+ def test_create_route_targets(self):
+ """
+ test method for create route target objects
+ """
+ with self.rbac_utils.override_role(self):
+ self._create_route_targets()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="update_route_target")
+ @idempotent_id('dd830a77-4bfe-4a8c-b4e9-08b6ef2af3be')
+ def test_update_route_target(self):
+ """
+ test method for update route target objects
+ """
+ target = self._create_route_targets()
+ display_name = data_utils.rand_name('RouteTargetNew')
+ with self.rbac_utils.override_role(self):
+ self.route_client.update_route_target(
+ route_target_id=target['uuid'],
+ display_name=display_name)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="delete_route_target")
+ @idempotent_id('dfaa58f9-ec29-4d51-a475-870fac08908d')
+ def test_delete_route_target(self):
+ """
+ test method for delete route target objects
+ """
+ target = self._create_route_targets()
+ with self.rbac_utils.override_role(self):
+ self._delete_route_target(target['uuid'])
+
+
+class ContrailRouteAggregateTest(rbac_base.BaseContrailTest):
+
+ """
+ Test class to test route aggregate using RBAC roles
+ """
+
+ def _delete_route_aggregate(self, route_aggr_id):
+ self.route_client.delete_route_aggregate(route_aggr_id)
+
+ def _create_route_aggregates(self):
+ parent_type = 'project'
+ fq_name = ['default-domain',
+ self.tenant_name,
+ data_utils.rand_name('RouteAggregate')]
+ route_aggr = self.route_client.create_route_aggregates(
+ fq_name=fq_name,
+ parent_type=parent_type)['route-aggregate']
+ self.addCleanup(self._try_delete_resource,
+ self._delete_route_aggregate,
+ route_aggr['uuid'])
+ return route_aggr
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="list_route_aggregates")
+ @idempotent_id('15f2c30c-4404-4228-94a0-86c5ec5cf62e')
+ def test_list_route_aggregates(self):
+ """
+ test method for list route aggregate objects
+ """
+ self._create_route_aggregates()
+ with self.rbac_utils.override_role(self):
+ self.route_client.list_route_aggregates()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="show_route_aggregate")
+ @idempotent_id('c8edee30-81c4-44e2-8485-055bed853384')
+ def test_show_route_aggregate(self):
+ """
+ test method for show route aggregate objects
+ """
+ route_aggr = self._create_route_aggregates()
+ with self.rbac_utils.override_role(self):
+ self.route_client.show_route_aggregate(
+ route_aggr['uuid'])
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="create_route_aggregates")
+ @idempotent_id('7553a54f-e41c-4555-b745-a858c5a70690')
+ def test_create_route_aggregates(self):
+ """
+ test method for create route aggregate objects
+ """
+ with self.rbac_utils.override_role(self):
+ self._create_route_aggregates()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="update_route_aggregate")
+ @idempotent_id('de1e6102-0bc6-4f9b-a354-48eb051ab5e4')
+ def test_update_route_aggregate(self):
+ """
+ test method for update route aggregate objects
+ """
+ route_aggr = self._create_route_aggregates()
+ display_name = data_utils.rand_name('RouteAggregateNew')
+ with self.rbac_utils.override_role(self):
+ self.route_client.update_route_aggregate(
+ route_aggr_id=route_aggr['uuid'],
+ display_name=display_name)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="delete_route_aggregate")
+ @idempotent_id('e16dbdc6-d7cf-43c7-af9d-bd76cc220200')
+ def test_delete_route_aggregate(self):
+ """
+ test method for delete route aggregate objects
+ """
+ # Create aggregate
+ route_aggr = self._create_route_aggregates()
+ with self.rbac_utils.override_role(self):
+ self._delete_route_aggregate(route_aggr['uuid'])
diff --git a/tungsten_tempest_plugin/tests/api/contrail/test_routers.py b/tungsten_tempest_plugin/tests/api/contrail/test_routers.py
new file mode 100644
index 0000000..fb1daf3
--- /dev/null
+++ b/tungsten_tempest_plugin/tests/api/contrail/test_routers.py
@@ -0,0 +1,466 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest test-case to test project objects using RBAC roles
+"""
+
+from oslo_log import log as logging
+
+from tungsten_tempest_plugin.tests.api.contrail import rbac_base
+
+from patrole_tempest_plugin import rbac_rule_validation
+
+from tempest import config
+from tempest.lib.common.utils import data_utils
+from tempest.lib.decorators import idempotent_id
+
+CONF = config.CONF
+LOG = logging.getLogger(__name__)
+
+
+class BaseRouterTest(rbac_base.BaseContrailTest):
+
+ """
+ Test class to test router objects using RBAC roles
+ """
+
+ @classmethod
+ def resource_setup(cls):
+ super(BaseRouterTest, cls).resource_setup()
+ net_name = data_utils.rand_name('test-net')
+ net_fq_name = ['default-domain', cls.tenant_name, net_name]
+ cls.network = cls.vn_client.create_virtual_networks(
+ parent_type='project',
+ fq_name=net_fq_name)['virtual-network']
+
+ @classmethod
+ def resource_cleanup(cls):
+ cls._try_delete_resource(cls.vn_client.delete_virtual_network,
+ cls.network['uuid'])
+ super(BaseRouterTest, cls).resource_cleanup()
+
+ def _create_global_system_config(self):
+ config_name = data_utils.rand_name('test-config')
+ parent_type = 'config-root'
+ config_fq_name = [config_name]
+ new_config = \
+ self.config_client.create_global_system_configs(
+ parent_type=parent_type,
+ display_name=config_name,
+ fq_name=config_fq_name)['global-system-config']
+ self.addCleanup(self._try_delete_resource,
+ (self.config_client.
+ delete_global_system_config),
+ new_config['uuid'])
+ return new_config
+
+ def _create_physical_router(self, global_system_config):
+ fq_name = data_utils.rand_name('physical-router-template')
+ post_body = {
+ 'parent_type': 'global-system-config',
+ 'fq_name': [global_system_config, fq_name]}
+ router = self.router_client.create_physical_routers(
+ **post_body)['physical-router']
+ self.addCleanup(self._try_delete_resource,
+ self.router_client.delete_physical_router,
+ router['uuid'])
+ return router
+
+ def _create_routing_instances(self):
+ instance_name = data_utils.rand_name('test-instance')
+ instance_fq_name = ['default-domain', self.tenant_name,
+ self.network['name'], instance_name]
+ new_instance = self.routing_client.create_routing_instances(
+ parent_type='virtual-network',
+ fq_name=instance_fq_name)['routing-instance']
+ self.addCleanup(self._try_delete_resource,
+ self.routing_client.delete_routing_instance,
+ new_instance['uuid'])
+ LOG.debug("INSTANCE %s ", new_instance)
+ return new_instance
+
+ def _create_bgp_router(self, instance):
+ fq_name = data_utils.rand_name('bgp-router-template')
+ post_body = {
+ 'parent_type': 'routing-instance',
+ 'fq_name': ['default-domain', self.tenant_name,
+ self.network['name'], instance['name'], fq_name]}
+ router = self.router_client.create_bgp_routers(
+ **post_body)['bgp-router']
+ self.addCleanup(self._try_delete_resource,
+ self.router_client.delete_bgp_router,
+ router['uuid'])
+ return router
+
+ def _create_global_vrouter_config(self, global_system_config):
+ fq_name = data_utils.rand_name('global-vrouter-config-template')
+ post_body = {
+ 'parent_type': 'global-system-config',
+ 'fq_name': [global_system_config, fq_name]}
+ router = self.router_client.create_global_vrouter_configs(
+ **post_body)['global-vrouter-config']
+ self.addCleanup(self._try_delete_resource,
+ self.router_client.delete_global_vrouter_config,
+ router['uuid'])
+ return router
+
+ def _create_logical_router(self):
+ fq_name = data_utils.rand_name('logical-router-template')
+ post_body = {
+ 'parent_type': 'project',
+ 'fq_name': ['default-domain', self.tenant_name, fq_name]}
+ router = self.router_client.create_logical_routers(
+ **post_body)['logical-router']
+ self.addCleanup(self._try_delete_resource,
+ self.router_client.delete_logical_router,
+ router['uuid'])
+ return router
+
+ def _create_virtual_router(self, global_system_config):
+ fq_name = data_utils.rand_name('virtual-router-template')
+ post_body = {
+ 'parent_type': 'global-system-config',
+ 'fq_name': [global_system_config, fq_name]}
+ router = self.router_client.create_virtual_routers(
+ **post_body)['virtual-router']
+ self.addCleanup(self._try_delete_resource,
+ self.router_client.delete_virtual_router,
+ router['uuid'])
+ return router
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="list_physical_routers")
+ @idempotent_id('349ac042-b922-4727-9e1b-8f363ee343f3')
+ def test_list_physical_routers(self):
+ """
+ test method for list physical router objects
+ """
+ with self.rbac_utils.override_role(self):
+ self.router_client.list_physical_routers()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="create_physical_routers")
+ @idempotent_id('d0b7449e-9037-4f9f-8c7e-9f364c95f18a')
+ def test_create_physical_routers(self):
+ """
+ test method for create physical router objects
+ """
+ # Create global system config
+ global_system_config = self._create_global_system_config()['name']
+ with self.rbac_utils.override_role(self):
+ self._create_physical_router(global_system_config)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="show_physical_router")
+ @idempotent_id('6dfc53f4-a884-46d5-b303-22ba59c116f4')
+ def test_show_physical_router(self):
+ """
+ test method for show physical router objects
+ """
+ # Create global system config
+ global_system_config = self._create_global_system_config()['name']
+ physical_router_uuid = self._create_physical_router(
+ global_system_config)['uuid']
+ with self.rbac_utils.override_role(self):
+ self.router_client.show_physical_router(physical_router_uuid)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="update_physical_router")
+ @idempotent_id('c270f369-8cd7-4ee3-8ab1-4580c3138a5c')
+ def test_update_physical_router(self):
+ """
+ test method for update physical router objects
+ """
+ # Create global system config
+ global_system_config = self._create_global_system_config()['name']
+ updated_fq_name = data_utils.rand_name('rbac-physical-router-new-name')
+ physical_router_uuid = self._create_physical_router(
+ global_system_config)['uuid']
+ with self.rbac_utils.override_role(self):
+ self.router_client.update_physical_router(
+ physical_router_uuid,
+ display_name=updated_fq_name)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="delete_physical_router")
+ @idempotent_id('eeded742-6a8d-4e88-bfa8-fe32db463c53')
+ def test_delete_physical_router(self):
+ """
+ test method for delete physical router objects
+ """
+ # Create global system config
+ global_system_config = self._create_global_system_config()['name']
+ physical_router_uuid = self._create_physical_router(
+ global_system_config)['uuid']
+ with self.rbac_utils.override_role(self):
+ self.router_client.delete_physical_router(physical_router_uuid)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="list_bgp_routers")
+ @idempotent_id('49bfb461-f99e-4585-b051-e20a3c937589')
+ def test_list_bgp_routers(self):
+ """
+ test method for list bgp router objects
+ """
+ with self.rbac_utils.override_role(self):
+ self.router_client.list_bgp_routers()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="create_bgp_routers")
+ @idempotent_id('7567974c-040e-4edd-b3a1-c633aa9651cb')
+ def test_create_bgp_routers(self):
+ """
+ test method for create bgp router objects
+ """
+ # Create Routing Instance
+ routing_instance = self._create_routing_instances()
+ with self.rbac_utils.override_role(self):
+ self._create_bgp_router(routing_instance)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="show_bgp_router")
+ @idempotent_id('0d3ad424-18c9-4d96-8708-fa1ebd45594b')
+ def test_show_bgp_router(self):
+ """
+ test method for show bgp router objects
+ """
+ # Create Routing Instance
+ routing_instance = self._create_routing_instances()
+ bgp_router_uuid = self._create_bgp_router(routing_instance)['uuid']
+ with self.rbac_utils.override_role(self):
+ self.router_client.show_bgp_router(bgp_router_uuid)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="update_bgp_router")
+ @idempotent_id('dc50e7c5-7614-4281-8a66-282c52f3c769')
+ def test_update_bgp_router(self):
+ """
+ test method for update bgp router objects
+ """
+ # Create Routing Instance
+ routing_instance = self._create_routing_instances()
+ updated_fq_name = data_utils.rand_name('rbac-bgp-router-new-name')
+ bgp_router_uuid = self._create_bgp_router(routing_instance)['uuid']
+ with self.rbac_utils.override_role(self):
+ self.router_client.update_bgp_router(
+ bgp_router_uuid,
+ display_name=updated_fq_name)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="delete_bgp_router")
+ @idempotent_id('f14aee72-cad4-4c3e-8eea-7886a81abb24')
+ def test_delete_bgp_router(self):
+ """
+ test method for delete bgp router objects
+ """
+ # Create Routing Instance
+ routing_instance = self._create_routing_instances()
+ bgp_router_uuid = self._create_bgp_router(routing_instance)['uuid']
+ with self.rbac_utils.override_role(self):
+ self.router_client.delete_bgp_router(bgp_router_uuid)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="list_global_vrouter_configs")
+ @idempotent_id('4af768d1-3cbe-4aff-bcbc-0e045cac3277')
+ def test_list_global_vrouter(self):
+ """
+ test method for list global vrouter config objects
+ """
+ with self.rbac_utils.override_role(self):
+ self.router_client.list_global_vrouter_configs()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="create_global_vrouter_configs")
+ @idempotent_id('e13d800f-9304-4a06-9bf1-ad08345a13a8')
+ def test_create_global_vrouter(self):
+ """
+ test method for create global vrouter config objects
+ """
+ # Create global system config
+ global_system_config = self._create_global_system_config()['name']
+ with self.rbac_utils.override_role(self):
+ self._create_global_vrouter_config(global_system_config)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="show_global_vrouter_config")
+ @idempotent_id('3bb6f4e1-fd3f-4338-8392-f7f80974a80e')
+ def test_show_global_vrouter_config(self):
+ """
+ test method for show global vrouter config objects
+ """
+ # Create global system config
+ global_system_config = self._create_global_system_config()['name']
+ global_vrouter_config_uuid = self._create_global_vrouter_config(
+ global_system_config)['uuid']
+ with self.rbac_utils.override_role(self):
+ self.router_client.show_global_vrouter_config(
+ global_vrouter_config_uuid)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="update_global_vrouter_config")
+ @idempotent_id('36fcdd51-c42b-4e67-8c26-73d4cde47507')
+ def test_update_global_vrouter(self):
+ """
+ test method for update global vrouter config objects
+ """
+ # Create global system config
+ global_system_config = self._create_global_system_config()['name']
+ updated_fq_name = data_utils.rand_name(
+ 'rbac-global-vrouter-config-new-name')
+ global_vrouter_config_uuid = self._create_global_vrouter_config(
+ global_system_config)['uuid']
+ with self.rbac_utils.override_role(self):
+ self.router_client.update_global_vrouter_config(
+ global_vrouter_config_uuid,
+ display_name=updated_fq_name)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="delete_global_vrouter_config")
+ @idempotent_id('4f3d59e8-3dac-4346-9d13-5ebe5ad8f6cf')
+ def test_delete_global_vrouter(self):
+ """
+ test method for delete global vrouter config objects
+ """
+ # Create global system config
+ global_system_config = self._create_global_system_config()['name']
+ global_vrouter_config_uuid = self._create_global_vrouter_config(
+ global_system_config)['uuid']
+ with self.rbac_utils.override_role(self):
+ self.router_client.delete_global_vrouter_config(
+ global_vrouter_config_uuid)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="list_logical_routers")
+ @idempotent_id('674bf3de-a9e5-45c2-921b-b89db73a2abe')
+ def test_list_logical_routers(self):
+ """
+ test method for list logical router objects
+ """
+ with self.rbac_utils.override_role(self):
+ self.router_client.list_logical_routers()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="create_logical_routers")
+ @idempotent_id('610f051b-8eba-4d3a-ba43-91386bfc0e52')
+ def test_create_logical_routers(self):
+ """
+ test method for create logical router objects
+ """
+ with self.rbac_utils.override_role(self):
+ self._create_logical_router()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="show_logical_router")
+ @idempotent_id('992841d4-0d5d-4d85-b513-049b33e2a2e2')
+ def test_show_logical_router(self):
+ """
+ test method for show logical router objects
+ """
+ logical_router_uuid = self._create_logical_router()['uuid']
+ with self.rbac_utils.override_role(self):
+ self.router_client.show_logical_router(logical_router_uuid)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="update_logical_router")
+ @idempotent_id('518197bf-5233-4059-9021-5d7ecc74718e')
+ def test_update_logical_router(self):
+ """
+ test method for update logical router objects
+ """
+ updated_fq_name = data_utils.rand_name('rbac-logical-router-new-name')
+ logical_router_uuid = self._create_logical_router()['uuid']
+ with self.rbac_utils.override_role(self):
+ self.router_client.update_logical_router(
+ logical_router_uuid,
+ display_name=updated_fq_name)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="delete_logical_router")
+ @idempotent_id('70448b9c-4444-45e0-b307-7bff4dc075b1')
+ def test_delete_logical_router(self):
+ """
+ test method for delete logical router objects
+ """
+ logical_router_uuid = self._create_logical_router()['uuid']
+ with self.rbac_utils.override_role(self):
+ self.router_client.delete_logical_router(logical_router_uuid)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="list_virtual_routers")
+ @idempotent_id('604dc476-732e-4890-8665-a497360f5475')
+ def test_list_virtual_routers(self):
+ """
+ test method for list virtual router objects
+ """
+ with self.rbac_utils.override_role(self):
+ self.router_client.list_virtual_routers()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="create_virtual_routers")
+ @idempotent_id('114beb14-45c0-4714-a407-d160bb102022')
+ def test_create_virtual_routers(self):
+ """
+ test method for create virtual router objects
+ """
+ # Create global system config
+ global_system_config = self._create_global_system_config()['name']
+ with self.rbac_utils.override_role(self):
+ self._create_virtual_router(global_system_config)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="show_virtual_router")
+ @idempotent_id('258fe4e0-3e39-460f-aafa-e3b53c96e534')
+ def test_show_virtual_router(self):
+ """
+ test method for show virtual router objects
+ """
+ # Create global system config
+ global_system_config = self._create_global_system_config()['name']
+ virtual_router_uuid = self._create_virtual_router(
+ global_system_config)['uuid']
+ with self.rbac_utils.override_role(self):
+ self.router_client.show_virtual_router(virtual_router_uuid)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="update_virtual_router")
+ @idempotent_id('d1c72191-2068-4552-a78f-038cdd4c9c1d')
+ def test_update_virtual_router(self):
+ """
+ test method for update virtual router objects
+ """
+ # Create global system config
+ global_system_config = self._create_global_system_config()['name']
+ updated_fq_name = data_utils.rand_name('rbac-virtual-router-new-name')
+ virtual_router_uuid = self._create_virtual_router(
+ global_system_config)['uuid']
+ with self.rbac_utils.override_role(self):
+ self.router_client.update_virtual_router(
+ virtual_router_uuid,
+ display_name=updated_fq_name)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="delete_virtual_router")
+ @idempotent_id('efbe25d6-8763-42d4-baf6-9f342e710144')
+ def test_delete_virtual_router(self):
+ """
+ test method for delete virtual router objects
+ """
+ # Create global system config
+ global_system_config = self._create_global_system_config()['name']
+ virtual_router_uuid = self._create_virtual_router(
+ global_system_config)['uuid']
+ with self.rbac_utils.override_role(self):
+ self.router_client.delete_virtual_router(virtual_router_uuid)
diff --git a/tungsten_tempest_plugin/tests/api/contrail/test_routing.py b/tungsten_tempest_plugin/tests/api/contrail/test_routing.py
new file mode 100644
index 0000000..37d61e0
--- /dev/null
+++ b/tungsten_tempest_plugin/tests/api/contrail/test_routing.py
@@ -0,0 +1,117 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest test-case to test routing objects using RBAC roles
+"""
+
+from tungsten_tempest_plugin.tests.api.contrail import rbac_base
+
+from patrole_tempest_plugin import rbac_rule_validation
+
+from tempest import config
+from tempest.lib.common.utils import data_utils
+from tempest.lib.decorators import idempotent_id
+
+CONF = config.CONF
+
+
+class RoutingTest(rbac_base.BaseContrailTest):
+
+ """
+ Test class to test routing objects using RBAC roles
+ """
+
+ @classmethod
+ def resource_setup(cls):
+ super(RoutingTest, cls).resource_setup()
+ net_name = data_utils.rand_name('test-net')
+ net_fq_name = ['default-domain', cls.tenant_name, net_name]
+ cls.network = cls.vn_client.create_virtual_networks(
+ parent_type='project',
+ fq_name=net_fq_name)['virtual-network']
+
+ @classmethod
+ def resource_cleanup(cls):
+ cls._try_delete_resource(cls.vn_client.delete_virtual_network,
+ cls.network['uuid'])
+ super(RoutingTest, cls).resource_cleanup()
+
+ def _create_routing_instances(self):
+ instance_name = data_utils.rand_name('test-instance')
+ instance_fq_name = ['default-domain', self.tenant_name,
+ self.network['name'], instance_name]
+ new_instance = self.routing_client.create_routing_instances(
+ parent_type='virtual-network',
+ fq_name=instance_fq_name)['routing-instance']
+ self.addCleanup(self._try_delete_resource,
+ self.routing_client.delete_routing_instance,
+ new_instance['uuid'])
+ return new_instance
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="list_routing_instances")
+ @idempotent_id('054c56ba-76b2-4161-a702-40301d8de085')
+ def test_list_routing_instances(self):
+ """
+ test method for list routing instance objects
+ """
+ with self.rbac_utils.override_role(self):
+ self.routing_client.list_routing_instances()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="create_routing_instances")
+ @idempotent_id('3d44a46b-5436-43a8-b2f7-8581f0f04dbc')
+ def test_create_routing_instances(self):
+ """
+ test method for create routing instance objects
+ """
+ with self.rbac_utils.override_role(self):
+ self._create_routing_instances()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="show_routing_instance")
+ @idempotent_id('161abb37-6037-422b-b453-108a5d10caca')
+ def test_show_routing_instance(self):
+ """
+ test method for show routing instance objects
+ """
+ new_instance = self._create_routing_instances()
+ with self.rbac_utils.override_role(self):
+ self.routing_client.show_routing_instance(new_instance['uuid'])
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="delete_routing_instance")
+ @idempotent_id('1d3af01e-01bf-4347-a9bc-633732339e0e')
+ def test_delete_routing_instance(self):
+ """
+ test method for delete routing instance objects
+ """
+ new_instance = self._create_routing_instances()
+ with self.rbac_utils.override_role(self):
+ self.routing_client.delete_routing_instance(new_instance['uuid'])
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="update_routing_instance")
+ @idempotent_id('ebcfd442-2a26-4954-968b-e17e414ed0d1')
+ def test_update_routing_instance(self):
+ """
+ test method for update routing instance objects
+ """
+ new_instance = self._create_routing_instances()
+ with self.rbac_utils.override_role(self):
+ self.routing_client.update_routing_instance(
+ new_instance['uuid'],
+ display_name=data_utils.rand_name('test-instance'))
diff --git a/tungsten_tempest_plugin/tests/api/contrail/test_routing_policy.py b/tungsten_tempest_plugin/tests/api/contrail/test_routing_policy.py
new file mode 100644
index 0000000..d1dd443
--- /dev/null
+++ b/tungsten_tempest_plugin/tests/api/contrail/test_routing_policy.py
@@ -0,0 +1,112 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest test-case to test routing policy objects using RBAC roles
+"""
+
+from oslo_log import log as logging
+
+from tungsten_tempest_plugin.tests.api.contrail import rbac_base
+
+from patrole_tempest_plugin import rbac_rule_validation
+
+from tempest import config
+from tempest.lib.common.utils import data_utils
+from tempest.lib.decorators import idempotent_id
+
+CONF = config.CONF
+LOG = logging.getLogger(__name__)
+
+
+class RoutingPolicyTest(rbac_base.BaseContrailTest):
+
+ """
+ Test class to test routing policy objects using RBAC roles
+ """
+
+ def _create_routing_policy(self):
+ fq_name = data_utils.rand_name('routing-policy')
+ post_body = {
+ 'parent_type': 'project',
+ 'fq_name': ["default-domain", self.tenant_name, fq_name]
+ }
+ resp_body = self.routing_policy_client.create_routing_policys(
+ **post_body)
+ routing_policy_uuid = resp_body['routing-policy']['uuid']
+ self.addCleanup(self._try_delete_resource,
+ self.routing_policy_client.delete_routing_policy,
+ routing_policy_uuid)
+ return routing_policy_uuid
+
+ def _update_routing_policy(self, routing_policy_uuid):
+ put_body = {
+ 'display_name': data_utils.rand_name('routing-policy')
+ }
+ self.routing_policy_client.update_routing_policy(routing_policy_uuid,
+ **put_body)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="list_routing_policys")
+ @idempotent_id('fe25a306-bc4f-42b3-91ca-38df01e35345')
+ def test_list_routing_policys(self):
+ """
+ test method for list routing policy objects
+ """
+ with self.rbac_utils.override_role(self):
+ self.routing_policy_client.list_routing_policys()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="create_routing_policys")
+ @idempotent_id('f8ca5e30-8bb3-410f-8618-8fdca70bda06')
+ def test_create_routing_policys(self):
+ """
+ test method for create routing policy objects
+ """
+ with self.rbac_utils.override_role(self):
+ self._create_routing_policy()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="show_routing_policy")
+ @idempotent_id('3421e84e-3e2a-452a-9a26-b2caf00b1cbc')
+ def test_show_routing_policy(self):
+ """
+ test method for show routing policy objects
+ """
+ policy_uuid = self._create_routing_policy()
+ with self.rbac_utils.override_role(self):
+ self.routing_policy_client.show_routing_policy(policy_uuid)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="update_routing_policy")
+ @idempotent_id('9fc1f44f-c8e2-4f5a-8239-e9b783f55d94')
+ def test_update_routing_policy(self):
+ """
+ test method for update routing policy objects
+ """
+ policy_uuid = self._create_routing_policy()
+ with self.rbac_utils.override_role(self):
+ self._update_routing_policy(policy_uuid)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="delete_routing_policy")
+ @idempotent_id('24f1cd7a-2917-4b81-a0a3-a40ed2d40c7d')
+ def test_delete_routing_policy(self):
+ """
+ test method for delete routing policy objects
+ """
+ policy_uuid = self._create_routing_policy()
+ with self.rbac_utils.override_role(self):
+ self.routing_policy_client.delete_routing_policy(policy_uuid)
diff --git a/tungsten_tempest_plugin/tests/api/contrail/test_security_group.py b/tungsten_tempest_plugin/tests/api/contrail/test_security_group.py
new file mode 100644
index 0000000..f0973d2
--- /dev/null
+++ b/tungsten_tempest_plugin/tests/api/contrail/test_security_group.py
@@ -0,0 +1,115 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest test-case to test service group objects using RBAC roles
+"""
+from oslo_log import log as logging
+
+from tungsten_tempest_plugin.tests.api.contrail import rbac_base
+
+from patrole_tempest_plugin import rbac_rule_validation
+
+from tempest import config
+from tempest.lib.common.utils import data_utils
+from tempest.lib.decorators import idempotent_id
+
+CONF = config.CONF
+LOG = logging.getLogger(__name__)
+
+
+class ContrailSecurityGroupTest(rbac_base.BaseContrailTest):
+
+ """
+ Test class to test security group objects using RBAC roles
+ """
+
+ def _delete_security_group(self, sec_grp_id):
+ return self.security_group_client.delete_security_group(sec_grp_id)
+
+ def _create_security_groups(self):
+ name = data_utils.rand_name('securitygroup')
+ domain_name = 'default-domain'
+ fq_name = ['default-domain', self.tenant_name, name]
+ parent_type = 'project'
+ sec_grp = self.security_group_client.create_security_groups(
+ domain_name=domain_name,
+ fq_name=fq_name,
+ display_name=name,
+ parent_type=parent_type)['security-group']
+ self.addCleanup(self._try_delete_resource,
+ self._delete_security_group,
+ sec_grp['uuid'])
+ return sec_grp
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="list_security_groups")
+ @idempotent_id('a13cc1d5-f562-4b68-b732-980deb3cddf4')
+ def test_list_security_groups(self):
+ """
+ test method for list security group objects
+ """
+ self._create_security_groups()
+ with self.rbac_utils.override_role(self):
+ self.security_group_client.list_security_groups()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="show_security_group")
+ @idempotent_id('c7ca1781-08ae-4fa2-bd6d-1f369950c4c4')
+ def test_show_security_group(self):
+ """
+ test method for show security group objects
+ """
+ grp = self._create_security_groups()
+ grp_id = grp['uuid']
+ with self.rbac_utils.override_role(self):
+ self.security_group_client.show_security_group(grp_id)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="delete_security_group")
+ @idempotent_id('e682d7b4-deb8-4b5c-9c9b-1e1ada827b40')
+ def test_delete_security_group(self):
+ """
+ test method for delete security group objects
+ """
+ grp = self._create_security_groups()
+ grp_id = grp['uuid']
+ with self.rbac_utils.override_role(self):
+ self._delete_security_group(grp_id)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="create_security_groups")
+ @idempotent_id('63a2ff14-7869-40a2-962a-d65752de5651')
+ def test_create_security_groups(self):
+ """
+ test method for create security group objects
+ """
+ with self.rbac_utils.override_role(self):
+ self._create_security_groups()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="update_security_group")
+ @idempotent_id('cf9aafe2-fffb-4028-8fd7-4d6634e144e7')
+ def test_update_security_group(self):
+ """
+ test method for update security group objects
+ """
+ grp = self._create_security_groups()
+ grp_id = grp['uuid']
+ display_name = data_utils.rand_name('securitygroupnew')
+ with self.rbac_utils.override_role(self):
+ self.security_group_client.update_security_group(
+ sec_group_id=grp_id,
+ display_name=display_name)
diff --git a/tungsten_tempest_plugin/tests/api/contrail/test_service_appliances.py b/tungsten_tempest_plugin/tests/api/contrail/test_service_appliances.py
new file mode 100644
index 0000000..46dc15c
--- /dev/null
+++ b/tungsten_tempest_plugin/tests/api/contrail/test_service_appliances.py
@@ -0,0 +1,220 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest test-case to test service appliance using RBAC roles
+"""
+
+from tungsten_tempest_plugin.tests.api.contrail import rbac_base
+
+from patrole_tempest_plugin import rbac_rule_validation
+
+from tempest import config
+from tempest.lib.common.utils import data_utils
+from tempest.lib.decorators import idempotent_id
+
+CONF = config.CONF
+
+
+class ServiceAppliancesTest(rbac_base.BaseContrailTest):
+
+ """
+ Test class to test service appliances objects using RBAC roles
+ """
+
+ def _create_global_system_config(self):
+ config_name = data_utils.rand_name('test-config')
+ parent_type = 'config-root'
+ config_fq_name = [config_name]
+ new_config = \
+ self.config_client.create_global_system_configs(
+ parent_type=parent_type,
+ display_name=config_name,
+ fq_name=config_fq_name)['global-system-config']
+ self.addCleanup(self._try_delete_resource,
+ (self.config_client.
+ delete_global_system_config),
+ new_config['uuid'])
+ return new_config
+
+ def _create_service_appliance_sets(self, global_system_config):
+ set_name = data_utils.rand_name('test-set')
+ set_fq_name = [global_system_config, set_name]
+ new_set = self.service_appliances_client.create_service_appliance_sets(
+ parent_type='global-system-config',
+ fq_name=set_fq_name)['service-appliance-set']
+ self.addCleanup(self._try_delete_resource,
+ (self.service_appliances_client.
+ delete_service_appliance_set),
+ new_set['uuid'])
+ return new_set
+
+ def _create_service_appliances(self, app_set):
+ appliance_name = data_utils.rand_name('test-appliance')
+ appliance_fq_name = app_set['fq_name']
+ appliance_fq_name.append(appliance_name)
+ new_appliance = \
+ self.service_appliances_client.create_service_appliances(
+ parent_type='service-appliance-set',
+ fq_name=appliance_fq_name)['service-appliance']
+ self.addCleanup(self._try_delete_resource,
+ (self.service_appliances_client.
+ delete_service_appliance),
+ new_appliance['uuid'])
+ return new_appliance
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="list_service_appliances")
+ @idempotent_id('6b5fc17c-34e6-4d21-a53e-a0dfe69afd31')
+ def test_list_service_appliances(self):
+ """
+ test method for list service appliance objects
+ """
+ with self.rbac_utils.override_role(self):
+ self.service_appliances_client.list_service_appliances()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="create_service_appliances")
+ @idempotent_id('0563c0c8-b986-466e-8540-aa8ad7a10367')
+ def test_create_service_appliances(self):
+ """
+ test method for create service appliance objects
+ """
+ # Create global system config
+ global_system_config = self._create_global_system_config()['name']
+ new_set = \
+ self._create_service_appliance_sets(global_system_config)
+ with self.rbac_utils.override_role(self):
+ self._create_service_appliances(new_set)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="show_service_appliance")
+ @idempotent_id('ea30dcfe-8657-4a7d-9cf1-3176d334bf27')
+ def test_show_service_appliance(self):
+ """
+ test method for show service appliance objects
+ """
+ # Create global system config
+ global_system_config = \
+ self._create_global_system_config()['name']
+ new_set = \
+ self._create_service_appliance_sets(global_system_config)
+ new_appliance = self._create_service_appliances(new_set)
+ with self.rbac_utils.override_role(self):
+ self.service_appliances_client.show_service_appliance(
+ new_appliance['uuid'])
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="update_service_appliance")
+ @idempotent_id('a54ca33a-8590-4844-96d7-b96882b59e86')
+ def test_update_service_appliance(self):
+ """
+ test method for update service appliance objects
+ """
+ # Create global system config
+ global_system_config = self._create_global_system_config()['name']
+ new_set = \
+ self._create_service_appliance_sets(global_system_config)
+ new_appliance = self._create_service_appliances(new_set)
+ update_name = data_utils.rand_name('test')
+ with self.rbac_utils.override_role(self):
+ self.service_appliances_client.update_service_appliance(
+ new_appliance['uuid'],
+ display_name=update_name)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="delete_service_appliance")
+ @idempotent_id('362deff5-7b72-4929-ba81-972cfcfa1309')
+ def test_delete_service_appliance(self):
+ """
+ test method for delete service appliance objects
+ """
+ # Create global system config
+ global_system_config = self._create_global_system_config()['name']
+ new_set = \
+ self._create_service_appliance_sets(global_system_config)
+ new_appliance = self._create_service_appliances(new_set)
+ with self.rbac_utils.override_role(self):
+ self.service_appliances_client.delete_service_appliance(
+ new_appliance['uuid'])
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="list_service_appliance_sets")
+ @idempotent_id('c1e74da9-00b6-4c88-adda-2ce49094e570')
+ def test_list_service_appl_sets(self):
+ """
+ test method for list service appliance sets objects
+ """
+ with self.rbac_utils.override_role(self):
+ self.service_appliances_client.list_service_appliance_sets()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="create_service_appliance_sets")
+ @idempotent_id('eb00d6cf-590f-41bf-8ee4-5be625d9cb93')
+ def test_create_service_appl_sets(self):
+ """
+ test method for create service appliance sets objects
+ """
+ # Create global system config
+ global_system_config = self._create_global_system_config()['name']
+ with self.rbac_utils.override_role(self):
+ self._create_service_appliance_sets(global_system_config)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="show_service_appliance_set")
+ @idempotent_id('dd35dd04-e7d9-46bb-8f36-26835f122572')
+ def test_show_service_appl_set(self):
+ """
+ test method for show service appliance sets objects
+ """
+ # Create global system config
+ global_system_config = self._create_global_system_config()['name']
+ new_set = self._create_service_appliance_sets(
+ global_system_config)
+ with self.rbac_utils.override_role(self):
+ self.service_appliances_client.show_service_appliance_set(
+ new_set['uuid'])
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="update_service_appliance_set")
+ @idempotent_id('952f063b-bc71-4f62-83b1-719bce5ad4ed')
+ def test_update_service_appl_set(self):
+ """
+ test method for update service appliance sets objects
+ """
+ # Create global system config
+ global_system_config = self._create_global_system_config()['name']
+ new_set = self._create_service_appliance_sets(
+ global_system_config)
+ update_name = data_utils.rand_name('test')
+ with self.rbac_utils.override_role(self):
+ self.service_appliances_client.update_service_appliance_set(
+ new_set['uuid'],
+ display_name=update_name)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="delete_service_appliance_set")
+ @idempotent_id('7b56ce24-da1d-4565-bd22-c58dc57d7045')
+ def test_delete_service_appl_set(self):
+ """
+ test method for delete service appliance sets objects
+ """
+ # Create global system config
+ global_system_config = self._create_global_system_config()['name']
+ new_set = self._create_service_appliance_sets(
+ global_system_config)
+ with self.rbac_utils.override_role(self):
+ self.service_appliances_client.delete_service_appliance_set(
+ new_set['uuid'])
diff --git a/tungsten_tempest_plugin/tests/api/contrail/test_service_clients.py b/tungsten_tempest_plugin/tests/api/contrail/test_service_clients.py
new file mode 100644
index 0000000..8d65159
--- /dev/null
+++ b/tungsten_tempest_plugin/tests/api/contrail/test_service_clients.py
@@ -0,0 +1,261 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest test-case to test service clients objects using RBAC roles
+"""
+
+from tungsten_tempest_plugin.tests.api.contrail import rbac_base
+
+from patrole_tempest_plugin import rbac_rule_validation
+
+from tempest import config
+from tempest.lib.common.utils import data_utils
+from tempest.lib.decorators import idempotent_id
+
+CONF = config.CONF
+
+
+class ServiceClientsTest(rbac_base.BaseContrailTest):
+
+ """
+ Tempest test-case to test service clients objects using RBAC roles
+ """
+
+ def _create_service_template(self):
+ template_name = data_utils.rand_name('test-template')
+ domain_name = 'default-domain'
+ parent_type = 'domain'
+ template_fq_name = ['default-domain', template_name]
+ new_template = \
+ self.service_client.create_service_templates(
+ domain_name=domain_name,
+ parent_type=parent_type,
+ display_name=template_name,
+ fq_name=template_fq_name)['service-template']
+ self.addCleanup(self._try_delete_resource,
+ (self.service_client.
+ delete_service_template),
+ new_template['uuid'])
+ return new_template
+
+ def _create_service_health_check(self):
+ health_check_name = data_utils.rand_name('test-health-check')
+ domain_name = 'default-domain'
+ parent_type = 'project'
+ health_check_fq_name = ['default-domain', self.tenant_name,
+ health_check_name]
+ new_health_check = \
+ self.service_client.create_service_health_checks(
+ domain_name=domain_name,
+ parent_type=parent_type,
+ display_name=health_check_name,
+ fq_name=health_check_fq_name)['service-health-check']
+ self.addCleanup(self._try_delete_resource,
+ (self.service_client.
+ delete_service_health_check),
+ new_health_check['uuid'])
+ return new_health_check
+
+ def _create_service_instance(self):
+ instance_name = data_utils.rand_name('test-instance')
+ domain_name = 'default-domain'
+ parent_type = 'project'
+ instance_fq_name = ['default-domain', self.tenant_name, instance_name]
+ new_instance = \
+ self.service_client.create_service_instances(
+ domain_name=domain_name,
+ fq_name=instance_fq_name,
+ display_name=instance_name,
+ parent_type=parent_type)['service-instance']
+ self.addCleanup(self._try_delete_resource,
+ (self.service_client.
+ delete_service_instance),
+ new_instance['uuid'])
+ return new_instance
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="list_service_templates")
+ @idempotent_id('841b1d32-4308-4fb6-852a-41bdd8c56c37')
+ def test_list_service_templates(self):
+ """
+ test method for list service template objects
+ """
+ with self.rbac_utils.override_role(self):
+ self.service_client.list_service_templates()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="create_service_templates")
+ @idempotent_id('3f02d14a-31e2-4476-821f-87d0cc42d9fb')
+ def test_create_service_templates(self):
+ """
+ test method for create service template objects
+ """
+ with self.rbac_utils.override_role(self):
+ self._create_service_template()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="show_service_template")
+ @idempotent_id('1f15d734-2cc6-4ded-916e-134286c6b87b')
+ def test_show_service_template(self):
+ """
+ test method for show service template objects
+ """
+ new_template = self._create_service_template()
+ with self.rbac_utils.override_role(self):
+ self.service_client.show_service_template(
+ new_template['uuid'])
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="update_service_template")
+ @idempotent_id('3549debd-4c7a-4574-8d11-4190c8530a23')
+ def test_update_service_template(self):
+ """
+ test method for update service template objects
+ """
+ new_template = self._create_service_template()
+ update_name = data_utils.rand_name('test')
+ with self.rbac_utils.override_role(self):
+ self.service_client.update_service_template(
+ new_template['uuid'],
+ display_name=update_name)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="delete_service_template")
+ @idempotent_id('e86cabd2-5b7e-4ee8-86ec-db52619b852b')
+ def test_delete_service_template(self):
+ """
+ test method for delete service template objects
+ """
+ new_template = self._create_service_template()
+ with self.rbac_utils.override_role(self):
+ self.service_client.delete_service_template(
+ new_template['uuid'])
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="list_service_health_checks")
+ @idempotent_id('5210d6ca-9a38-4b6b-b5b7-f836c3846079')
+ def test_list_service_health_checks(self):
+ """
+ test method for list service health check objects
+ """
+ with self.rbac_utils.override_role(self):
+ self.service_client.list_service_health_checks()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="create_service_health_checks")
+ @idempotent_id('77716feb-0d05-4cfd-8a17-79cf0b19ed3c')
+ def test_create_service_health(self):
+ """
+ test method for create service health check objects
+ """
+ with self.rbac_utils.override_role(self):
+ self._create_service_health_check()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="show_service_health_check")
+ @idempotent_id('80db4445-8d6c-4c8f-aa25-d4ea53d32d2c')
+ def test_show_service_health(self):
+ """
+ test method for show service health check objects
+ """
+ new_health_check = self._create_service_health_check()
+ with self.rbac_utils.override_role(self):
+ self.service_client.show_service_health_check(
+ new_health_check['uuid'])
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="update_service_health_check")
+ @idempotent_id('68fb1510-4b76-40cc-8979-e56e537229d2')
+ def test_update_service_health(self):
+ """
+ test method for update service health check objects
+ """
+ new_health_check = self._create_service_health_check()
+ update_name = data_utils.rand_name('test')
+ with self.rbac_utils.override_role(self):
+ self.service_client.update_service_health_check(
+ new_health_check['uuid'],
+ display_name=update_name)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="delete_service_health_check")
+ @idempotent_id('2dce3942-402a-48a4-b682-fdc425d3d935')
+ def test_delete_service_health(self):
+ """
+ test method for delete service health check objects
+ """
+ new_health_check = self._create_service_health_check()
+ with self.rbac_utils.override_role(self):
+ self.service_client.delete_service_health_check(
+ new_health_check['uuid'])
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="create_service_instances")
+ @idempotent_id('1469c71e-f6f5-419f-9672-c3c67f879704')
+ def test_create_service_instances(self):
+ """
+ test method for create service client objects
+ """
+ with self.rbac_utils.override_role(self):
+ self._create_service_instance()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="show_service_instance")
+ @idempotent_id('ea5b716d-5de8-4c71-becd-f1501c22f0df')
+ def test_show_service_instance(self):
+ """
+ test method for show service client objects
+ """
+ new_instance = self._create_service_instance()
+ with self.rbac_utils.override_role(self):
+ self.service_client.show_service_instance(
+ new_instance['uuid'])
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="delete_service_instance")
+ @idempotent_id('74934833-29cd-416b-a5a6-273f733d058a')
+ def test_delete_service_instance(self):
+ """
+ test method for delete service client objects
+ """
+ new_instance = self._create_service_instance()
+ with self.rbac_utils.override_role(self):
+ self.service_client.delete_service_instance(
+ new_instance['uuid'])
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="list_service_instances")
+ @idempotent_id('da6016a3-a2a8-42a8-b064-c124c22fef6f')
+ def test_list_service_instances(self):
+ """
+ test method for list service client objects
+ """
+ with self.rbac_utils.override_role(self):
+ self.service_client.list_service_instances()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="update_service_instance")
+ @idempotent_id('a6237b99-336b-42db-a8eb-9604a1b08fc6')
+ def test_update_service_instance(self):
+ """
+ test method for update service client objects
+ """
+ new_instance = self._create_service_instance()
+ update_name = data_utils.rand_name('test')
+ with self.rbac_utils.override_role(self):
+ self.service_client.update_service_instance(
+ new_instance['uuid'],
+ display_name=update_name)
diff --git a/tungsten_tempest_plugin/tests/api/contrail/test_subnet.py b/tungsten_tempest_plugin/tests/api/contrail/test_subnet.py
new file mode 100644
index 0000000..211aaf6
--- /dev/null
+++ b/tungsten_tempest_plugin/tests/api/contrail/test_subnet.py
@@ -0,0 +1,109 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest test-case to test subnet objects using RBAC roles
+"""
+
+from oslo_log import log as logging
+
+from tungsten_tempest_plugin.tests.api.contrail import rbac_base
+
+from patrole_tempest_plugin import rbac_rule_validation
+
+from tempest import config
+from tempest.lib.common.utils import data_utils
+from tempest.lib.decorators import idempotent_id
+
+CONF = config.CONF
+LOG = logging.getLogger(__name__)
+
+
+class SubnetContrailTest(rbac_base.BaseContrailTest):
+
+ """
+ Test class to test subnet objects using RBAC roles
+ """
+
+ def _create_subnet(self):
+ post_body = {
+ 'fq_name': [data_utils.rand_name('subnet')]
+ }
+ resp_body = self.subnet_client.create_subnets(
+ **post_body)
+ subnet_uuid = resp_body['subnet']['uuid']
+ self.addCleanup(self._try_delete_resource,
+ self.subnet_client.delete_subnet,
+ subnet_uuid)
+ return subnet_uuid
+
+ def _update_subnet(self, subnet_uuid):
+ put_body = {
+ 'display_name': data_utils.rand_name('subnet')
+ }
+ self.subnet_client.update_subnet(subnet_uuid, **put_body)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="list_subnets")
+ @idempotent_id('ddd1d9ae-cf2f-4a74-98ba-b0f481f27977')
+ def test_list_subnets(self):
+ """
+ test method for list subnet objects
+ """
+ with self.rbac_utils.override_role(self):
+ self.subnet_client.list_subnets()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="create_subnets")
+ @idempotent_id('ee0cb904-d162-44a4-b7b0-a7451f667ed5')
+ def test_create_subnets(self):
+ """
+ test method for create subnet objects
+ """
+ with self.rbac_utils.override_role(self):
+ self._create_subnet()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="show_subnet")
+ @idempotent_id('994618f2-5b40-460c-a6a8-6479bc15bf80')
+ def test_show_subnet(self):
+ """
+ test method for show subnet objects
+ """
+ subnet_uuid = self._create_subnet()
+ with self.rbac_utils.override_role(self):
+ self.subnet_client.show_subnet(subnet_uuid)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="update_subnet")
+ @idempotent_id('565e44c9-eb9b-4ae6-9ebb-db422a9751ee')
+ def test_update_subnet(self):
+ """
+ test method for update subnet objects
+ """
+ subnet_uuid = self._create_subnet()
+ with self.rbac_utils.override_role(self):
+ self._update_subnet(subnet_uuid)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="delete_subnet")
+ @idempotent_id('a733b913-7a88-45d9-ac0a-d858fa3dc662')
+ def test_delete_subnet(self):
+ """
+ test method for delete subnet objects
+ """
+ subnet_uuid = self._create_subnet()
+ with self.rbac_utils.override_role(self):
+ self.subnet_client.delete_subnet(subnet_uuid)
diff --git a/tungsten_tempest_plugin/tests/api/contrail/test_virtual_dns.py b/tungsten_tempest_plugin/tests/api/contrail/test_virtual_dns.py
new file mode 100644
index 0000000..5974c8c
--- /dev/null
+++ b/tungsten_tempest_plugin/tests/api/contrail/test_virtual_dns.py
@@ -0,0 +1,210 @@
+# Copyright 2016 AT&T Corp
+# All Rignhts 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.
+
+"""
+Tempest test-case to test virtual dns objects using RBAC roles
+"""
+
+from oslo_log import log as logging
+
+from tungsten_tempest_plugin.tests.api.contrail import rbac_base
+
+from patrole_tempest_plugin import rbac_rule_validation
+
+from tempest import config
+from tempest.lib.common.utils import data_utils
+from tempest.lib.decorators import idempotent_id
+
+CONF = config.CONF
+LOG = logging.getLogger(__name__)
+
+
+# noinspection PyPep8Naming
+class VirtualDNSTest(rbac_base.BaseContrailTest):
+
+ """
+ Test class to test virtual dns objects using RBAC roles
+ """
+
+ def _create_virtual_dns(self):
+ parent_type = "domain"
+ virtual_dns_data = {"domain_name": "default-domain",
+ "default_ttl_seconds": 0,
+ "record_order": "fixed"}
+ display_name = data_utils.rand_name('virtual-dns')
+ fq_name = ["default-domain", display_name]
+ dns = self.virtual_dns_client.create_virtual_dns(
+ parent_type=parent_type,
+ virtual_DNS_data=virtual_dns_data,
+ display_name=display_name,
+ fq_name=fq_name)
+ self.addCleanup(self._try_delete_resource,
+ self.virtual_dns_client.delete_virtual_dns,
+ dns['virtual-DNS']['uuid'])
+ return dns
+
+ def _create_virtual_dns_record(self, dns):
+ parent_type = "virtual-DNS"
+ record_name = data_utils.rand_name('virtual-dns-record')
+ virtual_dns_record_data = {"record_type": "A",
+ "record_ttl_seconds": 86400,
+ "record_name": record_name,
+ "record_class": "IN",
+ "record_data": "1.1.1.1"}
+ fq_name = dns['virtual-DNS']['fq_name']
+ fq_name.append(record_name)
+ parent_uuid = dns['virtual-DNS']['uuid']
+ dns_record = self.virtual_dns_client.create_virtual_dns_records(
+ parent_type=parent_type,
+ virtual_DNS_record_data=virtual_dns_record_data,
+ fq_name=fq_name,
+ parent_uuid=parent_uuid)
+ self.addCleanup(self._try_delete_resource,
+ self.virtual_dns_client.delete_virtual_dns_record,
+ dns_record['virtual-DNS-record']['uuid'])
+ return dns_record
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="list_virtual_DNSs")
+ @idempotent_id('8401d690-afdf-4b6e-ad60-b9363a8cfb1d')
+ def test_list_virtual_dns(self):
+ """
+ test method for list virtual dns objects
+ """
+ with self.rbac_utils.override_role(self):
+ self.virtual_dns_client.list_virtual_dns()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="create_virtual_DNSs")
+ @idempotent_id('a7dd2c9e-e1eb-4dc4-ac70-4d48a291a3bf')
+ def test_create_virtual_dns(self):
+ """
+ test method for create virtual dns objects
+ """
+ with self.rbac_utils.override_role(self):
+ self._create_virtual_dns()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="show_virtual_DNS")
+ @idempotent_id('ffc0fc82-3bff-48ab-b65a-3d90b4a3154d')
+ def test_show_virtual_dns(self):
+ """
+ test method for show virtual dns objects
+ """
+ dns = self._create_virtual_dns()
+ with self.rbac_utils.override_role(self):
+ self.virtual_dns_client.show_virtual_dns(
+ dns['virtual-DNS']['uuid'])
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="delete_virtual_DNS")
+ @idempotent_id('4793caa1-7707-4123-b1b4-c3feae91312f')
+ def test_delete_virtual_dns(self):
+ """
+ test method for delete virtual dns objects
+ """
+ dns = self._create_virtual_dns()
+ with self.rbac_utils.override_role(self):
+ self.virtual_dns_client.delete_virtual_dns(
+ dns['virtual-DNS']['uuid'])
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="update_virtual_DNS")
+ @idempotent_id('2bc43935-57c1-4bf6-9868-78ccfce164bb')
+ def test_update_virtual_dns(self):
+ """
+ test method for update virtual dns objects
+ """
+ dns = self._create_virtual_dns()
+ virtual_dns_data = {"domain_name": "default-domain",
+ "default_ttl_seconds": 0,
+ "record_order": "fixed"}
+ display_name = data_utils.rand_name('virtual-dns-updated')
+ with self.rbac_utils.override_role(self):
+ self.virtual_dns_client.update_virtual_dns(
+ dns_id=dns['virtual-DNS']['uuid'],
+ virtual_DNS_data=virtual_dns_data,
+ display_name=display_name)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="list_virtual_DNS_records")
+ @idempotent_id('e9103999-2f02-4f04-a8a0-906ca4fb394d')
+ def test_list_virtual_dns_records(self):
+ """
+ test method for list virtual dns record objects
+ """
+ with self.rbac_utils.override_role(self):
+ self.virtual_dns_client.list_virtual_dns_records()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="create_virtual_DNS_records")
+ @idempotent_id('bd9f3992-0ce4-4477-97a0-1271bc8ad9ef')
+ def test_create_virtual_dns_records(self):
+ """
+ test method for create virtual dns record objects
+ """
+ # A virtual DNS is needed to create a record
+ dns = self._create_virtual_dns()
+ with self.rbac_utils.override_role(self):
+ self._create_virtual_dns_record(dns)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="show_virtual_DNS_record")
+ @idempotent_id('fa3d1a2b-d788-4623-89a4-3a9ed1db7a7d')
+ def test_show_virtual_dns_record(self):
+ """
+ test method for show virtual dns record objects
+ """
+ # A virtual DNS is needed to create a record
+ dns = self._create_virtual_dns()
+ dns_record = self._create_virtual_dns_record(dns)
+ with self.rbac_utils.override_role(self):
+ self.virtual_dns_client.show_virtual_dns_record(
+ dns_record['virtual-DNS-record']['uuid'])
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="delete_virtual_DNS_record")
+ @idempotent_id('de31e867-c997-4b4c-a095-43c647f5c192')
+ def test_delete_virtual_dns_record(self):
+ """
+ test method for delete virtual dns record objects
+ """
+ # A virtual DNS is needed to create a record
+ dns = self._create_virtual_dns()
+ dns_record = self._create_virtual_dns_record(dns)
+ with self.rbac_utils.override_role(self):
+ self.virtual_dns_client.delete_virtual_dns_record(
+ dns_record['virtual-DNS-record']['uuid'])
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="update_virtual_DNS_record")
+ @idempotent_id('65acef26-646f-4b36-923c-8a1d07e90c5c')
+ def test_update_virtual_dns_record(self):
+ """
+ test method for update virtual dns record objects
+ """
+ # A virtual DNS is needed to create a record
+ dns = self._create_virtual_dns()
+ dns_record = self._create_virtual_dns_record(dns)
+ record_name = data_utils.rand_name('virtual-dns-record-updated')
+ virtual_dns_record_data = {"record_type": "A",
+ "record_ttl_seconds": 86400,
+ "record_name": record_name,
+ "record_class": "IN",
+ "record_data": "1.1.1.1"}
+ with self.rbac_utils.override_role(self):
+ self.virtual_dns_client.update_virtual_dns_record(
+ dns_record_id=dns_record['virtual-DNS-record']['uuid'],
+ virtual_DNS_record_data=virtual_dns_record_data)
diff --git a/tungsten_tempest_plugin/tests/api/contrail/test_virtual_ip.py b/tungsten_tempest_plugin/tests/api/contrail/test_virtual_ip.py
new file mode 100644
index 0000000..0f229a6
--- /dev/null
+++ b/tungsten_tempest_plugin/tests/api/contrail/test_virtual_ip.py
@@ -0,0 +1,110 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest test-case to test virtual ip objects using RBAC roles
+"""
+
+from oslo_log import log as logging
+
+from tungsten_tempest_plugin.tests.api.contrail import rbac_base
+
+from patrole_tempest_plugin import rbac_rule_validation
+
+from tempest import config
+from tempest.lib.common.utils import data_utils
+from tempest.lib.decorators import idempotent_id
+
+CONF = config.CONF
+LOG = logging.getLogger(__name__)
+
+
+class VirtualIPTest(rbac_base.BaseContrailTest):
+
+ """
+ Test class to test virtual ip objects using RBAC roles
+ """
+
+ def _create_virtual_ip(self):
+ fq_name = data_utils.rand_name('virtual_ip')
+ post_body = {
+ 'parent_type': 'project',
+ 'fq_name': ["default-domain", self.tenant_name, fq_name]
+ }
+ resp_body = self.virtual_ip_client.create_virtual_ips(**post_body)
+ virtual_ip_uuid = resp_body['virtual-ip']['uuid']
+ self.addCleanup(self._try_delete_resource,
+ self.virtual_ip_client.delete_virtual_ip,
+ virtual_ip_uuid)
+ return virtual_ip_uuid
+
+ def _update_virtual_ip(self, virtual_ip_uuid):
+ put_body = {
+ 'display_name': data_utils.rand_name('virtual_ip')
+ }
+ self.virtual_ip_client.update_virtual_ip(virtual_ip_uuid, **put_body)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="list_virtual_ips")
+ @idempotent_id('92303eee-bd96-48bc-a02c-39950bd19a21')
+ def test_list_virtual_ips(self):
+ """
+ test method for list virtual ip objects
+ """
+ with self.rbac_utils.override_role(self):
+ self.virtual_ip_client.list_virtual_ips()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="create_virtual_ips")
+ @idempotent_id('e0070888-995d-46ab-91fc-db1412eba2f7')
+ def test_create_virtual_ips(self):
+ """
+ test method for create virtual ip objects
+ """
+ with self.rbac_utils.override_role(self):
+ self._create_virtual_ip()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="show_virtual_ip")
+ @idempotent_id('2a4b3abd-c6f7-4d82-aa31-02e53d2a8fb9')
+ def test_show_virtual_ip(self):
+ """
+ test method for show virtual ip objects
+ """
+ virtual_ip_uuid = self._create_virtual_ip()
+ with self.rbac_utils.override_role(self):
+ self.virtual_ip_client.show_virtual_ip(virtual_ip_uuid)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="update_virtual_ip")
+ @idempotent_id('0e975c92-62dc-4e6e-82cc-8cf37da3c5b2')
+ def test_update_virtual_ip(self):
+ """
+ test method for update virtual ip objects
+ """
+ virtual_ip_uuid = self._create_virtual_ip()
+ with self.rbac_utils.override_role(self):
+ self._update_virtual_ip(virtual_ip_uuid)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="delete_virtual_ip")
+ @idempotent_id('fd0b2635-36bd-4345-97b7-9c0a57372eba')
+ def test_delete_virtual_ip(self):
+ """
+ test method for delete virtual ip objects
+ """
+ virtual_ip_uuid = self._create_virtual_ip()
+ with self.rbac_utils.override_role(self):
+ self.virtual_ip_client.delete_virtual_ip(virtual_ip_uuid)
diff --git a/tungsten_tempest_plugin/tests/api/contrail/test_virtual_machines.py b/tungsten_tempest_plugin/tests/api/contrail/test_virtual_machines.py
new file mode 100644
index 0000000..ae54c78
--- /dev/null
+++ b/tungsten_tempest_plugin/tests/api/contrail/test_virtual_machines.py
@@ -0,0 +1,161 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest test-case to test virtual machines objects using RBAC roles
+"""
+
+from oslo_log import log as logging
+
+from tungsten_tempest_plugin.tests.api.contrail import rbac_base
+
+from patrole_tempest_plugin import rbac_rule_validation
+
+from tempest import config
+from tempest.lib.common.utils import data_utils
+from tempest.lib.decorators import idempotent_id
+
+LOG = logging.getLogger(__name__)
+CONF = config.CONF
+
+
+class VMContrailTest(rbac_base.BaseContrailTest):
+
+ """
+ Test class to test vm objects using RBAC roles
+ """
+
+ @classmethod
+ def resource_setup(cls):
+ super(VMContrailTest, cls).resource_setup()
+ # Create subnet using ipam
+ ipam_name = data_utils.rand_name('rbac-fip-ipam')
+ fq_name_ipam = ['default-domain',
+ cls.tenant_name,
+ ipam_name]
+ ip_cidr = CONF.network.project_network_cidr
+ ip_prefix, ip_prefix_len = ip_cidr.split('/')
+ subnet_ip_prefix = {'ip_prefix': ip_prefix,
+ 'ip_prefix_len': int(ip_prefix_len)}
+ ipam_post_body = {'parent_type': 'project', 'fq_name': fq_name_ipam}
+ body = cls.network_ipams_client.create_network_ipams(**ipam_post_body)
+ cls.ipam = body['network-ipam']
+ # Create network
+ net_name = data_utils.rand_name('rbac-pool-network')
+ fq_name = ['default-domain', cls.tenant_name, net_name]
+ post_body = {'parent_type': 'project',
+ 'router_external': True,
+ 'fq_name': fq_name,
+ 'network_ipam_refs': [
+ {
+ 'to': cls.ipam['fq_name'],
+ 'href': cls.ipam['href'],
+ 'uuid': cls.ipam['uuid'],
+ 'attr': {
+ 'ipam_subnets': [{'subnet': subnet_ip_prefix}]
+ }
+ }
+ ]
+ }
+ body = cls.vn_client.create_virtual_networks(**post_body)
+ cls.network = body['virtual-network']
+
+ def _delete_virtual_machine_interface(self, instance_id):
+ return self.vm_client.delete_vm_interface(instance_id)
+
+ def _create_virual_machine_interface(self):
+ to_vm = ["default-domain", self.tenant_name, self.network['name']]
+ net_id = self.network['uuid']
+ virtual_network_refs = {"uuid": net_id,
+ "to": to_vm}
+ name = data_utils.rand_name('vitual-machine-interface')
+ domain_name = 'default-domain'
+ fq_name = ['default-domain', self.tenant_name, name]
+ parent_type = 'project'
+ interface = self.vm_client.create_vm_interfaces(
+ fq_name=fq_name,
+ domain_name=domain_name,
+ parent_type=parent_type,
+ virtual_network_refs=[virtual_network_refs]
+ )['virtual-machine-interface']
+ self.addCleanup(self._try_delete_resource,
+ self._delete_virtual_machine_interface,
+ interface['uuid'])
+ return interface
+
+ @classmethod
+ def resource_cleanup(cls):
+ cls._try_delete_resource(cls.vn_client.delete_virtual_network,
+ cls.network['uuid'])
+ cls._try_delete_resource(cls.network_ipams_client.delete_network_ipam,
+ cls.ipam['uuid'])
+ super(VMContrailTest, cls).resource_cleanup()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="list_virtual_machine_interfaces")
+ @idempotent_id('e27d1fae-7324-4ef3-87b1-e7f519b1e2a7')
+ def test_list_vm_interfaces(self):
+ """
+ test method for list vm interfaces objects
+ """
+ self._create_virual_machine_interface()
+ with self.rbac_utils.override_role(self):
+ self.vm_client.list_virtual_machine_interfaces()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="create_virtual_machine_interfaces")
+ @idempotent_id('d8a3a524-d61b-4bcb-8146-c5d4f308df8e')
+ def test_add_vm_interfaces(self):
+ """
+ test method for add vm interfaces objects
+ """
+ with self.rbac_utils.override_role(self):
+ self._create_virual_machine_interface()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="show_virtual_machine_interface")
+ @idempotent_id('3f17125a-9060-4c4a-a23f-0fe2aba2ccef')
+ def test_show_vm_interface(self):
+ """
+ test method for show vm interfaces objects
+ """
+ test = self._create_virual_machine_interface()
+ with self.rbac_utils.override_role(self):
+ self.vm_client.show_virtual_machine_interface(test['uuid'])
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="delete_virtual_machine_interface")
+ @idempotent_id('ce7f9471-ba1b-40d2-94f1-bdd0c610e22f')
+ def test_delete_vm_interface(self):
+ """
+ test method for delete vm interfaces objects
+ """
+ body = self._create_virual_machine_interface()
+ with self.rbac_utils.override_role(self):
+ self.vm_client.delete_vm_interface(body['uuid'])
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="update_virtual_machine_interface")
+ @idempotent_id('7ca3046a-6245-4c15-914b-5a8ecdbeee11')
+ def test_update_vm_interface(self):
+ """
+ test method for update vm interfaces objects
+ """
+ virtual_machine = self._create_virual_machine_interface()
+ display_name = data_utils.rand_name('new-vitual-machine-inf-name')
+ with self.rbac_utils.override_role(self):
+ self.vm_client.update_vm_interface(
+ instance_id=virtual_machine['uuid'],
+ display_name=display_name)
diff --git a/tungsten_tempest_plugin/tests/api/contrail/test_virtual_networks.py b/tungsten_tempest_plugin/tests/api/contrail/test_virtual_networks.py
new file mode 100644
index 0000000..9e91164
--- /dev/null
+++ b/tungsten_tempest_plugin/tests/api/contrail/test_virtual_networks.py
@@ -0,0 +1,126 @@
+# Copyright 2016 AT&T Corp
+# 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.
+
+"""
+Tempest test-case to test virtual network objects using RBAC roles
+"""
+
+from oslo_log import log as logging
+
+from tungsten_tempest_plugin.tests.api.contrail import rbac_base
+
+from patrole_tempest_plugin import rbac_rule_validation
+
+from tempest import config
+from tempest.lib.common.utils import data_utils
+from tempest.lib.decorators import idempotent_id
+
+CONF = config.CONF
+LOG = logging.getLogger(__name__)
+
+
+class NetworksTest(rbac_base.BaseContrailTest):
+
+ """
+ Test class to test vm network using RBAC roles
+ """
+
+ @classmethod
+ def resource_setup(cls):
+ super(NetworksTest, cls).resource_setup()
+
+ # Create virtual network for tests
+ net_name = data_utils.rand_name('rbac-virtual-network')
+ fq_name = ['default-domain', cls.tenant_name, net_name]
+ post_body = {'parent_type': 'project',
+ 'router_external': True,
+ 'fq_name': fq_name}
+ cls.network = cls.vn_client.create_virtual_networks(
+ **post_body)['virtual-network']
+
+ @classmethod
+ def resource_cleanup(cls):
+
+ cls._try_delete_resource(cls.vn_client.delete_virtual_network,
+ cls.network['uuid'])
+ super(NetworksTest, cls).resource_cleanup()
+
+ def _create_virtual_network(self):
+ net_name = data_utils.rand_name('rbac-virtual-network')
+ fq_name = ['default-domain', self.tenant_name, net_name]
+ post_body = {'parent_type': 'project',
+ 'router_external': True,
+ 'fq_name': fq_name}
+ network = self.vn_client.create_virtual_networks(
+ **post_body)['virtual-network']
+ self.addCleanup(self._try_delete_resource,
+ self.vn_client.delete_virtual_network,
+ network['uuid'])
+ return network
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="list_virtual_networks")
+ @idempotent_id('375ebc8d-dc52-4d9c-877b-85aba35b1539')
+ def test_list_virtual_networks(self):
+ """
+ test method for list vm network objects
+ """
+ with self.rbac_utils.override_role(self):
+ self.vn_client.list_virtual_networks()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="create_virtual_networks")
+ @idempotent_id('375ebc8d-dc52-4d9c-877b-96aba35b2530')
+ def test_create_virtual_networks(self):
+ """
+ test method for create vm network objects
+ """
+ with self.rbac_utils.override_role(self):
+ self._create_virtual_network()
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="update_virtual_network")
+ @idempotent_id('375ebc8d-dc52-4d9c-566b-150a025c1237')
+ def test_update_virtual_network(self):
+ """
+ test method for update vm network objects
+ """
+ # Create virtual network
+ uuid = self._create_virtual_network()['uuid']
+ with self.rbac_utils.override_role(self):
+ self.vn_client.update_virtual_network(
+ uuid, router_external=False)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="delete_virtual_network")
+ @idempotent_id('375ebc8d-dc52-4d9c-877b-17bcb53c3641')
+ def test_delete_virtual_network(self):
+ """
+ test method for delete vm network objects
+ """
+ uuid = self._create_virtual_network()['uuid']
+ with self.rbac_utils.override_role(self):
+ self.vn_client.delete_virtual_network(uuid)
+
+ @rbac_rule_validation.action(service="Contrail",
+ rule="show_virtual_network")
+ @idempotent_id('375ebc8d-dc52-4d9c-877b-27c1a1242a81')
+ def test_show_virtual_network(self):
+ """
+ test method for show vm network objects
+ """
+ uuid = self._create_virtual_network()['uuid']
+ with self.rbac_utils.override_role(self):
+ self.vn_client.show_virtual_network(uuid)
diff --git a/tungsten_tempest_plugin/tests/scenario/__init__.py b/tungsten_tempest_plugin/tests/scenario/__init__.py
new file mode 100644
index 0000000..e69de29
--- /dev/null
+++ b/tungsten_tempest_plugin/tests/scenario/__init__.py
diff --git a/tungsten_tempest_plugin/tests/unit/__init__.py b/tungsten_tempest_plugin/tests/unit/__init__.py
new file mode 100644
index 0000000..e69de29
--- /dev/null
+++ b/tungsten_tempest_plugin/tests/unit/__init__.py
diff --git a/tungsten_tempest_plugin/version.py b/tungsten_tempest_plugin/version.py
new file mode 100644
index 0000000..0a387dc
--- /dev/null
+++ b/tungsten_tempest_plugin/version.py
@@ -0,0 +1,18 @@
+# Copyright (c) 2017 AT&T Corporation.
+#
+# 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 pbr.version
+
+version_info = pbr.version.VersionInfo('tungsten_tempest')