Statistics
| Branch: | Tag: | Revision:

root / snf-tools / synnefo_tools / burnin / common.py @ fe81ddd7

History | View | Annotate | Download (23.7 kB)

1 4c52d5bf Ilias Tsitsimpis
# Copyright 2013 GRNET S.A. All rights reserved.
2 4c52d5bf Ilias Tsitsimpis
#
3 4c52d5bf Ilias Tsitsimpis
# Redistribution and use in source and binary forms, with or
4 4c52d5bf Ilias Tsitsimpis
# without modification, are permitted provided that the following
5 4c52d5bf Ilias Tsitsimpis
# conditions are met:
6 4c52d5bf Ilias Tsitsimpis
#
7 4c52d5bf Ilias Tsitsimpis
#   1. Redistributions of source code must retain the above
8 4c52d5bf Ilias Tsitsimpis
#      copyright notice, this list of conditions and the following
9 4c52d5bf Ilias Tsitsimpis
#      disclaimer.
10 4c52d5bf Ilias Tsitsimpis
#
11 4c52d5bf Ilias Tsitsimpis
#   2. Redistributions in binary form must reproduce the above
12 4c52d5bf Ilias Tsitsimpis
#      copyright notice, this list of conditions and the following
13 4c52d5bf Ilias Tsitsimpis
#      disclaimer in the documentation and/or other materials
14 4c52d5bf Ilias Tsitsimpis
#      provided with the distribution.
15 4c52d5bf Ilias Tsitsimpis
#
16 4c52d5bf Ilias Tsitsimpis
# THIS SOFTWARE IS PROVIDED BY GRNET S.A. ``AS IS'' AND ANY EXPRESS
17 4c52d5bf Ilias Tsitsimpis
# OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
18 4c52d5bf Ilias Tsitsimpis
# WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
19 4c52d5bf Ilias Tsitsimpis
# PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL GRNET S.A OR
20 4c52d5bf Ilias Tsitsimpis
# CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
21 4c52d5bf Ilias Tsitsimpis
# SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
22 4c52d5bf Ilias Tsitsimpis
# LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
23 4c52d5bf Ilias Tsitsimpis
# USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
24 4c52d5bf Ilias Tsitsimpis
# AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
25 4c52d5bf Ilias Tsitsimpis
# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
26 4c52d5bf Ilias Tsitsimpis
# ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
27 4c52d5bf Ilias Tsitsimpis
# POSSIBILITY OF SUCH DAMAGE.
28 4c52d5bf Ilias Tsitsimpis
#
29 4c52d5bf Ilias Tsitsimpis
# The views and conclusions contained in the software and
30 4c52d5bf Ilias Tsitsimpis
# documentation are those of the authors and should not be
31 4c52d5bf Ilias Tsitsimpis
# interpreted as representing official policies, either expressed
32 4c52d5bf Ilias Tsitsimpis
# or implied, of GRNET S.A.
33 4c52d5bf Ilias Tsitsimpis
34 4c52d5bf Ilias Tsitsimpis
"""
35 4c52d5bf Ilias Tsitsimpis
Common utils for burnin tests
36 4c52d5bf Ilias Tsitsimpis

37 4c52d5bf Ilias Tsitsimpis
"""
38 4c52d5bf Ilias Tsitsimpis
39 f772699c Ilias Tsitsimpis
import re
40 f772699c Ilias Tsitsimpis
import shutil
41 d11c80c0 Ilias Tsitsimpis
import unittest
42 6f2b9836 Ilias Tsitsimpis
import datetime
43 f772699c Ilias Tsitsimpis
import tempfile
44 4c52d5bf Ilias Tsitsimpis
import traceback
45 fe81ddd7 Stavros Sachtouris
from tempfile import NamedTemporaryFile
46 fe81ddd7 Stavros Sachtouris
from os import urandom
47 fe81ddd7 Stavros Sachtouris
from sys import stderr
48 4c52d5bf Ilias Tsitsimpis
49 60a80953 Ilias Tsitsimpis
from kamaki.clients.cyclades import CycladesClient, CycladesNetworkClient
50 eca500f3 Ilias Tsitsimpis
from kamaki.clients.astakos import AstakosClient, parse_endpoints
51 4c52d5bf Ilias Tsitsimpis
from kamaki.clients.compute import ComputeClient
52 79a5c431 Ilias Tsitsimpis
from kamaki.clients.pithos import PithosClient
53 f772699c Ilias Tsitsimpis
from kamaki.clients.image import ImageClient
54 4c52d5bf Ilias Tsitsimpis
55 12ef696f Ilias Tsitsimpis
from synnefo_tools.burnin.logger import Log
56 4c52d5bf Ilias Tsitsimpis
57 4c52d5bf Ilias Tsitsimpis
58 4c52d5bf Ilias Tsitsimpis
# --------------------------------------------------------------------
59 4c52d5bf Ilias Tsitsimpis
# Global variables
60 08f1780b Ilias Tsitsimpis
logger = None   # Invalid constant name. pylint: disable-msg=C0103
61 08f1780b Ilias Tsitsimpis
success = None  # Invalid constant name. pylint: disable-msg=C0103
62 12ef696f Ilias Tsitsimpis
SNF_TEST_PREFIX = "snf-test-"
63 4c52d5bf Ilias Tsitsimpis
CONNECTION_RETRY_LIMIT = 2
64 f772699c Ilias Tsitsimpis
SYSTEM_USERS = ["images@okeanos.grnet.gr", "images@demo.synnefo.org"]
65 3e5bbd85 Ilias Tsitsimpis
KB = 2**10
66 3e5bbd85 Ilias Tsitsimpis
MB = 2**20
67 3e5bbd85 Ilias Tsitsimpis
GB = 2**30
68 4c52d5bf Ilias Tsitsimpis
69 4c52d5bf Ilias Tsitsimpis
70 4c52d5bf Ilias Tsitsimpis
# --------------------------------------------------------------------
71 4c52d5bf Ilias Tsitsimpis
# BurninTestResult class
72 4c52d5bf Ilias Tsitsimpis
class BurninTestResult(unittest.TestResult):
73 4c52d5bf Ilias Tsitsimpis
    """Modify the TextTestResult class"""
74 4c52d5bf Ilias Tsitsimpis
    def __init__(self):
75 4c52d5bf Ilias Tsitsimpis
        super(BurninTestResult, self).__init__()
76 4c52d5bf Ilias Tsitsimpis
77 4c52d5bf Ilias Tsitsimpis
        # Test parameters
78 4c52d5bf Ilias Tsitsimpis
        self.failfast = True
79 4c52d5bf Ilias Tsitsimpis
80 4c52d5bf Ilias Tsitsimpis
    def startTest(self, test):  # noqa
81 4c52d5bf Ilias Tsitsimpis
        """Called when the test case test is about to be run"""
82 4c52d5bf Ilias Tsitsimpis
        super(BurninTestResult, self).startTest(test)
83 3139b628 Stavros Sachtouris
        logger.log(
84 3139b628 Stavros Sachtouris
            test.__class__.__name__,
85 3139b628 Stavros Sachtouris
            test.shortDescription() or 'Test %s' % test.__class__.__name__)
