Skip modifying creds if Variables.robot is missing
[functest.git] / functest / opnfv_tests / sdn / odl / odl.py
1 #!/usr/bin/env python
2
3 # Copyright (c) 2016 Orange and others.
4 #
5 # All rights reserved. This program and the accompanying materials
6 # are made available under the terms of the Apache License, Version 2.0
7 # which accompanies this distribution, and is available at
8 # http://www.apache.org/licenses/LICENSE-2.0
9
10 """Define classes required to run ODL suites.
11
12 It has been designed for any context. But helpers are given for
13 running test suites in OPNFV environment.
14
15 Example:
16         $ python odl.py
17 """
18
19 from __future__ import division
20
21 import argparse
22 import fileinput
23 import logging
24 import os
25 import re
26 import sys
27
28 from six.moves import urllib
29
30 from functest.core import robotframework
31 from functest.utils import constants
32 import functest.utils.openstack_utils as op_utils
33
34 __author__ = "Cedric Ollivier <cedric.ollivier@orange.com>"
35
36
37 class ODLTests(robotframework.RobotFramework):
38     """ODL test runner."""
39
40     odl_test_repo = constants.CONST.__getattribute__('dir_repo_odl_test')
41     neutron_suite_dir = os.path.join(
42         odl_test_repo, "csit/suites/openstack/neutron")
43     basic_suite_dir = os.path.join(
44         odl_test_repo, "csit/suites/integration/basic")
45     default_suites = [basic_suite_dir, neutron_suite_dir]
46     odl_variables_file = os.path.join(
47         odl_test_repo, 'csit/variables/Variables.robot')
48     __logger = logging.getLogger(__name__)
49
50     def __init__(self, **kwargs):
51         super(ODLTests, self).__init__(**kwargs)
52         self.res_dir = os.path.join(
53             constants.CONST.__getattribute__('dir_results'), 'odl')
54         self.xml_file = os.path.join(self.res_dir, 'output.xml')
55
56     @classmethod
57     def set_robotframework_vars(cls, odlusername="admin", odlpassword="admin"):
58         """Set credentials in csit/variables/Variables.robot.
59
60         Returns:
61             True if credentials are set.
62             False otherwise.
63         """
64
65         try:
66             for line in fileinput.input(cls.odl_variables_file,
67                                         inplace=True):
68                 print(re.sub("@{AUTH}.*",
69                              "@{{AUTH}}           {}    {}".format(
70                                  odlusername, odlpassword),
71                              line.rstrip()))
72             return True
73         except Exception:  # pylint: disable=broad-except
74             cls.__logger.exception("Cannot set ODL creds:")
75             return False
76
77     def run_suites(self, suites=None, **kwargs):
78         """Run the test suites
79
80         It has been designed to be called in any context.
81         It requires the following keyword arguments:
82
83            * odlusername,
84            * odlpassword,
85            * osauthurl,
86            * neutronurl,
87            * osusername,
88            * osprojectname,
89            * ospassword,
90            * odlip,
91            * odlwebport,
92            * odlrestconfport.
93
94         Here are the steps:
95            * set all RobotFramework_variables,
96            * create the output directories if required,
97            * get the results in output.xml,
98            * delete temporary files.
99
100         Args:
101             kwargs: Arbitrary keyword arguments.
102
103         Returns:
104             EX_OK if all suites ran well.
105             EX_RUN_ERROR otherwise.
106         """
107         try:
108             if not suites:
109                 suites = self.default_suites
110             odlusername = kwargs['odlusername']
111             odlpassword = kwargs['odlpassword']
112             osauthurl = kwargs['osauthurl']
113             keystoneurl = "{}://{}".format(
114                 urllib.parse.urlparse(osauthurl).scheme,
115                 urllib.parse.urlparse(osauthurl).netloc)
116             variable = ['KEYSTONEURL:' + keystoneurl,
117                         'NEUTRONURL:' + kwargs['neutronurl'],
118                         'OS_AUTH_URL:"' + osauthurl + '"',
119                         'OSUSERNAME:"' + kwargs['osusername'] + '"',
120                         ('OSUSERDOMAINNAME:"' +
121                          kwargs['osuserdomainname'] + '"'),
122                         'OSTENANTNAME:"' + kwargs['osprojectname'] + '"',
123                         ('OSPROJECTDOMAINNAME:"' +
124                          kwargs['osprojectdomainname'] + '"'),
125                         'OSPASSWORD:"' + kwargs['ospassword'] + '"',
126                         'ODL_SYSTEM_IP:' + kwargs['odlip'],
127                         'PORT:' + kwargs['odlwebport'],
128                         'RESTCONFPORT:' + kwargs['odlrestconfport']]
129         except KeyError:
130             self.__logger.exception("Cannot run ODL testcases. Please check")
131             return self.EX_RUN_ERROR
132         if not os.path.isfile(self.odl_variables_file):
133             self.__logger.info("Skip writting ODL creds")
134         else:
135             if not self.set_robotframework_vars(odlusername, odlpassword):
136                 return self.EX_RUN_ERROR
137         return super(ODLTests, self).run(variable=variable, suites=suites)
138
139     def run(self, **kwargs):
140         """Run suites in OPNFV environment
141
142         It basically check env vars to call main() with the keywords
143         required.
144
145         Args:
146             kwargs: Arbitrary keyword arguments.
147
148         Returns:
149             EX_OK if all suites ran well.
150             EX_RUN_ERROR otherwise.
151         """
152         try:
153             suites = self.default_suites
154             try:
155                 suites = kwargs["suites"]
156             except KeyError:
157                 pass
158             kwargs = {'neutronurl': op_utils.get_endpoint(
159                 service_type='network')}
160             kwargs['odlip'] = urllib.parse.urlparse(
161                 kwargs['neutronurl']).hostname
162             kwargs['odlwebport'] = '8080'
163             kwargs['odlrestconfport'] = '8181'
164             kwargs['odlusername'] = 'admin'
165             kwargs['odlpassword'] = 'admin'
166             installer_type = None
167             if 'INSTALLER_TYPE' in os.environ:
168                 installer_type = os.environ['INSTALLER_TYPE']
169             kwargs['osusername'] = os.environ['OS_USERNAME']
170             kwargs['osuserdomainname'] = os.environ.get(
171                 'OS_USER_DOMAIN_NAME', 'Default')
172             kwargs['osprojectname'] = os.environ['OS_PROJECT_NAME']
173             kwargs['osprojectdomainname'] = os.environ.get(
174                 'OS_PROJECT_DOMAIN_NAME', 'Default')
175             kwargs['osauthurl'] = os.environ['OS_AUTH_URL']
176             kwargs['ospassword'] = os.environ['OS_PASSWORD']
177             if installer_type == 'fuel':
178                 kwargs['odlwebport'] = '8181'
179                 kwargs['odlrestconfport'] = '8282'
180             elif installer_type == 'apex' or installer_type == 'netvirt':
181                 kwargs['odlip'] = os.environ['SDN_CONTROLLER_IP']
182                 kwargs['odlwebport'] = '8081'
183                 kwargs['odlrestconfport'] = '8081'
184             elif installer_type == 'joid':
185                 kwargs['odlip'] = os.environ['SDN_CONTROLLER']
186             elif installer_type == 'compass':
187                 kwargs['odlrestconfport'] = '8080'
188             elif installer_type == 'daisy':
189                 kwargs['odlip'] = os.environ['SDN_CONTROLLER_IP']
190                 kwargs['odlwebport'] = '8181'
191                 kwargs['odlrestconfport'] = '8087'
192             else:
193                 kwargs['odlip'] = os.environ['SDN_CONTROLLER_IP']
194         except KeyError as ex:
195             self.__logger.error("Cannot run ODL testcases. "
196                                 "Please check env var: "
197                                 "%s", str(ex))
198             return self.EX_RUN_ERROR
199         except Exception:  # pylint: disable=broad-except
200             self.__logger.exception("Cannot run ODL testcases.")
201             return self.EX_RUN_ERROR
202
203         return self.run_suites(suites, **kwargs)
204
205
206 class ODLParser(object):  # pylint: disable=too-few-public-methods
207     """Parser to run ODL test suites."""
208
209     def __init__(self):
210         self.parser = argparse.ArgumentParser()
211         self.parser.add_argument(
212             '-n', '--neutronurl', help='Neutron Endpoint',
213             default='http://127.0.0.1:9696')
214         self.parser.add_argument(
215             '-k', '--osauthurl', help='OS_AUTH_URL as defined by OpenStack',
216             default='http://127.0.0.1:5000/v3')
217         self.parser.add_argument(
218             '-a', '--osusername', help='Username for OpenStack',
219             default='admin')
220         self.parser.add_argument(
221             '-f', '--osuserdomainname', help='User domain name for OpenStack',
222             default='Default')
223         self.parser.add_argument(
224             '-b', '--osprojectname', help='Projet name for OpenStack',
225             default='admin')
226         self.parser.add_argument(
227             '-g', '--osprojectdomainname',
228             help='Project domain name for OpenStack',
229             default='Default')
230         self.parser.add_argument(
231             '-c', '--ospassword', help='Password for OpenStack',
232             default='admin')
233         self.parser.add_argument(
234             '-o', '--odlip', help='OpenDaylight IP',
235             default='127.0.0.1')
236         self.parser.add_argument(
237             '-w', '--odlwebport', help='OpenDaylight Web Portal Port',
238             default='8080')
239         self.parser.add_argument(
240             '-r', '--odlrestconfport', help='OpenDaylight RESTConf Port',
241             default='8181')
242         self.parser.add_argument(
243             '-d', '--odlusername', help='Username for ODL',
244             default='admin')
245         self.parser.add_argument(
246             '-e', '--odlpassword', help='Password for ODL',
247             default='admin')
248         self.parser.add_argument(
249             '-p', '--pushtodb', help='Push results to DB',
250             action='store_true')
251
252     def parse_args(self, argv=None):
253         """Parse arguments.
254
255         It can call sys.exit if arguments are incorrect.
256
257         Returns:
258             the arguments from cmdline
259         """
260         if not argv:
261             argv = []
262         return vars(self.parser.parse_args(argv))
263
264
265 def main():
266     """Entry point"""
267     logging.basicConfig()
268     odl = ODLTests()
269     parser = ODLParser()
270     args = parser.parse_args(sys.argv[1:])
271     try:
272         result = odl.run_suites(ODLTests.default_suites, **args)
273         if result != robotframework.RobotFramework.EX_OK:
274             return result
275         if args['pushtodb']:
276             return odl.push_to_db()
277         else:
278             return result
279     except Exception:  # pylint: disable=broad-except
280         return robotframework.RobotFramework.EX_RUN_ERROR