diff options
Diffstat (limited to 'hgext/notify.py')
-rw-r--r-- | hgext/notify.py | 171 |
1 files changed, 54 insertions, 117 deletions
diff --git a/hgext/notify.py b/hgext/notify.py index b0fbcee..5e96f11 100644 --- a/hgext/notify.py +++ b/hgext/notify.py @@ -5,135 +5,77 @@ # This software may be used and distributed according to the terms of the # GNU General Public License version 2 or any later version. -'''hooks for sending email push notifications +'''hooks for sending email notifications at commit/push time -This extension implements hooks to send email notifications when -changesets are sent from or received by the local repository. +Subscriptions can be managed through a hgrc file. Default mode is to +print messages to stdout, for testing and configuring. -First, enable the extension as explained in :hg:`help extensions`, and -register the hook you want to run. ``incoming`` and ``changegroup`` hooks -are run when changesets are received, while ``outgoing`` hooks are for -changesets sent to another repository:: +To use, configure the notify extension and enable it in hgrc like +this:: + + [extensions] + notify = [hooks] # one email for each incoming changeset incoming.notify = python:hgext.notify.hook - # one email for all incoming changesets + # batch emails when many changesets incoming at one time changegroup.notify = python:hgext.notify.hook - - # one email for all outgoing changesets + # batch emails when many changesets outgoing at one time (client side) outgoing.notify = python:hgext.notify.hook -This registers the hooks. To enable notification, subscribers must -be assigned to repositories. The ``[usersubs]`` section maps multiple -repositories to a given recipient. The ``[reposubs]`` section maps -multiple recipients to a single repository:: + [notify] + # config items go here + +Required configuration items:: + + config = /path/to/file # file containing subscriptions + +Optional configuration items:: + + test = True # print messages to stdout for testing + strip = 3 # number of slashes to strip for url paths + domain = example.com # domain to use if committer missing domain + style = ... # style file to use when formatting email + template = ... # template to use when formatting email + incoming = ... # template to use when run as incoming hook + outgoing = ... # template to use when run as outgoing hook + changegroup = ... # template to use when run as changegroup hook + maxdiff = 300 # max lines of diffs to include (0=none, -1=all) + maxsubject = 67 # truncate subject line longer than this + diffstat = True # add a diffstat before the diff content + sources = serve # notify if source of incoming changes in this list + # (serve == ssh or http, push, pull, bundle) + merge = False # send notification for merges (default True) + [email] + from = user@host.com # email address to send as if none given + [web] + baseurl = http://hgserver/... # root of hg web site for browsing commits + +The notify config file has same format as a regular hgrc file. It has +two sections so you can express subscriptions in whatever way is +handier for you. + +:: [usersubs] - # key is subscriber email, value is a comma-separated list of repo glob - # patterns + # key is subscriber email, value is ","-separated list of glob patterns user@host = pattern [reposubs] - # key is glob pattern, value is a comma-separated list of subscriber - # emails + # key is glob pattern, value is ","-separated list of subscriber emails pattern = user@host -Glob patterns are matched against absolute path to repository -root. - -In order to place them under direct user management, ``[usersubs]`` and -``[reposubs]`` sections may be placed in a separate ``hgrc`` file and -incorporated by reference:: - - [notify] - config = /path/to/subscriptionsfile - -Notifications will not be sent until the ``notify.test`` value is set -to ``False``; see below. - -Notifications content can be tweaked with the following configuration entries: - -notify.test - If ``True``, print messages to stdout instead of sending them. Default: True. - -notify.sources - Space-separated list of change sources. Notifications are activated only - when a changeset's source is in this list. Sources may be: - - :``serve``: changesets received via http or ssh - :``pull``: changesets received via ``hg pull`` - :``unbundle``: changesets received via ``hg unbundle`` - :``push``: changesets sent or received via ``hg push`` - :``bundle``: changesets sent via ``hg unbundle`` - - Default: serve. - -notify.strip - Number of leading slashes to strip from url paths. By default, notifications - reference repositories with their absolute path. ``notify.strip`` lets you - turn them into relative paths. For example, ``notify.strip=3`` will change - ``/long/path/repository`` into ``repository``. Default: 0. - -notify.domain - Default email domain for sender or recipients with no explicit domain. - -notify.style - Style file to use when formatting emails. - -notify.template - Template to use when formatting emails. - -notify.incoming - Template to use when run as an incoming hook, overriding ``notify.template``. - -notify.outgoing - Template to use when run as an outgoing hook, overriding ``notify.template``. - -notify.changegroup - Template to use when running as a changegroup hook, overriding - ``notify.template``. - -notify.maxdiff - Maximum number of diff lines to include in notification email. Set to 0 - to disable the diff, or -1 to include all of it. Default: 300. - -notify.maxsubject - Maximum number of characters in email's subject line. Default: 67. - -notify.diffstat - Set to True to include a diffstat before diff content. Default: True. - -notify.merge - If True, send notifications for merge changesets. Default: True. - -notify.mbox - If set, append mails to this mbox file instead of sending. Default: None. - -notify.fromauthor - If set, use the committer of the first changeset in a changegroup for - the "From" field of the notification mail. If not set, take the user - from the pushing repo. Default: False. - -If set, the following entries will also be used to customize the -notifications: - -email.from - Email ``From`` address to use if none can be found in the generated - email content. - -web.baseurl - Root repository URL to combine with repository paths when making - references. See also ``notify.strip``. +Glob patterns are matched against path to repository root. +If you like, you can put notify config file in repository that users +can push changes to, they can manage their own subscriptions. ''' from mercurial.i18n import _ from mercurial import patch, cmdutil, templater, util, mail import email.Parser, email.Errors, fnmatch, socket, time -testedwith = 'internal' - # template for single changeset can include email headers. single_template = ''' Subject: changeset in {webroot}: {desc|firstline|strip} @@ -170,7 +112,6 @@ class notifier(object): self.stripcount = int(self.ui.config('notify', 'strip', 0)) self.root = self.strip(self.repo.root) self.domain = self.ui.config('notify', 'domain') - self.mbox = self.ui.config('notify', 'mbox') self.test = self.ui.configbool('notify', 'test', True) self.charsets = mail._charsets(self.ui) self.subs = self.subscribers() @@ -226,6 +167,9 @@ class notifier(object): return [mail.addressencode(self.ui, s, self.charsets, self.test) for s in sorted(subs)] + def url(self, path=None): + return self.ui.config('web', 'baseurl') + (path or self.root) + def node(self, ctx, **props): '''format one changeset, unless it is a suppressed merge.''' if not self.merge and len(ctx.parents()) > 1: @@ -303,7 +247,7 @@ class notifier(object): self.ui.status(_('notify: sending %d subscribers %d changes\n') % (len(self.subs), count)) mail.sendmail(self.ui, util.email(msg['From']), - self.subs, msgtext, mbox=self.mbox) + self.subs, msgtext) def diff(self, ctx, ref=None): @@ -349,18 +293,15 @@ def hook(ui, repo, hooktype, node=None, source=None, **kwargs): ui.pushbuffer() data = '' count = 0 - author = '' if hooktype == 'changegroup' or hooktype == 'outgoing': start, end = ctx.rev(), len(repo) for rev in xrange(start, end): if n.node(repo[rev]): count += 1 - if not author: - author = repo[rev].user() else: data += ui.popbuffer() - ui.note(_('notify: suppressing notification for merge %d:%s\n') - % (rev, repo[rev].hex()[:12])) + ui.note(_('notify: suppressing notification for merge %d:%s\n') % + (rev, repo[rev].hex()[:12])) ui.pushbuffer() if count: n.diff(ctx, repo['tip']) @@ -374,9 +315,5 @@ def hook(ui, repo, hooktype, node=None, source=None, **kwargs): n.diff(ctx) data += ui.popbuffer() - fromauthor = ui.config('notify', 'fromauthor') - if author and fromauthor: - data = '\n'.join(['From: %s' % author, data]) - if count: n.send(ctx, count, data) |