86 4c52d5bf Ilias Tsitsimpis
87 4c52d5bf Ilias Tsitsimpis
    # Method could be a function. pylint: disable-msg=R0201
88 4c52d5bf Ilias Tsitsimpis
    def _test_failed(self, test, err):
89 4c52d5bf Ilias Tsitsimpis
        """Test failed"""
90 79a5c431 Ilias Tsitsimpis
        # Get class name
91 79a5c431 Ilias Tsitsimpis
        if test.__class__.__name__ == "_ErrorHolder":
92 79a5c431 Ilias Tsitsimpis
            class_name = test.id().split('.')[-1].rstrip(')')
93 79a5c431 Ilias Tsitsimpis
        else:
94 79a5c431 Ilias Tsitsimpis
            class_name = test.__class__.__name__
95 fe15cd00 Ilias Tsitsimpis
        err_msg = str(test) + "... failed (%s)."
96 6f2b9836 Ilias Tsitsimpis
        timestamp = datetime.datetime.strftime(
97 6f2b9836 Ilias Tsitsimpis
            datetime.datetime.now(), "%a %b %d %Y %H:%M:%S")
98 79a5c431 Ilias Tsitsimpis
        logger.error(class_name, err_msg, timestamp)
99 4c52d5bf Ilias Tsitsimpis
        (err_type, err_value, err_trace) = err
100 4c52d5bf Ilias Tsitsimpis
        trcback = traceback.format_exception(err_type, err_value, err_trace)
101 79a5c431 Ilias Tsitsimpis
        logger.info(class_name, trcback)
102 4c52d5bf Ilias Tsitsimpis
103 4c52d5bf Ilias Tsitsimpis
    def addError(self, test, err):  # noqa
104 4c52d5bf Ilias Tsitsimpis
        """Called when the test case test raises an unexpected exception"""
105 4c52d5bf Ilias Tsitsimpis
        super(BurninTestResult, self).addError(test, err)
106 4c52d5bf Ilias Tsitsimpis
        self._test_failed(test, err)
107 4c52d5bf Ilias Tsitsimpis
108 4c52d5bf Ilias Tsitsimpis
    def addFailure(self, test, err):  # noqa
109 4c52d5bf Ilias Tsitsimpis
        """Called when the test case test signals a failure"""
110 4c52d5bf Ilias Tsitsimpis
        super(BurninTestResult, self).addFailure(test, err)
111 4c52d5bf Ilias Tsitsimpis
        self._test_failed(test, err)
112 4c52d5bf Ilias Tsitsimpis
113 4c52d5bf Ilias Tsitsimpis
114 4c52d5bf Ilias Tsitsimpis
# --------------------------------------------------------------------
115 5bef1f49 Ilias Tsitsimpis
# Helper Classes
116 6c78720b Ilias Tsitsimpis
# Too few public methods. pylint: disable-msg=R0903
117 6c78720b Ilias Tsitsimpis
# Too many instance attributes. pylint: disable-msg=R0902
118 12ef696f Ilias Tsitsimpis
class Clients(object):
119 12ef696f Ilias Tsitsimpis
    """Our kamaki clients"""
120 12ef696f Ilias Tsitsimpis
    auth_url = None
121 12ef696f Ilias Tsitsimpis
    token = None
122 79a5c431 Ilias Tsitsimpis
    # Astakos
123 12ef696f Ilias Tsitsimpis
    astakos = None
124 12ef696f Ilias Tsitsimpis
    retry = CONNECTION_RETRY_LIMIT
125 79a5c431 Ilias Tsitsimpis
    # Compute
126 12ef696f Ilias Tsitsimpis
    compute = None
127 12ef696f Ilias Tsitsimpis
    compute_url = None
128 79a5c431 Ilias Tsitsimpis
    # Cyclades
129 79a5c431 Ilias Tsitsimpis
    cyclades = None
130 60a80953 Ilias Tsitsimpis
    # Network
131 60a80953 Ilias Tsitsimpis
    network = None
132 60a80953 Ilias Tsitsimpis
    network_url = None
133 79a5c431 Ilias Tsitsimpis
    # Pithos
134 79a5c431 Ilias Tsitsimpis
    pithos = None
135 79a5c431 Ilias Tsitsimpis
    pithos_url = None
136 f772699c Ilias Tsitsimpis
    # Image
137 f772699c Ilias Tsitsimpis
    image = None
138 f772699c Ilias Tsitsimpis
    image_url = None
139 12ef696f Ilias Tsitsimpis
140 5bef1f49 Ilias Tsitsimpis
    def initialize_clients(self):
141 5bef1f49 Ilias Tsitsimpis
        """Initialize all the Kamaki Clients"""
142 5bef1f49 Ilias Tsitsimpis
        self.astakos = AstakosClient(self.auth_url, self.token)
143 5bef1f49 Ilias Tsitsimpis
        self.astakos.CONNECTION_RETRY_LIMIT = self.retry
144 5bef1f49 Ilias Tsitsimpis
145 eca500f3 Ilias Tsitsimpis
        endpoints = self.astakos.authenticate()
146 eca500f3 Ilias Tsitsimpis
147 eca500f3 Ilias Tsitsimpis
        self.compute_url = _get_endpoint_url(endpoints, "compute")
148 5bef1f49 Ilias Tsitsimpis
        self.compute = ComputeClient(self.compute_url, self.token)
149 5bef1f49 Ilias Tsitsimpis
        self.compute.CONNECTION_RETRY_LIMIT = self.retry
150 5bef1f49 Ilias Tsitsimpis
151 5bef1f49 Ilias Tsitsimpis
        self.cyclades = CycladesClient(self.compute_url, self.token)
152 5bef1f49 Ilias Tsitsimpis
        self.cyclades.CONNECTION_RETRY_LIMIT = self.retry
153 5bef1f49 Ilias Tsitsimpis
154 eca500f3 Ilias Tsitsimpis
        self.network_url = _get_endpoint_url(endpoints, "network")
155 60a80953 Ilias Tsitsimpis
        self.network = CycladesNetworkClient(self.network_url, self.token)
156 60a80953 Ilias Tsitsimpis
        self.network.CONNECTION_RETRY_LIMIT = self.retry
157 60a80953 Ilias Tsitsimpis
158 eca500f3 Ilias Tsitsimpis
        self.pithos_url = _get_endpoint_url(endpoints, "object-store")
159 5bef1f49 Ilias Tsitsimpis
        self.pithos = PithosClient(self.pithos_url, self.token)
160 5bef1f49 Ilias Tsitsimpis
        self.pithos.CONNECTION_RETRY_LIMIT = self.retry
161 5bef1f49 Ilias Tsitsimpis
162 eca500f3 Ilias Tsitsimpis
        self.image_url = _get_endpoint_url(endpoints, "image")
163 5bef1f49 Ilias Tsitsimpis
        self.image = ImageClient(self.image_url, self.token)
164 5bef1f49 Ilias Tsitsimpis
        self.image.CONNECTION_RETRY_LIMIT = self.retry
165 5bef1f49 Ilias Tsitsimpis
166 5bef1f49 Ilias Tsitsimpis
167 eca500f3 Ilias Tsitsimpis
def _get_endpoint_url(endpoints, endpoint_type):
168 eca500f3 Ilias Tsitsimpis
    """Get the publicURL for the specified endpoint"""
