Statistics
| Branch: | Tag: | Revision:

root / ci / utils.py @ dae06cfc

History | View | Annotate | Download (23.9 kB)

1 525f2979 Ilias Tsitsimpis
#!/usr/bin/env python
2 525f2979 Ilias Tsitsimpis
3 525f2979 Ilias Tsitsimpis
"""
4 525f2979 Ilias Tsitsimpis
Synnefo ci utils module
5 525f2979 Ilias Tsitsimpis
"""
6 525f2979 Ilias Tsitsimpis
7 525f2979 Ilias Tsitsimpis
import os
8 dae06cfc Ilias Tsitsimpis
import re
9 525f2979 Ilias Tsitsimpis
import sys
10 525f2979 Ilias Tsitsimpis
import time
11 525f2979 Ilias Tsitsimpis
import logging
12 525f2979 Ilias Tsitsimpis
import fabric.api as fabric
13 024faf05 Christos Stavrakakis
import subprocess
14 124c300e Christos Stavrakakis
import tempfile
15 525f2979 Ilias Tsitsimpis
from ConfigParser import ConfigParser, DuplicateSectionError
16 525f2979 Ilias Tsitsimpis
17 da593e0c Christos Stavrakakis
from kamaki.cli import config as kamaki_config
18 525f2979 Ilias Tsitsimpis
from kamaki.clients.astakos import AstakosClient
19 525f2979 Ilias Tsitsimpis
from kamaki.clients.cyclades import CycladesClient
20 525f2979 Ilias Tsitsimpis
from kamaki.clients.image import ImageClient
21 dae06cfc Ilias Tsitsimpis
from kamaki.clients.compute import ComputeClient
22 525f2979 Ilias Tsitsimpis
23 e2db4a57 Christos Stavrakakis
DEFAULT_CONFIG_FILE = "new_config"
24 60ddcdc3 Ilias Tsitsimpis
# UUID of owner of system images
25 60ddcdc3 Ilias Tsitsimpis
DEFAULT_SYSTEM_IMAGES_UUID = [
26 60ddcdc3 Ilias Tsitsimpis
    "25ecced9-bf53-4145-91ee-cf47377e9fb2",  # production (okeanos.grnet.gr)
27 60ddcdc3 Ilias Tsitsimpis
    "04cbe33f-29b7-4ef1-94fb-015929e5fc06",  # testing (okeanos.io)
28 60ddcdc3 Ilias Tsitsimpis
    ]
29 e2db4a57 Christos Stavrakakis
30 525f2979 Ilias Tsitsimpis
31 525f2979 Ilias Tsitsimpis
def _run(cmd, verbose):
32 525f2979 Ilias Tsitsimpis
    """Run fabric with verbose level"""
33 525f2979 Ilias Tsitsimpis
    if verbose:
34 525f2979 Ilias Tsitsimpis
        args = ('running',)
35 525f2979 Ilias Tsitsimpis
    else:
36 525f2979 Ilias Tsitsimpis
        args = ('running', 'stdout',)
37 33ad9a0d Ilias Tsitsimpis
    with fabric.hide(*args):  # Used * or ** magic. pylint: disable-msg=W0142
38 525f2979 Ilias Tsitsimpis
        return fabric.run(cmd)
39 525f2979 Ilias Tsitsimpis
40 525f2979 Ilias Tsitsimpis
41 4c818bb2 Ilias Tsitsimpis
def _put(local, remote):
42 4c818bb2 Ilias Tsitsimpis
    """Run fabric put command without output"""
43 4c818bb2 Ilias Tsitsimpis
    with fabric.quiet():
44 4c818bb2 Ilias Tsitsimpis
        fabric.put(local, remote)
45 4c818bb2 Ilias Tsitsimpis
46 4c818bb2 Ilias Tsitsimpis
47 525f2979 Ilias Tsitsimpis
def _red(msg):
48 525f2979 Ilias Tsitsimpis
    """Red color"""
49 525f2979 Ilias Tsitsimpis
    #return "\x1b[31m" + str(msg) + "\x1b[0m"
50 525f2979 Ilias Tsitsimpis
    return str(msg)
51 525f2979 Ilias Tsitsimpis
52 525f2979 Ilias Tsitsimpis
53 525f2979 Ilias Tsitsimpis
def _yellow(msg):
54 525f2979 Ilias Tsitsimpis
    """Yellow color"""
55 525f2979 Ilias Tsitsimpis
    #return "\x1b[33m" + str(msg) + "\x1b[0m"
56 525f2979 Ilias Tsitsimpis
    return str(msg)
57 525f2979 Ilias Tsitsimpis
58 525f2979 Ilias Tsitsimpis
59 525f2979 Ilias Tsitsimpis
def _green(msg):
60 525f2979 Ilias Tsitsimpis
    """Green color"""
61 525f2979 Ilias Tsitsimpis
    #return "\x1b[32m" + str(msg) + "\x1b[0m"
62 525f2979 Ilias Tsitsimpis
    return str(msg)
63 525f2979 Ilias Tsitsimpis
64 525f2979 Ilias Tsitsimpis
65 525f2979 Ilias Tsitsimpis
def _check_fabric(fun):
66 525f2979 Ilias Tsitsimpis
    """Check if fabric env has been set"""
67 947b6106 Christos Stavrakakis
    def wrapper(self, *args, **kwargs):
68 525f2979 Ilias Tsitsimpis
        """wrapper function"""
69 525f2979 Ilias Tsitsimpis
        if not self.fabric_installed:
70 525f2979 Ilias Tsitsimpis
            self.setup_fabric()
71 947b6106 Christos Stavrakakis
        return fun(self, *args, **kwargs)
72 525f2979 Ilias Tsitsimpis
    return wrapper
73 525f2979 Ilias Tsitsimpis
74 525f2979 Ilias Tsitsimpis
75 525f2979 Ilias Tsitsimpis
def _check_kamaki(fun):
76 525f2979 Ilias Tsitsimpis
    """Check if kamaki has been initialized"""
77 947b6106 Christos Stavrakakis
    def wrapper(self, *args, **kwargs):
78 525f2979 Ilias Tsitsimpis
        """wrapper function"""
79 525f2979 Ilias Tsitsimpis
        if not self.kamaki_installed:
80 525f2979 Ilias Tsitsimpis
            self.setup_kamaki()
81 947b6106 Christos Stavrakakis
        return fun(self, *args, **kwargs)
82 525f2979 Ilias Tsitsimpis
    return wrapper
83 525f2979 Ilias Tsitsimpis
84 525f2979 Ilias Tsitsimpis
85 525f2979 Ilias Tsitsimpis
class _MyFormatter(logging.Formatter):
86 525f2979 Ilias Tsitsimpis
    """Logging Formatter"""
87 525f2979 Ilias Tsitsimpis
    def format(self, record):
88 525f2979 Ilias Tsitsimpis
        format_orig = self._fmt
89 525f2979 Ilias Tsitsimpis
        if record.levelno == logging.DEBUG:
90 525f2979 Ilias Tsitsimpis
            self._fmt = "  %(msg)s"
91 525f2979 Ilias Tsitsimpis
        elif record.levelno == logging.INFO:
92 525f2979 Ilias Tsitsimpis
            self._fmt = "%(msg)s"
93 525f2979 Ilias Tsitsimpis
        elif record.levelno == logging.WARNING:
94 525f2979 Ilias Tsitsimpis
            self._fmt = _yellow("[W] %(msg)s")
95 525f2979 Ilias Tsitsimpis
        elif record.levelno == logging.ERROR:
96 525f2979 Ilias Tsitsimpis
            self._fmt = _red("[E] %(msg)s")
97 525f2979 Ilias Tsitsimpis
        result = logging.Formatter.format(self, record)
98 525f2979 Ilias Tsitsimpis
        self._fmt = format_orig
99 525f2979 Ilias Tsitsimpis
        return result
100 525f2979 Ilias Tsitsimpis
101 525f2979 Ilias Tsitsimpis
102 d8363ea2 Ilias Tsitsimpis
# Too few public methods. pylint: disable-msg=R0903
103 d8363ea2 Ilias Tsitsimpis
class _InfoFilter(logging.Filter):
104 d8363ea2 Ilias Tsitsimpis
    """Logging Filter that allows DEBUG and INFO messages only"""
105 d8363ea2 Ilias Tsitsimpis
    def filter(self, rec):
106 d8363ea2 Ilias Tsitsimpis
        """The filter"""
107 d8363ea2 Ilias Tsitsimpis
        return rec.levelno in (logging.DEBUG, logging.INFO)
108 d8363ea2 Ilias Tsitsimpis
109 d8363ea2 Ilias Tsitsimpis
110 d8363ea2 Ilias Tsitsimpis
# Too many instance attributes. pylint: disable-msg=R0902
111 525f2979 Ilias Tsitsimpis
class SynnefoCI(object):
112 525f2979 Ilias Tsitsimpis
    """SynnefoCI python class"""
113 525f2979 Ilias Tsitsimpis
114 e2db4a57 Christos Stavrakakis
    def __init__(self, config_file=None, cleanup_config=False, cloud=None):
115 525f2979 Ilias Tsitsimpis
        """ Initialize SynnefoCI python class
116 525f2979 Ilias Tsitsimpis

117 525f2979 Ilias Tsitsimpis
        Setup logger, local_dir, config and kamaki
118 525f2979 Ilias Tsitsimpis
        """
119 525f2979 Ilias Tsitsimpis
        # Setup logger
120 525f2979 Ilias Tsitsimpis
        self.logger = logging.getLogger('synnefo-ci')
121 525f2979 Ilias Tsitsimpis
        self.logger.setLevel(logging.DEBUG)
122 d8363ea2 Ilias Tsitsimpis
123 d8363ea2 Ilias Tsitsimpis
        handler1 = logging.StreamHandler(sys.stdout)
124 d8363ea2 Ilias Tsitsimpis
        handler1.setLevel(logging.DEBUG)
125 d8363ea2 Ilias Tsitsimpis
        handler1.addFilter(_InfoFilter())
126 d8363ea2 Ilias Tsitsimpis
        handler1.setFormatter(_MyFormatter())
127 d8363ea2 Ilias Tsitsimpis
        handler2 = logging.StreamHandler(sys.stderr)
128 d8363ea2 Ilias Tsitsimpis
        handler2.setLevel(logging.WARNING)
129 d8363ea2 Ilias Tsitsimpis
        handler2.setFormatter(_MyFormatter())
130 d8363ea2 Ilias Tsitsimpis
131 d8363ea2 Ilias Tsitsimpis
        self.logger.addHandler(handler1)
132 d8363ea2 Ilias Tsitsimpis
        self.logger.addHandler(handler2)
133 525f2979 Ilias Tsitsimpis
134 525f2979 Ilias Tsitsimpis
        # Get our local dir
135 525f2979 Ilias Tsitsimpis
        self.ci_dir = os.path.dirname(os.path.abspath(__file__))
136 525f2979 Ilias Tsitsimpis
        self.repo_dir = os.path.dirname(self.ci_dir)
137 525f2979 Ilias Tsitsimpis
138 525f2979 Ilias Tsitsimpis
        # Read config file
139 e2db4a57 Christos Stavrakakis
        if config_file is None:
140 e2db4a57 Christos Stavrakakis
            config_file = DEFAULT_CONFIG_FILE
141 e2db4a57 Christos Stavrakakis
        if not os.path.isabs(config_file):
142 e2db4a57 Christos Stavrakakis
            config_file = os.path.join(self.ci_dir, config_file)
143 133e5a5b Christos Stavrakakis
144 525f2979 Ilias Tsitsimpis
        self.config = ConfigParser()
145 525f2979 Ilias Tsitsimpis
        self.config.optionxform = str
146 e2db4a57 Christos Stavrakakis
        self.config.read(config_file)
147 525f2979 Ilias Tsitsimpis
        temp_config = self.config.get('Global', 'temporary_config')
148 525f2979 Ilias Tsitsimpis
        if cleanup_config:
149 525f2979 Ilias Tsitsimpis
            try:
150 525f2979 Ilias Tsitsimpis
                os.remove(temp_config)
151 33ad9a0d Ilias Tsitsimpis
            except OSError:
152 525f2979 Ilias Tsitsimpis
                pass
153 525f2979 Ilias Tsitsimpis
        else:
154 525f2979 Ilias Tsitsimpis
            self.config.read(self.config.get('Global', 'temporary_config'))
155 525f2979 Ilias Tsitsimpis
156 da593e0c Christos Stavrakakis
        # Set kamaki cloud
157 da593e0c Christos Stavrakakis
        if cloud is not None:
158 da593e0c Christos Stavrakakis
            self.kamaki_cloud = cloud
159 da593e0c Christos Stavrakakis
        elif self.config.has_option("Deployment", "kamaki_cloud"):
160 da593e0c Christos Stavrakakis
            kamaki_cloud = self.config.get("Deployment", "kamaki_cloud")
161 da593e0c Christos Stavrakakis
            if kamaki_cloud == "":
162 da593e0c Christos Stavrakakis
                self.kamaki_cloud = None
163 da593e0c Christos Stavrakakis
        else:
164 da593e0c Christos Stavrakakis
            self.kamaki_cloud = None
165 da593e0c Christos Stavrakakis
166 525f2979 Ilias Tsitsimpis
        # Initialize variables
167 525f2979 Ilias Tsitsimpis
        self.fabric_installed = False
168 525f2979 Ilias Tsitsimpis
        self.kamaki_installed = False
169 525f2979 Ilias Tsitsimpis
        self.cyclades_client = None
170 dae06cfc Ilias Tsitsimpis
        self.compute_client = None
171 525f2979 Ilias Tsitsimpis
        self.image_client = None
172 525f2979 Ilias Tsitsimpis
173 525f2979 Ilias Tsitsimpis
    def setup_kamaki(self):
