Programming Post-Commit Hooks for Subversion with Python

I am a regular user of Subversion, all my important TeX files are stored in a SVN repository. SVN has a few builtin hooks, which means at certain events certain scripts are called. The following templates can be found in the hooks subdirectory of the server repository:

  • post-commit.tmpl
  • post-lock.tmpl
  • post-revprop-change.tmpl
  • post-unlock.tmpl
  • pre-commit.tmpl
  • pre-lock.tmpl
  • pre-revprop-change.tmpl
  • pre-unlock.tmpl
  • start-commit.tmpl

It does not matter in what kind of language the scripts are written, Subversion only cares if an executable script (or *.exe file with this name) is present (remove ‚.tmpl‘ at the end of a script to activate it). Today, after reading http://palita.net/2011/08/24/svn-hooks-automatischer-checkout-nach-commits/, I was interested in writing a small Python script which notifies me if a commit has taken place. Based on some e-mail script from http://segfault.in/2010/12/sending-gmail-from-python/ and the argparse tutorial I managed to finish this script in just a few minutes. argparse is needed since Subversion calls the post-commit script with two parameters, the path to the repository and the version of the commit.

One note on the Google password: It is recommended to use application-specific passwords, see http://support.google.com/mail/bin/answer.py?hl=en&answer=1173270 for details.

#!/usr/bin/python
 
import smtplib # part of standard installation
import argparse # not part of standard installation
 
parser = argparse.ArgumentParser()
parser.add_argument("path", help="path to the repository on the server")
parser.add_argument("version", help="version of the commit")
 
args = parser.parse_args()
print args.path
print args.version
 
server = 'smtp.gmail.com'
port = 587
 
sender = '<sender mail address>'
recipient = '<receiver mail address>'
password = "<password>"
subject = 'SVN Commit'
body = 'SVN Commit: '
 
body = body +  args.path + ' ' +  args.version
 
headers = ["From: " + sender,
           "Subject: " + subject,
           "To: " + recipient,
           "MIME-Version: 1.0",
           "Content-Type: text/html"]
headers = "\r\n".join(headers)
 
session = smtplib.SMTP(server, port)
 
session.ehlo()
session.starttls()
session.ehlo
session.login(sender, password)
 
session.sendmail(sender, recipient, headers + "\r\n\r\n" + body)
session.quit()

Deutsche Zusammenfassung: Subversion stellt gewisse Einsprungspunkte bereit, zu denen man eigene Skripte ausführen kann. Mit Python lässt sich recht einfach ein Skript schreiben, das einen Nutzer über z.B. ein Commit informiert.