169 eca500f3 Ilias Tsitsimpis
170 eca500f3 Ilias Tsitsimpis
    service_catalog = parse_endpoints(endpoints, ep_type=endpoint_type)
171 eca500f3 Ilias Tsitsimpis
    return service_catalog[0]['endpoints'][0]['publicURL']
172 eca500f3 Ilias Tsitsimpis
173 eca500f3 Ilias Tsitsimpis
174 5bef1f49 Ilias Tsitsimpis
class Proper(object):
175 5bef1f49 Ilias Tsitsimpis
    """A descriptor used by tests implementing the TestCase class
176 5bef1f49 Ilias Tsitsimpis

177 5bef1f49 Ilias Tsitsimpis
    Since each instance of the TestCase will only be used to run a single
178 5bef1f49 Ilias Tsitsimpis
    test method (a new fixture is created for each test) the attributes can
179 5bef1f49 Ilias Tsitsimpis
    not be saved in the class instances. Instead we use descriptors.
180 12ef696f Ilias Tsitsimpis

181 5bef1f49 Ilias Tsitsimpis
    """
182 5bef1f49 Ilias Tsitsimpis
    def __init__(self, value=None):
183 5bef1f49 Ilias Tsitsimpis
        self.val = value
184 5bef1f49 Ilias Tsitsimpis
185 5bef1f49 Ilias Tsitsimpis
    def __get__(self, obj, objtype=None):
186 5bef1f49 Ilias Tsitsimpis
        return self.val
187 5bef1f49 Ilias Tsitsimpis
188 5bef1f49 Ilias Tsitsimpis
    def __set__(self, obj, value):
189 5bef1f49 Ilias Tsitsimpis
        self.val = value
190 5bef1f49 Ilias Tsitsimpis
191 5bef1f49 Ilias Tsitsimpis
192 5bef1f49 Ilias Tsitsimpis
# --------------------------------------------------------------------
193 5bef1f49 Ilias Tsitsimpis
# BurninTests class
194 4c52d5bf Ilias Tsitsimpis
# Too many public methods (45/20). pylint: disable-msg=R0904
195 4c52d5bf Ilias Tsitsimpis
class BurninTests(unittest.TestCase):
196 4c52d5bf Ilias Tsitsimpis
    """Common class that all burnin tests should implement"""
197 12ef696f Ilias Tsitsimpis
    clients = Clients()
198 6f2b9836 Ilias Tsitsimpis
    run_id = None
199 79a5c431 Ilias Tsitsimpis
    use_ipv6 = None
200 79a5c431 Ilias Tsitsimpis
    action_timeout = None
201 79a5c431 Ilias Tsitsimpis
    action_warning = None
202 79a5c431 Ilias Tsitsimpis
    query_interval = None
203 f772699c Ilias Tsitsimpis
    system_user = None
204 6c78720b Ilias Tsitsimpis
    images = None
205 6c78720b Ilias Tsitsimpis
    flavors = None
206 8c67f82e Ilias Tsitsimpis
    delete_stale = False
207 24d1788b Ilias Tsitsimpis
    temp_directory = None
208 2c60bfa6 Ilias Tsitsimpis
    failfast = None
209 49517b8a Stavros Sachtouris
    temp_containers = []
210 49517b8a Stavros Sachtouris
211 12ef696f Ilias Tsitsimpis
212 5bef1f49 Ilias Tsitsimpis
    quotas = Proper(value=None)
213 5bef1f49 Ilias Tsitsimpis
214 4c52d5bf Ilias Tsitsimpis
    @classmethod
215 4c52d5bf Ilias Tsitsimpis
    def setUpClass(cls):  # noqa
216 4c52d5bf Ilias Tsitsimpis
        """Initialize BurninTests"""
217 4c52d5bf Ilias Tsitsimpis
        cls.suite_name = cls.__name__
218 4c52d5bf Ilias Tsitsimpis
        logger.testsuite_start(cls.suite_name)
219 4c52d5bf Ilias Tsitsimpis
220 4c52d5bf Ilias Tsitsimpis
        # Set test parameters
221 4c52d5bf Ilias Tsitsimpis
        cls.longMessage = True
222 4c52d5bf Ilias Tsitsimpis
223 fe15cd00 Ilias Tsitsimpis
    def test_000_clients_setup(self):
224 4c52d5bf Ilias Tsitsimpis
        """Initializing astakos/cyclades/pithos clients"""
225 4c52d5bf Ilias Tsitsimpis
        # Update class attributes
226 5bef1f49 Ilias Tsitsimpis
        self.clients.initialize_clients()
227 12ef696f Ilias Tsitsimpis
        self.info("Astakos auth url is %s", self.clients.auth_url)
228 12ef696f Ilias Tsitsimpis
        self.info("Cyclades url is %s", self.clients.compute_url)
229 60a80953 Ilias Tsitsimpis
        self.info("Network url is %s", self.clients.network_url)
230 79a5c431 Ilias Tsitsimpis
        self.info("Pithos url is %s", self.clients.pithos_url)
231 f772699c Ilias Tsitsimpis
        self.info("Image url is %s", self.clients.image_url)
232 5bef1f49 Ilias Tsitsimpis
233 5bef1f49 Ilias Tsitsimpis
        self.quotas = self._get_quotas()
234 3e5bbd85 Ilias Tsitsimpis
        self.info("  Disk usage is %s bytes",
235 5bef1f49 Ilias Tsitsimpis
                  self.quotas['system']['cyclades.disk']['usage'])
236 5bef1f49 Ilias Tsitsimpis
        self.info("  VM usage is %s",
237 5bef1f49 Ilias Tsitsimpis
                  self.quotas['system']['cyclades.vm']['usage'])
238 3e5bbd85 Ilias Tsitsimpis
        self.info("  DiskSpace usage is %s bytes",
239 5bef1f49 Ilias Tsitsimpis
                  self.quotas['system']['pithos.diskspace']['usage'])
240 3e5bbd85 Ilias Tsitsimpis
        self.info("  Ram usage is %s bytes",
241 5bef1f49 Ilias Tsitsimpis
                  self.quotas['system']['cyclades.ram']['usage'])
242 60a80953 Ilias Tsitsimpis
        self.info("  Floating IPs usage is %s",
243 60a80953 Ilias Tsitsimpis
                  self.quotas['system']['cyclades.floating_ip']['usage'])
244 5bef1f49 Ilias Tsitsimpis
        self.info("  CPU usage is %s",
245 5bef1f49 Ilias Tsitsimpis
                  self.quotas['system']['cyclades.cpu']['usage'])
246 5bef1f49 Ilias Tsitsimpis
        self.info("  Network usage is %s",
247 5bef1f49 Ilias Tsitsimpis
                  self.quotas['system']['cyclades.network.private']['usage'])
248 f772699c Ilias Tsitsimpis
249 08f1780b Ilias Tsitsimpis
    def _run_tests(self, tcases):
250 08f1780b Ilias Tsitsimpis
        """Run some generated testcases"""