174 525f2979 Ilias Tsitsimpis
        """Initialize kamaki
175 525f2979 Ilias Tsitsimpis

176 dae06cfc Ilias Tsitsimpis
        Setup cyclades_client, image_client and compute_client
177 525f2979 Ilias Tsitsimpis
        """
178 da593e0c Christos Stavrakakis
179 da593e0c Christos Stavrakakis
        config = kamaki_config.Config()
180 da593e0c Christos Stavrakakis
        if self.kamaki_cloud is None:
181 da593e0c Christos Stavrakakis
            self.kamaki_cloud = config.get_global("default_cloud")
182 da593e0c Christos Stavrakakis
183 da593e0c Christos Stavrakakis
        self.logger.info("Setup kamaki client, using cloud '%s'.." %
184 da593e0c Christos Stavrakakis
                         self.kamaki_cloud)
185 da593e0c Christos Stavrakakis
        auth_url = config.get_cloud(self.kamaki_cloud, "url")
186 525f2979 Ilias Tsitsimpis
        self.logger.debug("Authentication URL is %s" % _green(auth_url))
187 da593e0c Christos Stavrakakis
        token = config.get_cloud(self.kamaki_cloud, "token")
188 525f2979 Ilias Tsitsimpis
        #self.logger.debug("Token is %s" % _green(token))
189 525f2979 Ilias Tsitsimpis
190 525f2979 Ilias Tsitsimpis
        astakos_client = AstakosClient(auth_url, token)
191 525f2979 Ilias Tsitsimpis
192 525f2979 Ilias Tsitsimpis
        cyclades_url = \
193 525f2979 Ilias Tsitsimpis
            astakos_client.get_service_endpoints('compute')['publicURL']
194 525f2979 Ilias Tsitsimpis
        self.logger.debug("Cyclades API url is %s" % _green(cyclades_url))
195 525f2979 Ilias Tsitsimpis
        self.cyclades_client = CycladesClient(cyclades_url, token)
196 525f2979 Ilias Tsitsimpis
        self.cyclades_client.CONNECTION_RETRY_LIMIT = 2
197 525f2979 Ilias Tsitsimpis
198 525f2979 Ilias Tsitsimpis
        image_url = \
199 525f2979 Ilias Tsitsimpis
            astakos_client.get_service_endpoints('image')['publicURL']
200 525f2979 Ilias Tsitsimpis
        self.logger.debug("Images API url is %s" % _green(image_url))
201 525f2979 Ilias Tsitsimpis
        self.image_client = ImageClient(cyclades_url, token)
202 525f2979 Ilias Tsitsimpis
        self.image_client.CONNECTION_RETRY_LIMIT = 2
203 525f2979 Ilias Tsitsimpis
204 dae06cfc Ilias Tsitsimpis
        compute_url = \
205 dae06cfc Ilias Tsitsimpis
            astakos_client.get_service_endpoints('compute')['publicURL']
206 dae06cfc Ilias Tsitsimpis
        self.logger.debug("Compute API url is %s" % _green(compute_url))
207 dae06cfc Ilias Tsitsimpis
        self.compute_client = ComputeClient(compute_url, token)
208 dae06cfc Ilias Tsitsimpis
        self.compute_client.CONNECTION_RETRY_LIMIT = 2
209 dae06cfc Ilias Tsitsimpis
210 525f2979 Ilias Tsitsimpis
    def _wait_transition(self, server_id, current_status, new_status):
211 525f2979 Ilias Tsitsimpis
        """Wait for server to go from current_status to new_status"""
212 525f2979 Ilias Tsitsimpis
        self.logger.debug("Waiting for server to become %s" % new_status)
213 525f2979 Ilias Tsitsimpis
        timeout = self.config.getint('Global', 'build_timeout')
214 525f2979 Ilias Tsitsimpis
        sleep_time = 5
215 525f2979 Ilias Tsitsimpis
        while True:
216 525f2979 Ilias Tsitsimpis
            server = self.cyclades_client.get_server_details(server_id)
217 525f2979 Ilias Tsitsimpis
            if server['status'] == new_status:
218 525f2979 Ilias Tsitsimpis
                return server
219 525f2979 Ilias Tsitsimpis
            elif timeout < 0:
220 525f2979 Ilias Tsitsimpis
                self.logger.error(
221 525f2979 Ilias Tsitsimpis
                    "Waiting for server to become %s timed out" % new_status)
222 525f2979 Ilias Tsitsimpis
                self.destroy_server(False)
223 525f2979 Ilias Tsitsimpis
                sys.exit(-1)
224 525f2979 Ilias Tsitsimpis
            elif server['status'] == current_status:
225 525f2979 Ilias Tsitsimpis
                # Sleep for #n secs and continue
226 525f2979 Ilias Tsitsimpis
                timeout = timeout - sleep_time
227 525f2979 Ilias Tsitsimpis
                time.sleep(sleep_time)
228 525f2979 Ilias Tsitsimpis
            else:
229 525f2979 Ilias Tsitsimpis
                self.logger.error(
230 525f2979 Ilias Tsitsimpis
                    "Server failed with status %s" % server['status'])
231 525f2979 Ilias Tsitsimpis
                self.destroy_server(False)
232 525f2979 Ilias Tsitsimpis
                sys.exit(-1)
233 525f2979 Ilias Tsitsimpis
234 525f2979 Ilias Tsitsimpis
    @_check_kamaki
235 525f2979 Ilias Tsitsimpis
    def destroy_server(self, wait=True):
236 525f2979 Ilias Tsitsimpis
        """Destroy slave server"""
237 525f2979 Ilias Tsitsimpis
        server_id = self.config.getint('Temporary Options', 'server_id')
238 525f2979 Ilias Tsitsimpis
        self.logger.info("Destoying server with id %s " % server_id)
239 525f2979 Ilias Tsitsimpis
        self.cyclades_client.delete_server(server_id)
240 525f2979 Ilias Tsitsimpis
        if wait:
241 525f2979 Ilias Tsitsimpis
            self._wait_transition(server_id, "ACTIVE", "DELETED")
242 525f2979 Ilias Tsitsimpis
243 525f2979 Ilias Tsitsimpis
    @_check_kamaki
244 dae06cfc Ilias Tsitsimpis
    def create_server(self, image_id=None, flavor_name=None, ssh_keys=None):
245 525f2979 Ilias Tsitsimpis
        """Create slave server"""
246 525f2979 Ilias Tsitsimpis
        self.logger.info("Create a new server..")
247 947b6106 Christos Stavrakakis
        if image_id is None:
248 947b6106 Christos Stavrakakis
            image = self._find_image()
249 947b6106 Christos Stavrakakis
            self.logger.debug("Will use image \"%s\"" % _green(image['name']))
250 947b6106 Christos Stavrakakis
            image_id = image["id"]
251 947b6106 Christos Stavrakakis
        self.logger.debug("Image has id %s" % _green(image_id))
252 dae06cfc Ilias Tsitsimpis
        flavor_id = self._find_flavor(flavor_name)
