Example #1
0
def render_for_cond(cond):
    """Decorator helper to register a view for a given condition

    In:
      - ``cond`` -- the condition

    Return:
      - closure
    """
    return when(render, cond)
Example #2
0
def render_for_cond(cond):
    """Decorator helper to register a view for a given condition

    In:
      - ``cond`` -- the condition

    Return:
      - closure
    """
    return when(render, cond)
Example #3
0
def init_for(cls, cond=None):
    """Decorator helper to register an URL for a class of objects

    In:
      - ``cls`` -- the class
      - ``cond`` -- a generic condition

    Return:
      - a closure
    """
    if cond is not None:
        cond = "isinstance(self, %s) and (%s)" % (cls.__name__, cond)
    else:
        # No condition given, dispatch on the class
        cond = (cls,)

    return when(init, cond)
Example #4
0
def render_for(cls, model=None):
    """Decorator helper to register a view for a class of objects

    In:
      - ``cls`` -- the class
      - ``model`` -- the name of the view

    Return:
      - a closure
    """
    if model is not None:
        cond = 'isinstance(self, %s) and (model=="%s")' % (cls.__name__, model)
    else:
        # No name give, dispatch only on the arguments type
        cond = (cls, object, object, types.NoneType)

    return when(render, cond)
Example #5
0
def init_for(cls, cond=None):
    """Decorator helper to register an URL for a class of objects

    In:
      - ``cls`` -- the class
      - ``cond`` -- a generic condition

    Return:
      - a closure
    """
    if cond is not None:
        cond = "isinstance(self, %s) and (%s)" % (cls.__name__, cond)
    else:
        # No condition given, dispatch on the class
        cond = (cls, )

    return when(init, cond)
Example #6
0
def route_for(cls, cond=None, methods=('GET', 'HEAD')):
    """Decorator helper to register an URL for a class of objects

    In:
      - ``cls`` -- the class
      - ``cond`` -- a generic condition

    Return:
      - a closure
    """
    conds = []

    if not cond and not methods:
        # No condition given, dispatch on the class
        conds.append((cls,))

    if cond:
        conds.append('isinstance(o, %s) and (%s)' % (cls.__name__, cond))

    if methods:
        conds.append('(http_method in %r)' % (methods,))

    return when(route, ' and '.join(conds))
Example #7
0
def write_extension_data_for(cls):
    cond = 'isinstance(card_extension, %s)' % cls.__name__
    return when(write_extension_data, cond)
Example #8
0
def get_extension_title_for(cls):
    cond = 'card_extension_class.__name__ == "%s"' % cls.__name__
    return when(get_extension_title, cond)
Example #9
0
def write_extension_data_for(cls):
    cond = 'isinstance(card_extension, %s)' % cls.__name__
    return when(write_extension_data, cond)
Example #10
0
def get_extension_title_for(cls):
    cond = 'card_extension_class.__name__ == "%s"' % cls.__name__
    return when(get_extension_title, cond)