251 08f1780b Ilias Tsitsimpis
        global success  # Using global. pylint: disable-msg=C0103,W0603,W0602
252 08f1780b Ilias Tsitsimpis
253 08f1780b Ilias Tsitsimpis
        for tcase in tcases:
254 08f1780b Ilias Tsitsimpis
            self.info("Running testsuite %s", tcase.__name__)
255 08f1780b Ilias Tsitsimpis
            success = run_test(tcase) and success
256 08f1780b Ilias Tsitsimpis
            if self.failfast and not success:
257 08f1780b Ilias Tsitsimpis
                break
258 08f1780b Ilias Tsitsimpis
259 6f2b9836 Ilias Tsitsimpis
    # ----------------------------------
260 6f2b9836 Ilias Tsitsimpis
    # Loggers helper functions
261 4c52d5bf Ilias Tsitsimpis
    def log(self, msg, *args):
262 4c52d5bf Ilias Tsitsimpis
        """Pass the section value to logger"""
263 4c52d5bf Ilias Tsitsimpis
        logger.log(self.suite_name, msg, *args)
264 4c52d5bf Ilias Tsitsimpis
265 4c52d5bf Ilias Tsitsimpis
    def info(self, msg, *args):
266 4c52d5bf Ilias Tsitsimpis
        """Pass the section value to logger"""
267 4c52d5bf Ilias Tsitsimpis
        logger.info(self.suite_name, msg, *args)
268 4c52d5bf Ilias Tsitsimpis
269 4c52d5bf Ilias Tsitsimpis
    def debug(self, msg, *args):
270 4c52d5bf Ilias Tsitsimpis
        """Pass the section value to logger"""
271 4c52d5bf Ilias Tsitsimpis
        logger.debug(self.suite_name, msg, *args)
272 4c52d5bf Ilias Tsitsimpis
273 4c52d5bf Ilias Tsitsimpis
    def warning(self, msg, *args):
274 4c52d5bf Ilias Tsitsimpis
        """Pass the section value to logger"""
275 4c52d5bf Ilias Tsitsimpis
        logger.warning(self.suite_name, msg, *args)
276 4c52d5bf Ilias Tsitsimpis
277 4c52d5bf Ilias Tsitsimpis
    def error(self, msg, *args):
278 4c52d5bf Ilias Tsitsimpis
        """Pass the section value to logger"""
279 4c52d5bf Ilias Tsitsimpis
        logger.error(self.suite_name, msg, *args)
280 4c52d5bf Ilias Tsitsimpis
281 6f2b9836 Ilias Tsitsimpis
    # ----------------------------------
282 6f2b9836 Ilias Tsitsimpis
    # Helper functions that every testsuite may need
283 6f2b9836 Ilias Tsitsimpis
    def _get_uuid(self):
284 6f2b9836 Ilias Tsitsimpis
        """Get our uuid"""
285 6f2b9836 Ilias Tsitsimpis
        authenticate = self.clients.astakos.authenticate()
286 6f2b9836 Ilias Tsitsimpis
        uuid = authenticate['access']['user']['id']
287 6f2b9836 Ilias Tsitsimpis
        self.info("User's uuid is %s", uuid)
288 6f2b9836 Ilias Tsitsimpis
        return uuid
289 6f2b9836 Ilias Tsitsimpis
290 6f2b9836 Ilias Tsitsimpis
    def _get_username(self):
291 6f2b9836 Ilias Tsitsimpis
        """Get our User Name"""
292 6f2b9836 Ilias Tsitsimpis
        authenticate = self.clients.astakos.authenticate()
293 6f2b9836 Ilias Tsitsimpis
        username = authenticate['access']['user']['name']
294 6f2b9836 Ilias Tsitsimpis
        self.info("User's name is %s", username)
295 6f2b9836 Ilias Tsitsimpis
        return username
296 6f2b9836 Ilias Tsitsimpis
297 f772699c Ilias Tsitsimpis
    def _create_tmp_directory(self):
298 24d1788b Ilias Tsitsimpis
        """Create a tmp directory"""
299 24d1788b Ilias Tsitsimpis
        temp_dir = tempfile.mkdtemp(dir=self.temp_directory)
300 f772699c Ilias Tsitsimpis
        self.info("Temp directory %s created", temp_dir)
301 f772699c Ilias Tsitsimpis
        return temp_dir
302 f772699c Ilias Tsitsimpis
303 f772699c Ilias Tsitsimpis
    def _remove_tmp_directory(self, tmp_dir):
304 f772699c Ilias Tsitsimpis
        """Remove a tmp directory"""
305 f772699c Ilias Tsitsimpis
        try:
306 f772699c Ilias Tsitsimpis
            shutil.rmtree(tmp_dir)
307 f772699c Ilias Tsitsimpis
            self.info("Temp directory %s deleted", tmp_dir)
308 f772699c Ilias Tsitsimpis
        except OSError:
309 f772699c Ilias Tsitsimpis
            pass
310 f772699c Ilias Tsitsimpis
311 fe81ddd7 Stavros Sachtouris
    def _create_large_file(self, size):
312 fe81ddd7 Stavros Sachtouris
        """Create a large file at fs"""
313 fe81ddd7 Stavros Sachtouris
        f = NamedTemporaryFile()
314 fe81ddd7 Stavros Sachtouris
        Ki = size / 8
315 fe81ddd7 Stavros Sachtouris
        c = ['|', '/', '-', '\\']
316 fe81ddd7 Stavros Sachtouris
        stderr.write('Create file %s  ' % f.name)
317 fe81ddd7 Stavros Sachtouris
        for i, bytes in enumerate([b * Ki for b in range(size / Ki)]):
318 fe81ddd7 Stavros Sachtouris
            f.seek(bytes)
319 fe81ddd7 Stavros Sachtouris
            f.write(urandom(Ki))
320 fe81ddd7 Stavros Sachtouris
            f.flush()
321 fe81ddd7 Stavros Sachtouris
            stderr.write('\b' + c[i % 4])
322 fe81ddd7 Stavros Sachtouris
            stderr.flush()
323 fe81ddd7 Stavros Sachtouris
        stderr.write('\n')
324 fe81ddd7 Stavros Sachtouris
        stderr.flush()
325 fe81ddd7 Stavros Sachtouris
        f.seek(0)
326 fe81ddd7 Stavros Sachtouris
        return f
327 fe81ddd7 Stavros Sachtouris
328 f772699c Ilias Tsitsimpis
    def _get_uuid_of_system_user(self):
329 f772699c Ilias Tsitsimpis
        """Get the uuid of the system user
330 f772699c Ilias Tsitsimpis

331 f772699c Ilias Tsitsimpis
        This is the user that upload the 'official' images.
332 f772699c Ilias Tsitsimpis

333 f772699c Ilias Tsitsimpis
        """
334 f772699c Ilias Tsitsimpis
        self.info("Getting the uuid of the system user")
335 f772699c Ilias Tsitsimpis
        system_users = None
336 f772699c Ilias Tsitsimpis
        if self.system_user is not None:
337 eca500f3 Ilias Tsitsimpis
            try:
338 eca500f3 Ilias Tsitsimpis
                su_type, su_value = parse_typed_option(self.system_user)
