Sketch in skeleton of module from bzr-email
[bzrirker.git] / irkerhook.py
diff --git a/irkerhook.py b/irkerhook.py
new file mode 100644 (file)
index 0000000..b2dd4fe
--- /dev/null
@@ -0,0 +1,114 @@
+# -*- coding: utf-8 -*-
+# vim:fileencoding=utf-8 ai ts=4 sts=4 et sw=4
+# Copyright 2012 Neil Muller
+# GPL 2+ - see COPYING for details
+
+from bzrlib import (
+    errors,
+    revision as _mod_revision,
+    )
+from bzrlib.config import (
+    ListOption,
+    Option,
+    bool_from_store,
+    int_from_store,
+    )
+
+
+class IrkerSender(object):
+    """An irker message sender."""
+
+    def __init__(self, branch, revision_id, config, local_branch=None,
+        op='commit'):
+        self.config = config
+        self.branch = branch
+        self.repository = branch.repository
+        if (local_branch is not None and
+            local_branch.repository.has_revision(revision_id)):
+            self.repository = local_branch.repository
+        self._revision_id = revision_id
+        self.revision = None
+        self.revno = None
+        self.op = op
+
+    def _setup_revision_and_revno(self):
+        self.revision = self.repository.get_revision(self._revision_id)
+        self.revno = self.branch.revision_id_to_revno(self._revision_id)
+
+    def _format(self):
+        fields = {
+            'committer': self.revision.committer,
+            'message': self.revision.get_summary(),
+            'revision': '%d' % self.revno,
+            'url': self.url()
+        }
+        text = ''
+        #for name, value in fields.items():
+        #    text = text.replace('$%s' % name, value)
+        return text
+
+    def body(self):
+        from bzrlib import log
+
+        rev1 = rev2 = self.revno
+        if rev1 == 0:
+            rev1 = None
+            rev2 = None
+
+        # use 'replace' so that we don't abort if trying to write out
+        # in e.g. the default C locale.
+
+        # Following bzr-email, we use StringIO.StringIO to minimise possible
+        # unicode issues.
+        from StringIO import StringIO
+        outf = StringIO()
+
+        lf = log.log_formatter('line',
+                               show_ids=True,
+                               to_file=outf
+                               )
+
+        if len(self.revision.parent_ids) <= 1:
+            # This is not a merge, so we can special case the display of one
+            # revision, and not have to encur the show_log overhead.
+            lr = log.LogRevision(self.revision, self.revno, 0, None)
+            lf.log_revision(lr)
+        else:
+            # let the show_log code figure out what revisions need to be
+            # displayed, as this is a merge
+            log.show_log(self.branch,
+                         lf,
+                         start_revision=rev1,
+                         end_revision=rev2,
+                         verbose=True
+                         )
+
+        return outf.getvalue()
+
+    def url(self):
+        """What URL to display in the subject of the mail"""
+        url = self.config.get('irker_url')
+        if url is None:
+            url = self.config.get('public_branch')
+        if url is None:
+            url = self.branch.base
+        return url
+
+    def send(self):
+        """Send the info to irkerd.
+        """
+        self.branch.lock_read()
+        self.repository.lock_read()
+        try:
+            # Do this after we have locked, to make things faster.
+            self._setup_revision_and_revno()
+        finally:
+            self.repository.unlock()
+            self.branch.unlock()
+
+opt_irker_url = Option('irker_url',
+    help='URL to mention for branch in messages.')
+opt_irker_channels = Option('irker_channels',
+    help='Channel(s) to post commit messages to.')
+opt_irker_colours = Option('irker_colours',
+    help='Colour option for irker.')