Example #11
0
class DoulaBot(QBot):
    """
    Bot for pushing and releasing
    """
    default_gitssh = "*****@*****.**"
    default_ghuser = "******"
    svnprefix = "svn://svn/s"
    default_svntree = "py"
    nickname = 'doula'
    username = nickname
    mcmd = "command.startswith('%s:')"
    cmd = "command.startswith('%s')"
    cmd_is = "command == '%s'"
    notification_list = rq.notify_channel
    index_url = "http://yorick:9003/index"
    channel = '#release'

    v_regex = re.compile('^[a-zA-Z]+-([a-zA-Z0-9\.]+).tar.gz')
    v_splitter = re.compile('(rc|a|b|dev|\.)')
    re_d = re.compile('\d')
    cmd_end = ":"

    @property
    def exec_str(self):
        return self.nickname + ':'

    @abstract
    def command(self, source, command, args):
        """
        dispatch for commands
        """
        pass

    noop = when(command, 'True')(BaseBot.noop)

    def action_msg(self, cxn, msg):
        cxn.privmsg(self.channel, '%sACTION %s ' % (chr(1), msg))

    @when(command, cmd_is % 'dance')
    def shake_booty(self, source, command, args):
        user, address = source.split('!')
        if user.startswith('doug'):
            self.broadcast("/me refuses to dance for %s" % user)
        else:
            self.broadcast("/me shakes it's metal booty for %s" % user)

    @when(command, cmd_is % 'svn')
    def svnls(self, source, command, args):
        """
        dbot: svnls: tree/path
        """
        user, handle = source.split('!')
        if args == '':
            return self.broadcast(
                "%s: you have to give me a path to work with..." % user)
        return self.enqueue(qtasks.svn_ls, args)

    def _prep_release(self, source, args):
        """
        Does some basic error checking and data preparation to be used
        by commands doing a release.
        """
        user, handle = source.split('!')
        if args == '':
            return self.broadcast(
                "%s: you must give a python package to release" % user)
        pkgv = args.strip()
        self.broadcast("/me queues %s for release for %s." % (pkgv, user))
        parts = pkgv.split('@')
        branch = None
        if len(parts) == 2:
            pkgv, branch = parts
        tokens = pkgv.split('/')
        return pkgv, branch, tokens, user

    @when(command, cmd_is % 'relsvn')
    def svn_release(self, source, command, args):
        """
        dbot: relsvn: [tree_other_than_py]pkg-0.9.8rc2[@branch]
        """
        pkgv, branch, tokens, user = self._prep_release(source, args)

        svntree = self.default_svntree
        if len(tokens) == 2:
            svntree, pkgv = tokens

        svnprefix = utils.urljoin(self.svnprefix, svntree)
        return self.enqueue(pypkg.pyrelease_svn_task, pkgv, branch, svnprefix,
                            user)

    @when(command, cmd_is % 'relgit')
    def git_release(self, source, command, args):
        """
        dbot: relgit: [user_or_group/]pkg-0.1.1[@branch] (from git)
        """
        pkgv, branch, tokens, user = self._prep_release(source, args)

        ghuser = self.default_ghuser
        if len(tokens) == 2:
            ghuser, pkgv = tokens

        return self.enqueue(pypkg.pyrelease_git_task, pkgv, branch, ghuser,
                            user)

    javasrc = set(('billingdal', 'userdal'))

    @when(command, cmd_is % 'reljava')
    def release_java(self, source, command, args):
        """
        doula: reljava: {billingdal|userdal}-1.0rc2@branchname
        """
        user, handle = source.split('!')
        if args == '':
            return self.broadcast(
                "%s: you must give a java sourcetree (Billing or UserAccount) to release"
                % user)
        pkgv = args.strip()
        self.broadcast("/me queues %s for release for %s." % (pkgv, user))
        parts = pkgv.split('@')
        branch = None
        if len(parts) == 2:
            pkgv, branch = parts
        pv = pkgv.split('-')
        assert len(pv) == 2, "You must include a src tree and a version"
        assert pv[0] in self.javasrc, "%s not in available srctrees: %s" % (
            pv[0], self.javasrc)
        return self.enqueue(java.DALRelease, pkgv, branch)

    @when(command, cmd_is % 'help')
    def help(self, source, command, args):
        for name in sorted([
                'svnls', 'current_version', 'git_release', 'svn_release',
                'versions', 'push', 'cycle', 'release_java'
        ]):
            method = getattr(self, name)
            self.broadcast(method.__doc__.strip())

    @when(command, cmd_is % 'cycle')
    def cycle(self, source, command, args, task=qtasks.cycle2):
        """
        doula:cycle: bill*@mt1 | billweb:8100@mt2
        """
        user, o = source.split('!')
        args = [x.strip() for x in args.split('@')]
        if len(args) != 2:
            self.broadcast("%s: wrong format for cycle" % user)
            self.broadcast('help for cycle: cycle: someapp@mt1')
        app, mt = args
        self.broadcast('/me queues cycle for %s on %s' % (app, mt))
        self.enqueue(task, app, mt, user)

    @when(command, ' or '.join([cmd_is % 'push', cmd_is % 'push2']))
    def push(self, source, command, args, task=pushmod.push2):
        """
        doula:push: howler-0.9.8rc2 -> billweb@mt2,billweb@mt2
        """
        user, o = source.split('!')
        pkgv, mts = [x.strip() for x in args.split('->')]
        mts = [x.strip() for x in mts.split(',')]

        for mt in mts:
            self.broadcast('/me queues push to %s of %s for %s' %
                           (mt, pkgv, user))
            self.enqueue(task, pkgv, mt, user)

    def _fetch_versions(self, pkg):
        root = html.parse("%s/%s" % (self.index_url, pkg.strip())).getroot()
        return (x.text for x in root.cssselect('a'))

    @when(command, cmd_is % 'v')
    def versions(self, source, command, args):
        """
        doula:v:smlib.billing  (lists all available releases)
        """
        pkg = args
        versions = self.sorted_versions(self._fetch_versions(pkg))
        for version in versions:
            sleep(0.5)
            self.broadcast(version)

    @staticmethod
    def get_distro(url):
        return next(distros_for_url(url))

    def sorted_versions(self, raw_vs, reverse=False):
        distros = (self.get_distro(url) for url in raw_vs)
        distros = sorted(distros, reverse=reverse)
        for dist in distros:
            yield "-".join(dist.egg_name().rsplit('-')[:-1])

    @when(command, cmd_is % 'cv')
    def current_version(self, source, command, args):
        """
        doula:cv:smlib.billing  (shows current version by best guess)
        """
        pkg = args
        try:
            vs = self._fetch_versions(pkg)
        except IOError:
            return self.broadcast("/me could not find %s" % pkg)

        if vs:
            versions = self.sorted_versions(vs, reverse=True)
            self.broadcast(next(versions))