339 f772699c Ilias Tsitsimpis
                if su_type == "name":
340 f772699c Ilias Tsitsimpis
                    system_users = [su_value]
341 f772699c Ilias Tsitsimpis
                elif su_type == "id":
342 f772699c Ilias Tsitsimpis
                    self.info("System user's uuid is %s", su_value)
343 f772699c Ilias Tsitsimpis
                    return su_value
344 f772699c Ilias Tsitsimpis
                else:
345 f772699c Ilias Tsitsimpis
                    self.error("Unrecognized system-user type %s", su_type)
346 f772699c Ilias Tsitsimpis
                    self.fail("Unrecognized system-user type")
347 eca500f3 Ilias Tsitsimpis
            except ValueError:
348 eca500f3 Ilias Tsitsimpis
                msg = "Invalid system-user format: %s. Must be [id|name]:.+"
349 eca500f3 Ilias Tsitsimpis
                self.warning(msg, self.system_user)
350 f772699c Ilias Tsitsimpis
351 f772699c Ilias Tsitsimpis
        if system_users is None:
352 f772699c Ilias Tsitsimpis
            system_users = SYSTEM_USERS
353 f772699c Ilias Tsitsimpis
354 a59fbcea Stavros Sachtouris
        uuids = self.clients.astakos.get_uuids(system_users)
355 f772699c Ilias Tsitsimpis
        for su_name in system_users:
356 f772699c Ilias Tsitsimpis
            self.info("Trying username %s", su_name)
357 f772699c Ilias Tsitsimpis
            if su_name in uuids:
358 f772699c Ilias Tsitsimpis
                self.info("System user's uuid is %s", uuids[su_name])
359 f772699c Ilias Tsitsimpis
                return uuids[su_name]
360 f772699c Ilias Tsitsimpis
361 f772699c Ilias Tsitsimpis
        self.warning("No system user found")
362 f772699c Ilias Tsitsimpis
        return None
363 f772699c Ilias Tsitsimpis
364 6c78720b Ilias Tsitsimpis
    def _skip_if(self, condition, msg):
365 6c78720b Ilias Tsitsimpis
        """Skip tests"""
366 6c78720b Ilias Tsitsimpis
        if condition:
367 6c78720b Ilias Tsitsimpis
            self.info("Test skipped: %s" % msg)
368 6c78720b Ilias Tsitsimpis
            self.skipTest(msg)
369 6c78720b Ilias Tsitsimpis
370 f772699c Ilias Tsitsimpis
    # ----------------------------------
371 f772699c Ilias Tsitsimpis
    # Flavors
372 fe15cd00 Ilias Tsitsimpis
    def _get_list_of_flavors(self, detail=False):
373 fe15cd00 Ilias Tsitsimpis
        """Get (detailed) list of flavors"""
374 fe15cd00 Ilias Tsitsimpis
        if detail:
375 fe15cd00 Ilias Tsitsimpis
            self.info("Getting detailed list of flavors")
376 fe15cd00 Ilias Tsitsimpis
        else:
377 fe15cd00 Ilias Tsitsimpis
            self.info("Getting simple list of flavors")
378 fe15cd00 Ilias Tsitsimpis
        flavors = self.clients.compute.list_flavors(detail=detail)
379 fe15cd00 Ilias Tsitsimpis
        return flavors
380 fe15cd00 Ilias Tsitsimpis
381 6c78720b Ilias Tsitsimpis
    def _find_flavors(self, patterns, flavors=None):
382 6c78720b Ilias Tsitsimpis
        """Find a list of suitable flavors to use
383 6c78720b Ilias Tsitsimpis

384 6c78720b Ilias Tsitsimpis
        The patterns is a list of `typed_options'. A list of all flavors
385 6c78720b Ilias Tsitsimpis
        matching this patterns will be returned.
386 6c78720b Ilias Tsitsimpis

387 6c78720b Ilias Tsitsimpis
        """
388 6c78720b Ilias Tsitsimpis
        if flavors is None:
389 6c78720b Ilias Tsitsimpis
            flavors = self._get_list_of_flavors(detail=True)
390 6c78720b Ilias Tsitsimpis
391 6c78720b Ilias Tsitsimpis
        ret_flavors = []
392 6c78720b Ilias Tsitsimpis
        for ptrn in patterns:
393 eca500f3 Ilias Tsitsimpis
            try:
394 eca500f3 Ilias Tsitsimpis
                flv_type, flv_value = parse_typed_option(ptrn)
395 eca500f3 Ilias Tsitsimpis
            except ValueError:
396 6c78720b Ilias Tsitsimpis
                msg = "Invalid flavor format: %s. Must be [id|name]:.+"
397 6c78720b Ilias Tsitsimpis
                self.warning(msg, ptrn)
398 6c78720b Ilias Tsitsimpis
                continue
399 eca500f3 Ilias Tsitsimpis
400 6c78720b Ilias Tsitsimpis
            if flv_type == "name":
401 6c78720b Ilias Tsitsimpis
                # Filter flavor by name
402 6c78720b Ilias Tsitsimpis
                msg = "Trying to find a flavor with name %s"
403 6c78720b Ilias Tsitsimpis
                self.info(msg, flv_value)
404 6c78720b Ilias Tsitsimpis
                filtered_flvs = \
405 6c78720b Ilias Tsitsimpis
                    [f for f in flavors if
406 6c78720b Ilias Tsitsimpis
                     re.search(flv_value, f['name'], flags=re.I) is not None]
407 6c78720b Ilias Tsitsimpis
            elif flv_type == "id":
408 6c78720b Ilias Tsitsimpis
                # Filter flavors by id
409 6c78720b Ilias Tsitsimpis
                msg = "Trying to find a flavor with id %s"
410 6c78720b Ilias Tsitsimpis
                self.info(msg, flv_value)
411 6c78720b Ilias Tsitsimpis
                filtered_flvs = \
412 6c78720b Ilias Tsitsimpis
                    [f for f in flavors if str(f['id']) == flv_value]
413 6c78720b Ilias Tsitsimpis
            else:
414 6c78720b Ilias Tsitsimpis
                self.error("Unrecognized flavor type %s", flv_type)
415 6c78720b Ilias Tsitsimpis
                self.fail("Unrecognized flavor type")
416 6c78720b Ilias Tsitsimpis
417 6c78720b Ilias Tsitsimpis
            # Append and continue
418 6c78720b Ilias Tsitsimpis
            ret_flavors.extend(filtered_flvs)
419 6c78720b Ilias Tsitsimpis
420 6c78720b Ilias Tsitsimpis
        self.assertGreater(len(ret_flavors), 0,
421 6c78720b Ilias Tsitsimpis
                           "No matching flavors found")
422 6c78720b Ilias Tsitsimpis
        return ret_flavors
423 6c78720b Ilias Tsitsimpis
424 f772699c Ilias Tsitsimpis
    # ----------------------------------
425 f772699c Ilias Tsitsimpis
    # Images
426 f772699c Ilias Tsitsimpis
    def _get_list_of_images(self, detail=False):
427 f772699c Ilias Tsitsimpis
        """Get (detailed) list of images"""
428 f772699c Ilias Tsitsimpis
        if detail:
