aboutsummaryrefslogtreecommitdiff
blob: 291b88e11ee5e835f7ec2c1bd36d1069c88ed1d7 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
# vim: set sw=4 sts=4 et :
# Copyright: 2008 Gentoo Foundation
# Author(s): Nirbheek Chauhan <nirbheek.chauhan@gmail.com>
# License: GPL-2
#
# Immortal lh!
#

import os, subprocess, shutil
import os.path as osp
from .. import const

class Syncer(object):
    """
    Sync stuff
    """

    def __init__(self, scheme='bzr', uri=const.JOBTAGE_URI, rev='last:1', destdir=const.JOBTAGE_DIR):
        """
        Default is to sync the jobtage tree from the default location.

        @param destdir: Destination directory
        @scheme destdir: string

        @param uri: Uri where to sync from
        @scheme uri: string

        @param rev: Revision of SCM (if applicable), default is latest
        @scheme rev: string

        @param scheme: The URI scheme
        @scheme scheme: string
        """
        self.destdir = destdir
        if not uri.endswith('/'):
            uri += '/'
        self.command = Command(scheme, uri, rev, destdir)

    def sync(self):
        """
        Sync self.uri contents to self.destdir 
        self.destdir must not exist if init-ing
        Returns None if unsuccessful, returns True otherwise.
        """
        if osp.exists(self.destdir):
            if not osp.isdir(self.destdir):
                # FIXME: Custom exceptions
                raise '"%s" exists and is not a directory' % self.destdir
            #print 'Syncing...'
            self.command.run('sync')
        else:
            if not osp.exists(osp.dirname(self.destdir)):
                # Create parents
                os.makedirs(osp.dirname(self.destdir))
            #print 'Initing...'
            self.command.run('init')

class Command(object):
    """Command to use for each uri scheme and action"""

    def __init__(self, scheme, uri, rev, destdir):
        self.scheme = scheme
        self.uri = uri
        self.rev = rev
        self.destdir = destdir

    def _get_args(self, action):
        if self.scheme == 'bzr':
            if action == 'init':
                return 'bzr branch -r"%s" "%s" "%s"' % (self.rev, self.uri, self.destdir),
            elif action == 'sync':
                return 'bzr pull --overwrite -r"%s" -d "%s" "%s"' % (self.rev, self.destdir, self.uri),
        elif self.scheme == 'bzr-export':
            if action == 'init':
                return 'bzr export -r"%s" "%s" "%s"' % (self.rev, self.destdir, self.uri),
            elif action == 'sync':
                return  'bzr export -r"%s" "%s" "%s"' % (self.rev, self.destdir, self.uri), {'rmtree': self.destdir},
        elif self.scheme == 'rsync':
            return 'rsync -a --delete "%s" "%s"' % (self.uri, self.destdir),
        print "Unknown scheme: %s" % self.scheme
        return None

    def run(self, action):
        """Run a sync command"""
        args = self._get_args(action)
        # Uh, yeah, this is ugly.
        if len(args) == 2:
            params = args[1]
            if params.has_key('rmtree'):
                shutil.rmtree(params['rmtree'])
        subprocess.check_call(args[0], shell=True)