253 525f2979 Ilias Tsitsimpis
        server = self.cyclades_client.create_server(
254 525f2979 Ilias Tsitsimpis
            self.config.get('Deployment', 'server_name'),
255 947b6106 Christos Stavrakakis
            flavor_id,
256 947b6106 Christos Stavrakakis
            image_id)
257 525f2979 Ilias Tsitsimpis
        server_id = server['id']
258 525f2979 Ilias Tsitsimpis
        self.write_config('server_id', server_id)
259 525f2979 Ilias Tsitsimpis
        self.logger.debug("Server got id %s" % _green(server_id))
260 525f2979 Ilias Tsitsimpis
        server_user = server['metadata']['users']
261 525f2979 Ilias Tsitsimpis
        self.write_config('server_user', server_user)
262 525f2979 Ilias Tsitsimpis
        self.logger.debug("Server's admin user is %s" % _green(server_user))
263 525f2979 Ilias Tsitsimpis
        server_passwd = server['adminPass']
264 525f2979 Ilias Tsitsimpis
        self.write_config('server_passwd', server_passwd)
265 525f2979 Ilias Tsitsimpis
266 525f2979 Ilias Tsitsimpis
        server = self._wait_transition(server_id, "BUILD", "ACTIVE")
267 525f2979 Ilias Tsitsimpis
        self._get_server_ip_and_port(server)
268 4c818bb2 Ilias Tsitsimpis
        self._copy_ssh_keys(ssh_keys)
269 525f2979 Ilias Tsitsimpis
270 525f2979 Ilias Tsitsimpis
        self.setup_fabric()
271 525f2979 Ilias Tsitsimpis
        self.logger.info("Setup firewall")
272 4c818bb2 Ilias Tsitsimpis
        accept_ssh_from = self.config.get('Global', 'accept_ssh_from')
273 0082c787 Christos Stavrakakis
        if accept_ssh_from != "":
274 0082c787 Christos Stavrakakis
            self.logger.debug("Block ssh except from %s" % accept_ssh_from)
275 0082c787 Christos Stavrakakis
            cmd = """
276 0082c787 Christos Stavrakakis
            local_ip=$(/sbin/ifconfig eth0 | grep 'inet addr:' | \
277 0082c787 Christos Stavrakakis
                cut -d':' -f2 | cut -d' ' -f1)
278 0082c787 Christos Stavrakakis
            iptables -A INPUT -s localhost -j ACCEPT
279 0082c787 Christos Stavrakakis
            iptables -A INPUT -s $local_ip -j ACCEPT
280 0082c787 Christos Stavrakakis
            iptables -A INPUT -s {0} -p tcp --dport 22 -j ACCEPT
281 0082c787 Christos Stavrakakis
            iptables -A INPUT -p tcp --dport 22 -j DROP
282 0082c787 Christos Stavrakakis
            """.format(accept_ssh_from)
283 0082c787 Christos Stavrakakis
            _run(cmd, False)
284 525f2979 Ilias Tsitsimpis
285 dae06cfc Ilias Tsitsimpis
    def _find_flavor(self, flavor_name):
286 dae06cfc Ilias Tsitsimpis
        """Given a flavor_name (reg expression) find a flavor id to use"""
287 dae06cfc Ilias Tsitsimpis
        if flavor_name is None:
288 dae06cfc Ilias Tsitsimpis
            flavor_name = self.config.get('Deployment', 'flavor_name')
289 dae06cfc Ilias Tsitsimpis
        self.logger.debug("Try to find a flavor with name \"%s\"" % flavor_name)
290 dae06cfc Ilias Tsitsimpis
291 dae06cfc Ilias Tsitsimpis
        flavors = self.compute_client.list_flavors()
292 dae06cfc Ilias Tsitsimpis
        flavors = [f for f in flavors
293 dae06cfc Ilias Tsitsimpis
                   if re.search(flavor_name, f['name']) is not None]
294 dae06cfc Ilias Tsitsimpis
295 dae06cfc Ilias Tsitsimpis
        if flavors:
296 dae06cfc Ilias Tsitsimpis
            self.logger.debug("Will use %s with id %s"
297 dae06cfc Ilias Tsitsimpis
                              % (flavors[0]['name'], flavors[0]['id']))
298 dae06cfc Ilias Tsitsimpis
            return flavors[0]['id']
299 dae06cfc Ilias Tsitsimpis
        else:
300 dae06cfc Ilias Tsitsimpis
            self.logger.error("No matching flavor found.. aborting")
301 dae06cfc Ilias Tsitsimpis
            sys.exit(1)
302 dae06cfc Ilias Tsitsimpis
303 525f2979 Ilias Tsitsimpis
    def _find_image(self):
304 525f2979 Ilias Tsitsimpis
        """Find a suitable image to use
305 525f2979 Ilias Tsitsimpis

306 60ddcdc3 Ilias Tsitsimpis
        It has to belong to one of the `DEFAULT_SYSTEM_IMAGES_UUID'
307 60ddcdc3 Ilias Tsitsimpis
        users and contain the word given by `image_name' option.
308 525f2979 Ilias Tsitsimpis
        """
309 525f2979 Ilias Tsitsimpis
        image_name = self.config.get('Deployment', 'image_name').lower()
310 525f2979 Ilias Tsitsimpis
        images = self.image_client.list_public(detail=True)['images']
311 525f2979 Ilias Tsitsimpis
        # Select images by `system_uuid' user
312 60ddcdc3 Ilias Tsitsimpis
        images = [x for x in images
313 60ddcdc3 Ilias Tsitsimpis
                  if x['user_id'] in DEFAULT_SYSTEM_IMAGES_UUID]
314 525f2979 Ilias Tsitsimpis
        # Select images with `image_name' in their names
315 60ddcdc3 Ilias Tsitsimpis
        images = [x for x in images
316 60ddcdc3 Ilias Tsitsimpis
                  if x['name'].lower().find(image_name) != -1]
317 525f2979 Ilias Tsitsimpis
        # Let's select the first one
318 525f2979 Ilias Tsitsimpis
        return images[0]
319 525f2979 Ilias Tsitsimpis
320 525f2979 Ilias Tsitsimpis
    def _get_server_ip_and_port(self, server):
321 525f2979 Ilias Tsitsimpis
        """Compute server's IPv4 and ssh port number"""
322 525f2979 Ilias Tsitsimpis
        self.logger.info("Get server connection details..")
323 525f2979 Ilias Tsitsimpis
        server_ip = server['attachments'][0]['ipv4']
324 ddd240ff Christos Stavrakakis
        if ".okeanos.io" in self.cyclades_client.base_url:
325 525f2979 Ilias Tsitsimpis
            tmp1 = int(server_ip.split(".")[2])
326 525f2979 Ilias Tsitsimpis
            tmp2 = int(server_ip.split(".")[3])
327 525f2979 Ilias Tsitsimpis
            server_ip = "gate.okeanos.io"
328 525f2979 Ilias Tsitsimpis
            server_port = 10000 + tmp1 * 256 + tmp2