429 f772699c Ilias Tsitsimpis
            self.info("Getting detailed list of images")
430 f772699c Ilias Tsitsimpis
        else:
431 f772699c Ilias Tsitsimpis
            self.info("Getting simple list of images")
432 f772699c Ilias Tsitsimpis
        images = self.clients.image.list_public(detail=detail)
433 f772699c Ilias Tsitsimpis
        # Remove images registered by burnin
434 f772699c Ilias Tsitsimpis
        images = [img for img in images
435 f772699c Ilias Tsitsimpis
                  if not img['name'].startswith(SNF_TEST_PREFIX)]
436 f772699c Ilias Tsitsimpis
        return images
437 f772699c Ilias Tsitsimpis
438 f772699c Ilias Tsitsimpis
    def _get_list_of_sys_images(self, images=None):
439 f772699c Ilias Tsitsimpis
        """Get (detailed) list of images registered by system user or by me"""
440 f772699c Ilias Tsitsimpis
        self.info("Getting list of images registered by system user or by me")
441 f772699c Ilias Tsitsimpis
        if images is None:
442 f772699c Ilias Tsitsimpis
            images = self._get_list_of_images(detail=True)
443 f772699c Ilias Tsitsimpis
444 f772699c Ilias Tsitsimpis
        su_uuid = self._get_uuid_of_system_user()
445 f772699c Ilias Tsitsimpis
        my_uuid = self._get_uuid()
446 f772699c Ilias Tsitsimpis
        ret_images = [i for i in images
447 f772699c Ilias Tsitsimpis
                      if i['owner'] == su_uuid or i['owner'] == my_uuid]
448 f772699c Ilias Tsitsimpis
449 f772699c Ilias Tsitsimpis
        return ret_images
450 f772699c Ilias Tsitsimpis
451 6c78720b Ilias Tsitsimpis
    def _find_images(self, patterns, images=None):
452 6c78720b Ilias Tsitsimpis
        """Find a list of suitable images to use
453 f772699c Ilias Tsitsimpis

454 6c78720b Ilias Tsitsimpis
        The patterns is a list of `typed_options'. A list of all images
455 6c78720b Ilias Tsitsimpis
        matching this patterns will be returned.
456 f772699c Ilias Tsitsimpis

457 f772699c Ilias Tsitsimpis
        """
458 f772699c Ilias Tsitsimpis
        if images is None:
459 f772699c Ilias Tsitsimpis
            images = self._get_list_of_sys_images()
460 f772699c Ilias Tsitsimpis
461 6c78720b Ilias Tsitsimpis
        ret_images = []
462 f772699c Ilias Tsitsimpis
        for ptrn in patterns:
463 eca500f3 Ilias Tsitsimpis
            try:
464 eca500f3 Ilias Tsitsimpis
                img_type, img_value = parse_typed_option(ptrn)
465 eca500f3 Ilias Tsitsimpis
            except ValueError:
466 f772699c Ilias Tsitsimpis
                msg = "Invalid image format: %s. Must be [id|name]:.+"
467 f772699c Ilias Tsitsimpis
                self.warning(msg, ptrn)
468 f772699c Ilias Tsitsimpis
                continue
469 eca500f3 Ilias Tsitsimpis
470 f772699c Ilias Tsitsimpis
            if img_type == "name":
471 f772699c Ilias Tsitsimpis
                # Filter image by name
472 f772699c Ilias Tsitsimpis
                msg = "Trying to find an image with name %s"
473 f772699c Ilias Tsitsimpis
                self.info(msg, img_value)
474 f772699c Ilias Tsitsimpis
                filtered_imgs = \
475 f772699c Ilias Tsitsimpis
                    [i for i in images if
476 f772699c Ilias Tsitsimpis
                     re.search(img_value, i['name'], flags=re.I) is not None]
477 f772699c Ilias Tsitsimpis
            elif img_type == "id":
478 f772699c Ilias Tsitsimpis
                # Filter images by id
479 f772699c Ilias Tsitsimpis
                msg = "Trying to find an image with id %s"
480 f772699c Ilias Tsitsimpis
                self.info(msg, img_value)
481 f772699c Ilias Tsitsimpis
                filtered_imgs = \
482 f772699c Ilias Tsitsimpis
                    [i for i in images if
483 f772699c Ilias Tsitsimpis
                     i['id'].lower() == img_value.lower()]
484 f772699c Ilias Tsitsimpis
            else:
485 f772699c Ilias Tsitsimpis
                self.error("Unrecognized image type %s", img_type)
486 f772699c Ilias Tsitsimpis
                self.fail("Unrecognized image type")
487 f772699c Ilias Tsitsimpis
488 6c78720b Ilias Tsitsimpis
            # Append and continue
489 6c78720b Ilias Tsitsimpis
            ret_images.extend(filtered_imgs)
490 f772699c Ilias Tsitsimpis
491 6c78720b Ilias Tsitsimpis
        self.assertGreater(len(ret_images), 0,
492 6c78720b Ilias Tsitsimpis
                           "No matching images found")
493 6c78720b Ilias Tsitsimpis
        return ret_images
494 f772699c Ilias Tsitsimpis
495 f772699c Ilias Tsitsimpis
    # ----------------------------------
496 f772699c Ilias Tsitsimpis
    # Pithos
497 79a5c431 Ilias Tsitsimpis
    def _set_pithos_account(self, account):
498 f772699c Ilias Tsitsimpis
        """Set the Pithos account"""
499 79a5c431 Ilias Tsitsimpis
        assert account, "No pithos account was given"
500 79a5c431 Ilias Tsitsimpis
501 f772699c Ilias Tsitsimpis
        self.info("Setting Pithos account to %s", account)
502 79a5c431 Ilias Tsitsimpis
        self.clients.pithos.account = account
503 79a5c431 Ilias Tsitsimpis
504 f772699c Ilias Tsitsimpis
    def _set_pithos_container(self, container):
505 f772699c Ilias Tsitsimpis
        """Set the Pithos container"""
506 f772699c Ilias Tsitsimpis
        assert container, "No pithos container was given"
507 f772699c Ilias Tsitsimpis
508 f772699c Ilias Tsitsimpis
        self.info("Setting Pithos container to %s", container)
509 f772699c Ilias Tsitsimpis
        self.clients.pithos.container = container
510 f772699c Ilias Tsitsimpis
511 79a5c431 Ilias Tsitsimpis
    def _get_list_of_containers(self, account=None):
512 79a5c431 Ilias Tsitsimpis
        """Get list of containers"""
513 79a5c431 Ilias Tsitsimpis
        if account is not None:
514 79a5c431 Ilias Tsitsimpis
            self._set_pithos_account(account)
515 79a5c431 Ilias Tsitsimpis
        self.info("Getting list of containers")
516 79a5c431 Ilias Tsitsimpis
        return self.clients.pithos.list_containers()
517 79a5c431 Ilias Tsitsimpis
518 79a5c431 Ilias Tsitsimpis
    def _create_pithos_container(self, container):
519 79a5c431 Ilias Tsitsimpis
        """Create a pithos container
520 79a5c431 Ilias Tsitsimpis

521 79a5c431 Ilias Tsitsimpis
        If the container exists, nothing will happen
522 79a5c431 Ilias Tsitsimpis

523 79a5c431 Ilias Tsitsimpis
        """
524 79a5c431 Ilias Tsitsimpis
        assert container, "No pithos container was given"
525 79a5c431 Ilias Tsitsimpis
526 79a5c431 Ilias Tsitsimpis
        self.info("Creating pithos container %s", container)
527 49517b8a Stavros Sachtouris
        self.clients.pithos.create_container(container)
528 49517b8a Stavros Sachtouris
        self.temp_containers.append(container)
529 79a5c431 Ilias Tsitsimpis
530 5bef1f49 Ilias Tsitsimpis
    # ----------------------------------
531 5bef1f49 Ilias Tsitsimpis
    # Quotas
532 5bef1f49 Ilias Tsitsimpis
    def _get_quotas(self):
533 5bef1f49 Ilias Tsitsimpis
        """Get quotas"""
534 3e5bbd85 Ilias Tsitsimpis
        self.info("Getting quotas")
535 a59fbcea Stavros Sachtouris
        return self.clients.astakos.get_quotas()
536 5bef1f49 Ilias Tsitsimpis
537 3e5bbd85 Ilias Tsitsimpis
    # Invalid argument name. pylint: disable-msg=C0103
538 3e5bbd85 Ilias Tsitsimpis
    # Too many arguments. pylint: disable-msg=R0913
539 3e5bbd85 Ilias Tsitsimpis
    def _check_quotas(self, disk=None, vm=None, diskspace=None,
540 60a80953 Ilias Tsitsimpis
                      ram=None, ip=None, cpu=None, network=None):
541 3e5bbd85 Ilias Tsitsimpis
        """Check that quotas' changes are consistent"""
542 3e5bbd85 Ilias Tsitsimpis
        assert any(v is None for v in
543 60a80953 Ilias Tsitsimpis
                   [disk, vm, diskspace, ram, ip, cpu, network]), \
544 3e5bbd85 Ilias Tsitsimpis
            "_check_quotas require arguments"
545 3e5bbd85 Ilias Tsitsimpis
546 3e5bbd85 Ilias Tsitsimpis
        self.info("Check that quotas' changes are consistent")
547 3e5bbd85 Ilias Tsitsimpis
        old_quotas = self.quotas
548 3e5bbd85 Ilias Tsitsimpis
        new_quotas = self._get_quotas()
549 3e5bbd85 Ilias Tsitsimpis
        self.quotas = new_quotas
550 3e5bbd85 Ilias Tsitsimpis
551 3e5bbd85 Ilias Tsitsimpis
        # Check Disk usage
552 3e5bbd85 Ilias Tsitsimpis
        self._check_quotas_aux(
553 3e5bbd85 Ilias Tsitsimpis
            old_quotas, new_quotas, 'cyclades.disk', disk)
554 3e5bbd85 Ilias Tsitsimpis
        # Check VM usage
555 3e5bbd85 Ilias Tsitsimpis
        self._check_quotas_aux(
556 3e5bbd85 Ilias Tsitsimpis
            old_quotas, new_quotas, 'cyclades.vm', vm)
557 3e5bbd85 Ilias Tsitsimpis
        # Check DiskSpace usage
558 3e5bbd85 Ilias Tsitsimpis
        self._check_quotas_aux(
559 3e5bbd85 Ilias Tsitsimpis
            old_quotas, new_quotas, 'pithos.diskspace', diskspace)
560 3e5bbd85 Ilias Tsitsimpis
        # Check Ram usage
561 3e5bbd85 Ilias Tsitsimpis
        self._check_quotas_aux(
562 3e5bbd85 Ilias Tsitsimpis
            old_quotas, new_quotas, 'cyclades.ram', ram)
563 60a80953 Ilias Tsitsimpis
        # Check Floating IPs usage
564 60a80953 Ilias Tsitsimpis
        self._check_quotas_aux(
565 60a80953 Ilias Tsitsimpis
            old_quotas, new_quotas, 'cyclades.floating_ip', ip)
566 3e5bbd85 Ilias Tsitsimpis
        # Check CPU usage
567 3e5bbd85 Ilias Tsitsimpis
        self._check_quotas_aux(
568 3e5bbd85 Ilias Tsitsimpis
            old_quotas, new_quotas, 'cyclades.cpu', cpu)
569 3e5bbd85 Ilias Tsitsimpis
        # Check Network usage
570 3e5bbd85 Ilias Tsitsimpis
        self._check_quotas_aux(
571 3e5bbd85 Ilias Tsitsimpis
            old_quotas, new_quotas, 'cyclades.network.private', network)
572 3e5bbd85 Ilias Tsitsimpis
573 3e5bbd85 Ilias Tsitsimpis
    def _check_quotas_aux(self, old_quotas, new_quotas, resource, value):
574 3e5bbd85 Ilias Tsitsimpis
        """Auxiliary function for _check_quotas"""
575 3e5bbd85 Ilias Tsitsimpis
        old_value = old_quotas['system'][resource]['usage']
576 3e5bbd85 Ilias Tsitsimpis
        new_value = new_quotas['system'][resource]['usage']
577 3e5bbd85 Ilias Tsitsimpis
        if value is not None:
578 3e5bbd85 Ilias Tsitsimpis
            assert isinstance(value, int), \
579 3e5bbd85 Ilias Tsitsimpis
                "%s value has to be integer" % resource
580 3e5bbd85 Ilias Tsitsimpis
            old_value += value
581 3e5bbd85 Ilias Tsitsimpis
        self.assertEqual(old_value, new_value,
582 3e5bbd85 Ilias Tsitsimpis
                         "%s quotas don't match" % resource)
583 3e5bbd85 Ilias Tsitsimpis
584 4c52d5bf Ilias Tsitsimpis
585 4c52d5bf Ilias Tsitsimpis
# --------------------------------------------------------------------
586 12ef696f Ilias Tsitsimpis
# Initialize Burnin
587 8c67f82e Ilias Tsitsimpis
def initialize(opts, testsuites, stale_testsuites):
588 12ef696f Ilias Tsitsimpis
    """Initalize burnin
589 12ef696f Ilias Tsitsimpis

590 12ef696f Ilias Tsitsimpis
    Initialize our logger and burnin state
591 12ef696f Ilias Tsitsimpis

592 12ef696f Ilias Tsitsimpis
    """
593 12ef696f Ilias Tsitsimpis
    # Initialize logger
594 12ef696f Ilias Tsitsimpis
    global logger  # Using global statement. pylint: disable-msg=C0103,W0603
595 2afd10bf Ilias Tsitsimpis
    curr_time = datetime.datetime.now()
596 12ef696f Ilias Tsitsimpis
    logger = Log(opts.log_folder, verbose=opts.verbose,
597 0c1833c8 Ilias Tsitsimpis
                 use_colors=opts.use_colors, in_parallel=False,
598 ee89df69 Ilias Tsitsimpis
                 log_level=opts.log_level, curr_time=curr_time)
599 12ef696f Ilias Tsitsimpis
600 12ef696f Ilias Tsitsimpis
    # Initialize clients