329 525f2979 Ilias Tsitsimpis
        else:
330 525f2979 Ilias Tsitsimpis
            server_port = 22
331 525f2979 Ilias Tsitsimpis
        self.write_config('server_ip', server_ip)
332 525f2979 Ilias Tsitsimpis
        self.logger.debug("Server's IPv4 is %s" % _green(server_ip))
333 525f2979 Ilias Tsitsimpis
        self.write_config('server_port', server_port)
334 525f2979 Ilias Tsitsimpis
        self.logger.debug("Server's ssh port is %s" % _green(server_port))
335 4c818bb2 Ilias Tsitsimpis
        self.logger.debug("Access server using \"ssh -p %s %s@%s\"" %
336 2fab294e Ilias Tsitsimpis
                          (server_port, server['metadata']['users'], server_ip))
337 525f2979 Ilias Tsitsimpis
338 5c3b5c9f Christos Stavrakakis
    @_check_fabric
339 4c818bb2 Ilias Tsitsimpis
    def _copy_ssh_keys(self, ssh_keys):
340 33ad9a0d Ilias Tsitsimpis
        """Upload/Install ssh keys to server"""
341 2fab294e Ilias Tsitsimpis
        self.logger.debug("Check for authentication keys to use")
342 4c818bb2 Ilias Tsitsimpis
        if ssh_keys is None:
343 4c818bb2 Ilias Tsitsimpis
            ssh_keys = self.config.get("Deployment", "ssh_keys")
344 4c818bb2 Ilias Tsitsimpis
345 2fab294e Ilias Tsitsimpis
        if ssh_keys != "":
346 2fab294e Ilias Tsitsimpis
            self.logger.debug("Will use %s authentication keys file" % ssh_keys)
347 5c3b5c9f Christos Stavrakakis
            keyfile = '/tmp/%s.pub' % fabric.env.user
348 5c3b5c9f Christos Stavrakakis
            _run('mkdir -p ~/.ssh && chmod 700 ~/.ssh', False)
349 2fab294e Ilias Tsitsimpis
            if ssh_keys.startswith("http://") or \
350 2fab294e Ilias Tsitsimpis
                    ssh_keys.startswith("https://") or \
351 2fab294e Ilias Tsitsimpis
                    ssh_keys.startswith("ftp://"):
352 2fab294e Ilias Tsitsimpis
                cmd = """
353 2fab294e Ilias Tsitsimpis
                apt-get update
354 2fab294e Ilias Tsitsimpis
                apt-get install wget --yes
355 2fab294e Ilias Tsitsimpis
                wget {0} -O {1} --no-check-certificate
356 2fab294e Ilias Tsitsimpis
                """.format(ssh_keys, keyfile)
357 2fab294e Ilias Tsitsimpis
                _run(cmd, False)
358 2fab294e Ilias Tsitsimpis
            elif os.path.exists(ssh_keys):
359 2fab294e Ilias Tsitsimpis
                _put(ssh_keys, keyfile)
360 2fab294e Ilias Tsitsimpis
            else:
361 2fab294e Ilias Tsitsimpis
                self.logger.debug("No ssh keys found")
362 5c3b5c9f Christos Stavrakakis
            _run('cat %s >> ~/.ssh/authorized_keys' % keyfile, False)
363 5c3b5c9f Christos Stavrakakis
            _run('rm %s' % keyfile, False)
364 5c3b5c9f Christos Stavrakakis
            self.logger.debug("Uploaded ssh authorized keys")
365 5c3b5c9f Christos Stavrakakis
        else:
366 5c3b5c9f Christos Stavrakakis
            self.logger.debug("No ssh keys found")
367 5c3b5c9f Christos Stavrakakis
368 525f2979 Ilias Tsitsimpis
    def write_config(self, option, value, section="Temporary Options"):
369 525f2979 Ilias Tsitsimpis
        """Write changes back to config file"""
370 525f2979 Ilias Tsitsimpis
        try:
371 525f2979 Ilias Tsitsimpis
            self.config.add_section(section)
372 525f2979 Ilias Tsitsimpis
        except DuplicateSectionError:
373 525f2979 Ilias Tsitsimpis
            pass
374 525f2979 Ilias Tsitsimpis
        self.config.set(section, option, str(value))
375 525f2979 Ilias Tsitsimpis
        temp_conf_file = self.config.get('Global', 'temporary_config')
376 525f2979 Ilias Tsitsimpis
        with open(temp_conf_file, 'wb') as tcf:
377 525f2979 Ilias Tsitsimpis
            self.config.write(tcf)
378 525f2979 Ilias Tsitsimpis
379 525f2979 Ilias Tsitsimpis
    def setup_fabric(self):
380 525f2979 Ilias Tsitsimpis
        """Setup fabric environment"""
381 525f2979 Ilias Tsitsimpis
        self.logger.info("Setup fabric parameters..")
382 525f2979 Ilias Tsitsimpis
        fabric.env.user = self.config.get('Temporary Options', 'server_user')
383 525f2979 Ilias Tsitsimpis
        fabric.env.host_string = \
384 525f2979 Ilias Tsitsimpis
            self.config.get('Temporary Options', 'server_ip')
385 133e5a5b Christos Stavrakakis
        fabric.env.port = self.config.getint('Temporary Options',
386 133e5a5b Christos Stavrakakis
                                             'server_port')
387 133e5a5b Christos Stavrakakis
        fabric.env.password = self.config.get('Temporary Options',
388 133e5a5b Christos Stavrakakis
                                              'server_passwd')
389 525f2979 Ilias Tsitsimpis
        fabric.env.connection_attempts = 10
390 525f2979 Ilias Tsitsimpis
        fabric.env.shell = "/bin/bash -c"
391 525f2979 Ilias Tsitsimpis
        fabric.env.disable_known_hosts = True
392 525f2979 Ilias Tsitsimpis
        fabric.env.output_prefix = None
393 525f2979 Ilias Tsitsimpis
394 525f2979 Ilias Tsitsimpis
    def _check_hash_sum(self, localfile, remotefile):
395 525f2979 Ilias Tsitsimpis
        """Check hash sums of two files"""
396 525f2979 Ilias Tsitsimpis
        self.logger.debug("Check hash sum for local file %s" % localfile)
397 525f2979 Ilias Tsitsimpis
        hash1 = os.popen("sha256sum %s" % localfile).read().split(' ')[0]
398 525f2979 Ilias Tsitsimpis
        self.logger.debug("Local file has sha256 hash %s" % hash1)
399 525f2979 Ilias Tsitsimpis
        self.logger.debug("Check hash sum for remote file %s" % remotefile)
400 525f2979 Ilias Tsitsimpis
        hash2 = _run("sha256sum %s" % remotefile, False)
401 525f2979 Ilias Tsitsimpis
        hash2 = hash2.split(' ')[0]
402 525f2979 Ilias Tsitsimpis
        self.logger.debug("Remote file has sha256 hash %s" % hash2)
403 525f2979 Ilias Tsitsimpis
        if hash1 != hash2:
404 525f2979 Ilias Tsitsimpis
            self.logger.error("Hashes differ.. aborting")
405 525f2979 Ilias Tsitsimpis
            sys.exit(-1)
406 525f2979 Ilias Tsitsimpis
407 525f2979 Ilias Tsitsimpis
    @_check_fabric
408 525f2979 Ilias Tsitsimpis
    def clone_repo(self):
409 525f2979 Ilias Tsitsimpis
        """Clone Synnefo repo from slave server"""
410 525f2979 Ilias Tsitsimpis
        self.logger.info("Configure repositories on remote server..")
411 525f2979 Ilias Tsitsimpis
        self.logger.debug("Setup apt, install curl and git")
412 525f2979 Ilias Tsitsimpis
        cmd = """
413 525f2979 Ilias Tsitsimpis
        echo 'APT::Install-Suggests "false";' >> /etc/apt/apt.conf
414 525f2979 Ilias Tsitsimpis
        apt-get update
415 525f2979 Ilias Tsitsimpis
        apt-get install curl git --yes
416 525f2979 Ilias Tsitsimpis
        echo -e "\n\ndeb {0}" >> /etc/apt/sources.list
417 525f2979 Ilias Tsitsimpis
        curl https://dev.grnet.gr/files/apt-grnetdev.pub | apt-key add -
418 525f2979 Ilias Tsitsimpis
        apt-get update
419 525f2979 Ilias Tsitsimpis
        git config --global user.name {1}
420 b642f737 Christos Stavrakakis
        git config --global user.email {2}
421 525f2979 Ilias Tsitsimpis
        """.format(self.config.get('Global', 'apt_repo'),
422 525f2979 Ilias Tsitsimpis
                   self.config.get('Global', 'git_config_name'),
423 525f2979 Ilias Tsitsimpis
                   self.config.get('Global', 'git_config_mail'))
424 525f2979 Ilias Tsitsimpis
        _run(cmd, False)
425 525f2979 Ilias Tsitsimpis
426 525f2979 Ilias Tsitsimpis
        synnefo_repo = self.config.get('Global', 'synnefo_repo')
427 024faf05 Christos Stavrakakis
        synnefo_branch = self.config.get("Global", "synnefo_branch")
428 024faf05 Christos Stavrakakis
        if synnefo_branch == "":
429 33ad9a0d Ilias Tsitsimpis
            synnefo_branch = \
430 33ad9a0d Ilias Tsitsimpis
                subprocess.Popen(
431 33ad9a0d Ilias Tsitsimpis
                    ["git", "rev-parse", "--abbrev-ref", "HEAD"],
432 024faf05 Christos Stavrakakis
                    stdout=subprocess.PIPE).communicate()[0].strip()
433 024faf05 Christos Stavrakakis
            if synnefo_branch == "HEAD":
434 024faf05 Christos Stavrakakis
                synnefo_branch = \
435 33ad9a0d Ilias Tsitsimpis
                    subprocess.Popen(
436 33ad9a0d Ilias Tsitsimpis
                        ["git", "rev-parse", "--short", "HEAD"],
437 024faf05 Christos Stavrakakis
                        stdout=subprocess.PIPE).communicate()[0].strip()
438 024faf05 Christos Stavrakakis
        self.logger.info("Will use branch %s" % synnefo_branch)
439 525f2979 Ilias Tsitsimpis
        # Currently clonning synnefo can fail unexpectedly
440 133e5a5b Christos Stavrakakis
        cloned = False
441 024faf05 Christos Stavrakakis
        for i in range(10):
442 525f2979 Ilias Tsitsimpis
            self.logger.debug("Clone synnefo from %s" % synnefo_repo)
443 525f2979 Ilias Tsitsimpis
            try:
444 024faf05 Christos Stavrakakis
                _run("git clone %s synnefo" % synnefo_repo, False)
445 133e5a5b Christos Stavrakakis
                cloned = True
446 525f2979 Ilias Tsitsimpis
                break
447 33ad9a0d Ilias Tsitsimpis
            except BaseException:
448 133e5a5b Christos Stavrakakis
                self.logger.warning("Clonning synnefo failed.. retrying %s"
449 133e5a5b Christos Stavrakakis
                                    % i)
450 33ad9a0d Ilias Tsitsimpis
        cmd = """
451 024faf05 Christos Stavrakakis
        cd synnefo
452 33ad9a0d Ilias Tsitsimpis
        for branch in `git branch -a | grep remotes | \
453 33ad9a0d Ilias Tsitsimpis
                       grep -v HEAD | grep -v master`; do
454 024faf05 Christos Stavrakakis
            git branch --track ${branch##*/} $branch
455 024faf05 Christos Stavrakakis
        done
456 024faf05 Christos Stavrakakis
        git checkout %s
457 024faf05 Christos Stavrakakis
        """ % (synnefo_branch)
458 024faf05 Christos Stavrakakis
        _run(cmd, False)
459 024faf05 Christos Stavrakakis
460 133e5a5b Christos Stavrakakis
        if not cloned:
461 133e5a5b Christos Stavrakakis
            self.logger.error("Can not clone Synnefo repo.")
462 133e5a5b Christos Stavrakakis
            sys.exit(-1)
463 525f2979 Ilias Tsitsimpis
464 525f2979 Ilias Tsitsimpis
        deploy_repo = self.config.get('Global', 'deploy_repo')
465 525f2979 Ilias Tsitsimpis
        self.logger.debug("Clone snf-deploy from %s" % deploy_repo)
466 133e5a5b Christos Stavrakakis
        _run("git clone --depth 1 %s" % deploy_repo, False)
467 525f2979 Ilias Tsitsimpis
468 525f2979 Ilias Tsitsimpis
    @_check_fabric
469 525f2979 Ilias Tsitsimpis
    def build_synnefo(self):
470 525f2979 Ilias Tsitsimpis
        """Build Synnefo packages"""
471 525f2979 Ilias Tsitsimpis
        self.logger.info("Build Synnefo packages..")
472 525f2979 Ilias Tsitsimpis
        self.logger.debug("Install development packages")
473 525f2979 Ilias Tsitsimpis
        cmd = """
474 525f2979 Ilias Tsitsimpis
        apt-get update
475 525f2979 Ilias Tsitsimpis
        apt-get install zlib1g-dev dpkg-dev debhelper git-buildpackage \
476 525f2979 Ilias Tsitsimpis
                python-dev python-all python-pip --yes
477 525f2979 Ilias Tsitsimpis
        pip install devflow
478 525f2979 Ilias Tsitsimpis
        """
479 525f2979 Ilias Tsitsimpis
        _run(cmd, False)
480 525f2979 Ilias Tsitsimpis
481 133e5a5b Christos Stavrakakis
        if self.config.get('Global', 'patch_pydist') == "True":
482 525f2979 Ilias Tsitsimpis
            self.logger.debug("Patch pydist.py module")
483 525f2979 Ilias Tsitsimpis
            cmd = r"""
484 525f2979 Ilias Tsitsimpis
            sed -r -i 's/(\(\?P<name>\[A-Za-z\]\[A-Za-z0-9_\.)/\1\\\-/' \
485 525f2979 Ilias Tsitsimpis
                /usr/share/python/debpython/pydist.py
486 525f2979 Ilias Tsitsimpis
            """
487 525f2979 Ilias Tsitsimpis
            _run(cmd, False)
488 525f2979 Ilias Tsitsimpis

489 525f2979 Ilias Tsitsimpis
        self.logger.debug("Build snf-deploy package")
490 525f2979 Ilias Tsitsimpis
        cmd = """
491 525f2979 Ilias Tsitsimpis
        git checkout -t origin/debian
492 525f2979 Ilias Tsitsimpis
        git-buildpackage --git-upstream-branch=master \
493 525f2979 Ilias Tsitsimpis
                --git-debian-branch=debian \
494 525f2979 Ilias Tsitsimpis
                --git-export-dir=../snf-deploy_build-area \
495 525f2979 Ilias Tsitsimpis
                -uc -us
496 525f2979 Ilias Tsitsimpis
        """
497 525f2979 Ilias Tsitsimpis
        with fabric.cd("snf-deploy"):
498 525f2979 Ilias Tsitsimpis
            _run(cmd, True)
499 525f2979 Ilias Tsitsimpis

500 525f2979 Ilias Tsitsimpis
        self.logger.debug("Install snf-deploy package")
501 525f2979 Ilias Tsitsimpis
        cmd = """
502 525f2979 Ilias Tsitsimpis
        dpkg -i snf-deploy*.deb
503 525f2979 Ilias Tsitsimpis
        apt-get -f install --yes
504 525f2979 Ilias Tsitsimpis
        """
505 525f2979 Ilias Tsitsimpis
        with fabric.cd("snf-deploy_build-area"):
506 525f2979 Ilias Tsitsimpis
            with fabric.settings(warn_only=True):
507 525f2979 Ilias Tsitsimpis
                _run(cmd, True)
508 525f2979 Ilias Tsitsimpis

509 525f2979 Ilias Tsitsimpis
        self.logger.debug("Build synnefo packages")
510 525f2979 Ilias Tsitsimpis
        cmd = """
511 525f2979 Ilias Tsitsimpis
        devflow-autopkg snapshot -b ~/synnefo_build-area --no-sign
512 525f2979 Ilias Tsitsimpis
        """
513 525f2979 Ilias Tsitsimpis
        with fabric.cd("synnefo"):
514 525f2979 Ilias Tsitsimpis
            _run(cmd, True)
515 525f2979 Ilias Tsitsimpis

516 525f2979 Ilias Tsitsimpis
        self.logger.debug("Copy synnefo debs to snf-deploy packages dir")
517 525f2979 Ilias Tsitsimpis
        cmd = """
518 525f2979 Ilias Tsitsimpis
        cp ~/synnefo_build-area/*.deb /var/lib/snf-deploy/packages/
519 525f2979 Ilias Tsitsimpis
        """
520 525f2979 Ilias Tsitsimpis
        _run(cmd, False)
521 525f2979 Ilias Tsitsimpis

522 124c300e Christos Stavrakakis
    @_check_fabric
523 124c300e Christos Stavrakakis
    def build_documentation(self):
524 33ad9a0d Ilias Tsitsimpis
        """Build Synnefo documentation"""
525 124c300e Christos Stavrakakis
        self.logger.info("Build Synnefo documentation..")
526 124c300e Christos Stavrakakis
        _run("pip install -U Sphinx", False)
527 124c300e Christos Stavrakakis
        with fabric.cd("synnefo"):
528 33ad9a0d Ilias Tsitsimpis
            _run("devflow-update-version; "
529 33ad9a0d Ilias Tsitsimpis
                 "./ci/make_docs.sh synnefo_documentation", False)
530 124c300e Christos Stavrakakis

531 124c300e Christos Stavrakakis
    def fetch_documentation(self, dest=None):
532 33ad9a0d Ilias Tsitsimpis
        """Fetch Synnefo documentation"""
533 33ad9a0d Ilias Tsitsimpis
        self.logger.info("Fetch Synnefo documentation..")
534 124c300e Christos Stavrakakis
        if dest is None:
535 124c300e Christos Stavrakakis
            dest = "synnefo_documentation"
536 124c300e Christos Stavrakakis
        dest = os.path.abspath(dest)
537 124c300e Christos Stavrakakis
        if not os.path.exists(dest):
538 124c300e Christos Stavrakakis
            os.makedirs(dest)
539 124c300e Christos Stavrakakis
        self.fetch_compressed("synnefo/synnefo_documentation", dest)
540 124c300e Christos Stavrakakis
        self.logger.info("Downloaded documentation to %s" %
541 124c300e Christos Stavrakakis
                         _green(dest))
542 124c300e Christos Stavrakakis

543 525f2979 Ilias Tsitsimpis
    @_check_fabric
544 46a07468 Christos Stavrakakis
    def deploy_synnefo(self, schema=None):
545 525f2979 Ilias Tsitsimpis
        """Deploy Synnefo using snf-deploy"""
546 525f2979 Ilias Tsitsimpis
        self.logger.info("Deploy Synnefo..")
547 46a07468 Christos Stavrakakis
        if schema is None:
548 46a07468 Christos Stavrakakis
            schema = self.config.get('Global', 'schema')
549 525f2979 Ilias Tsitsimpis
        self.logger.debug("Will use %s schema" % schema)
550 525f2979 Ilias Tsitsimpis

551 46a07468 Christos Stavrakakis
        schema_dir = os.path.join(self.ci_dir, "schemas/%s" % schema)
552 46a07468 Christos Stavrakakis
        if not (os.path.exists(schema_dir) and os.path.isdir(schema_dir)):
553 46a07468 Christos Stavrakakis
            raise ValueError("Unknown schema: %s" % schema)
554 46a07468 Christos Stavrakakis

555 525f2979 Ilias Tsitsimpis
        self.logger.debug("Upload schema files to server")
556 4c818bb2 Ilias Tsitsimpis
        _put(os.path.join(schema_dir, "*"), "/etc/snf-deploy/")
557 525f2979 Ilias Tsitsimpis

558 525f2979 Ilias Tsitsimpis
        self.logger.debug("Change password in nodes.conf file")
559 525f2979 Ilias Tsitsimpis
        cmd = """
560 525f2979 Ilias Tsitsimpis
        sed -i 's/^password =.*/password = {0}/' /etc/snf-deploy/nodes.conf
561 525f2979 Ilias Tsitsimpis
        """.format(fabric.env.password)
562 525f2979 Ilias Tsitsimpis
        _run(cmd, False)
563 525f2979 Ilias Tsitsimpis

564 525f2979 Ilias Tsitsimpis
        self.logger.debug("Run snf-deploy")
565 525f2979 Ilias Tsitsimpis
        cmd = """
566 525f2979 Ilias Tsitsimpis
        snf-deploy all --autoconf
567 525f2979 Ilias Tsitsimpis
        """