601 12ef696f Ilias Tsitsimpis
    Clients.auth_url = opts.auth_url
602 12ef696f Ilias Tsitsimpis
    Clients.token = opts.token
603 12ef696f Ilias Tsitsimpis
604 12ef696f Ilias Tsitsimpis
    # Pass the rest options to BurninTests
605 79a5c431 Ilias Tsitsimpis
    BurninTests.use_ipv6 = opts.use_ipv6
606 79a5c431 Ilias Tsitsimpis
    BurninTests.action_timeout = opts.action_timeout
607 79a5c431 Ilias Tsitsimpis
    BurninTests.action_warning = opts.action_warning
608 79a5c431 Ilias Tsitsimpis
    BurninTests.query_interval = opts.query_interval
609 f772699c Ilias Tsitsimpis
    BurninTests.system_user = opts.system_user
610 6c78720b Ilias Tsitsimpis
    BurninTests.flavors = opts.flavors
611 6c78720b Ilias Tsitsimpis
    BurninTests.images = opts.images
612 8c67f82e Ilias Tsitsimpis
    BurninTests.delete_stale = opts.delete_stale
613 24d1788b Ilias Tsitsimpis
    BurninTests.temp_directory = opts.temp_directory
614 2c60bfa6 Ilias Tsitsimpis
    BurninTests.failfast = opts.failfast
615 79a5c431 Ilias Tsitsimpis
    BurninTests.run_id = SNF_TEST_PREFIX + \
616 2afd10bf Ilias Tsitsimpis
        datetime.datetime.strftime(curr_time, "%Y%m%d%H%M%S")
617 12ef696f Ilias Tsitsimpis
618 12ef696f Ilias Tsitsimpis
    # Choose tests to run
619 8c67f82e Ilias Tsitsimpis
    if opts.show_stale:
620 8c67f82e Ilias Tsitsimpis
        # We will run the stale_testsuites
621 3eaf0ec5 Ilias Tsitsimpis
        return (stale_testsuites, True)
622 8c67f82e Ilias Tsitsimpis
623 12ef696f Ilias Tsitsimpis
    if opts.tests != "all":
624 12ef696f Ilias Tsitsimpis
        testsuites = opts.tests
625 12ef696f Ilias Tsitsimpis
    if opts.exclude_tests is not None:
626 12ef696f Ilias Tsitsimpis
        testsuites = [tsuite for tsuite in testsuites
627 12ef696f Ilias Tsitsimpis
                      if tsuite not in opts.exclude_tests]
628 12ef696f Ilias Tsitsimpis
629 3eaf0ec5 Ilias Tsitsimpis
    return (testsuites, opts.failfast)
630 12ef696f Ilias Tsitsimpis
631 12ef696f Ilias Tsitsimpis
632 12ef696f Ilias Tsitsimpis
# --------------------------------------------------------------------
633 12ef696f Ilias Tsitsimpis
# Run Burnin
634 ee89df69 Ilias Tsitsimpis
def run_burnin(testsuites, failfast=False):
635 12ef696f Ilias Tsitsimpis
    """Run burnin testsuites"""
636 08f1780b Ilias Tsitsimpis
    # Using global. pylint: disable-msg=C0103,W0603,W0602
637 08f1780b Ilias Tsitsimpis
    global logger, success
638 12ef696f Ilias Tsitsimpis
639 12ef696f Ilias Tsitsimpis
    success = True
640 08f1780b Ilias Tsitsimpis
    run_tests(testsuites, failfast=failfast)
641 12ef696f Ilias Tsitsimpis
642 12ef696f Ilias Tsitsimpis
    # Clean up our logger
643 eca500f3 Ilias Tsitsimpis
    del logger
644 12ef696f Ilias Tsitsimpis
645 12ef696f Ilias Tsitsimpis
    # Return
646 12ef696f Ilias Tsitsimpis
    return 0 if success else 1
647 12ef696f Ilias Tsitsimpis
648 12ef696f Ilias Tsitsimpis
649 08f1780b Ilias Tsitsimpis
def run_tests(tcases, failfast=False):
650 08f1780b Ilias Tsitsimpis
    """Run some testcases"""
651 08f1780b Ilias Tsitsimpis
    global success  # Using global. pylint: disable-msg=C0103,W0603,W0602
652 08f1780b Ilias Tsitsimpis
653 08f1780b Ilias Tsitsimpis
    for tcase in tcases:
654 08f1780b Ilias Tsitsimpis
        was_success = run_test(tcase)
655 08f1780b Ilias Tsitsimpis
        success = success and was_success
656 08f1780b Ilias Tsitsimpis
        if failfast and not success:
657 08f1780b Ilias Tsitsimpis
            break
658 08f1780b Ilias Tsitsimpis
659 08f1780b Ilias Tsitsimpis
660 6c78720b Ilias Tsitsimpis
def run_test(tcase):
661 6c78720b Ilias Tsitsimpis
    """Run a testcase"""
662 6c78720b Ilias Tsitsimpis
    tsuite = unittest.TestLoader().loadTestsFromTestCase(tcase)
663 6c78720b Ilias Tsitsimpis
    results = tsuite.run(BurninTestResult())
664 6c78720b Ilias Tsitsimpis
665 6c78720b Ilias Tsitsimpis
    return was_successful(tcase.__name__, results.wasSuccessful())
666 6c78720b Ilias Tsitsimpis
667 6c78720b Ilias Tsitsimpis
668 12ef696f Ilias Tsitsimpis
# --------------------------------------------------------------------
669 4c52d5bf Ilias Tsitsimpis
# Helper functions
670 08f1780b Ilias Tsitsimpis
def was_successful(tsuite, successful):
671 4c52d5bf Ilias Tsitsimpis
    """Handle whether a testsuite was succesful or not"""
672 08f1780b Ilias Tsitsimpis
    if successful:
673 4c52d5bf Ilias Tsitsimpis
        logger.testsuite_success(tsuite)
674 12ef696f Ilias Tsitsimpis
        return True
675 4c52d5bf Ilias Tsitsimpis
    else:
676 4c52d5bf Ilias Tsitsimpis
        logger.testsuite_failure(tsuite)
677 12ef696f Ilias Tsitsimpis
        return False
678 f772699c Ilias Tsitsimpis
679 f772699c Ilias Tsitsimpis
680 f772699c Ilias Tsitsimpis
def parse_typed_option(value):
681 f772699c Ilias Tsitsimpis
    """Parse typed options (flavors and images)
682 f772699c Ilias Tsitsimpis

683 f772699c Ilias Tsitsimpis
    The options are in the form 'id:123-345' or 'name:^Debian Base$'
684 f772699c Ilias Tsitsimpis

685 f772699c Ilias Tsitsimpis
    """
686 f772699c Ilias Tsitsimpis
    try:
687 f772699c Ilias Tsitsimpis
        [type_, val] = value.strip().split(':')
688 f772699c Ilias Tsitsimpis
        if type_ not in ["id", "name"]:
689 f772699c Ilias Tsitsimpis
            raise ValueError
690 f772699c Ilias Tsitsimpis
        return type_, val
691 f772699c Ilias Tsitsimpis
    except ValueError:
692 eca500f3 Ilias Tsitsimpis
        raise