568 525f2979 Ilias Tsitsimpis
        _run(cmd, True)
569 525f2979 Ilias Tsitsimpis

570 525f2979 Ilias Tsitsimpis
    @_check_fabric
571 525f2979 Ilias Tsitsimpis
    def unit_test(self):
572 525f2979 Ilias Tsitsimpis
        """Run Synnefo unit test suite"""
573 525f2979 Ilias Tsitsimpis
        self.logger.info("Run Synnefo unit test suite")
574 525f2979 Ilias Tsitsimpis
        component = self.config.get('Unit Tests', 'component')
575 525f2979 Ilias Tsitsimpis

576 525f2979 Ilias Tsitsimpis
        self.logger.debug("Install needed packages")
577 525f2979 Ilias Tsitsimpis
        cmd = """
578 525f2979 Ilias Tsitsimpis
        pip install mock
579 525f2979 Ilias Tsitsimpis
        pip install factory_boy
580 525f2979 Ilias Tsitsimpis
        """
581 525f2979 Ilias Tsitsimpis
        _run(cmd, False)
582 525f2979 Ilias Tsitsimpis

583 2255812d Ilias Tsitsimpis
        self.logger.debug("Upload tests.sh file")
584 2255812d Ilias Tsitsimpis
        unit_tests_file = os.path.join(self.ci_dir, "tests.sh")
585 4c818bb2 Ilias Tsitsimpis
        _put(unit_tests_file, ".")
586 525f2979 Ilias Tsitsimpis

587 525f2979 Ilias Tsitsimpis
        self.logger.debug("Run unit tests")
588 525f2979 Ilias Tsitsimpis
        cmd = """
589 2255812d Ilias Tsitsimpis
        bash tests.sh {0}
590 525f2979 Ilias Tsitsimpis
        """.format(component)
591 525f2979 Ilias Tsitsimpis
        _run(cmd, True)
592 525f2979 Ilias Tsitsimpis

593 525f2979 Ilias Tsitsimpis
    @_check_fabric
594 525f2979 Ilias Tsitsimpis
    def run_burnin(self):
595 525f2979 Ilias Tsitsimpis
        """Run burnin functional test suite"""
596 525f2979 Ilias Tsitsimpis
        self.logger.info("Run Burnin functional test suite")
597 525f2979 Ilias Tsitsimpis
        cmd = """
598 525f2979 Ilias Tsitsimpis
        auth_url=$(grep -e '^url =' .kamakirc | cut -d' ' -f3)
599 525f2979 Ilias Tsitsimpis
        token=$(grep -e '^token =' .kamakirc | cut -d' ' -f3)
600 525f2979 Ilias Tsitsimpis
        images_user=$(kamaki image list -l | grep owner | \
601 525f2979 Ilias Tsitsimpis
                      cut -d':' -f2 | tr -d ' ')
602 525f2979 Ilias Tsitsimpis
        snf-burnin --auth-url=$auth_url --token=$token \
603 525f2979 Ilias Tsitsimpis
            --force-flavor=2 --image-id=all \
604 525f2979 Ilias Tsitsimpis
            --system-images-user=$images_user \
605 525f2979 Ilias Tsitsimpis
            {0}
606 525f2979 Ilias Tsitsimpis
        log_folder=$(ls -1d /var/log/burnin/* | tail -n1)
607 525f2979 Ilias Tsitsimpis
        for i in $(ls $log_folder/*/details*); do
608 525f2979 Ilias Tsitsimpis
            echo -e "\\n\\n"
609 525f2979 Ilias Tsitsimpis
            echo -e "***** $i\\n"
610 525f2979 Ilias Tsitsimpis
            cat $i
611 525f2979 Ilias Tsitsimpis
        done
612 525f2979 Ilias Tsitsimpis
        """.format(self.config.get('Burnin', 'cmd_options'))
613 525f2979 Ilias Tsitsimpis
        _run(cmd, True)
614 525f2979 Ilias Tsitsimpis

615 525f2979 Ilias Tsitsimpis
    @_check_fabric
616 124c300e Christos Stavrakakis
    def fetch_compressed(self, src, dest=None):
617 33ad9a0d Ilias Tsitsimpis
        """Create a tarball and fetch it locally"""
618 124c300e Christos Stavrakakis
        self.logger.debug("Creating tarball of %s" % src)
619 124c300e Christos Stavrakakis
        basename = os.path.basename(src)
620 124c300e Christos Stavrakakis
        tar_file = basename + ".tgz"
621 124c300e Christos Stavrakakis
        cmd = "tar czf %s %s" % (tar_file, src)
622 525f2979 Ilias Tsitsimpis
        _run(cmd, False)
623 124c300e Christos Stavrakakis
        if not os.path.exists(dest):
624 124c300e Christos Stavrakakis
            os.makedirs(dest)
625 525f2979 Ilias Tsitsimpis

626 124c300e Christos Stavrakakis
        tmp_dir = tempfile.mkdtemp()
627 124c300e Christos Stavrakakis
        fabric.get(tar_file, tmp_dir)
628 525f2979 Ilias Tsitsimpis

629 124c300e Christos Stavrakakis
        dest_file = os.path.join(tmp_dir, tar_file)
630 124c300e Christos Stavrakakis
        self._check_hash_sum(dest_file, tar_file)
631 124c300e Christos Stavrakakis
        self.logger.debug("Untar packages file %s" % dest_file)
632 ee2419c5 Christos Stavrakakis
        cmd = """
633 ee2419c5 Christos Stavrakakis
        cd %s
634 124c300e Christos Stavrakakis
        tar xzf %s
635 124c300e Christos Stavrakakis
        cp -r %s/* %s
636 124c300e Christos Stavrakakis
        rm -r %s
637 124c300e Christos Stavrakakis
        """ % (tmp_dir, tar_file, src, dest, tmp_dir)
638 ee2419c5 Christos Stavrakakis
        os.system(cmd)
639 124c300e Christos Stavrakakis
        self.logger.info("Downloaded %s to %s" %
640 124c300e Christos Stavrakakis
                         (src, _green(dest)))
641 124c300e Christos Stavrakakis

642 124c300e Christos Stavrakakis
    @_check_fabric
643 124c300e Christos Stavrakakis
    def fetch_packages(self, dest=None):
644 33ad9a0d Ilias Tsitsimpis
        """Fetch Synnefo packages"""
645 124c300e Christos Stavrakakis
        if dest is None:
646 124c300e Christos Stavrakakis
            dest = self.config.get('Global', 'pkgs_dir')
647 124c300e Christos Stavrakakis
        dest = os.path.abspath(dest)
648 124c300e Christos Stavrakakis
        if not os.path.exists(dest):
649 124c300e Christos Stavrakakis
            os.makedirs(dest)
650 124c300e Christos Stavrakakis
        self.fetch_compressed("synnefo_build-area", dest)
651 85bcc8da Christos Stavrakakis
        self.logger.info("Downloaded debian packages to %s" %
652 124c300e Christos Stavrakakis
                         _green(dest))