Main Contents

Grabbing git patches via gmail

Code

Im a rabid gmail user. I pretty much funnel every piece of email I get from my various email addresses into google. Yes, I drank the kool-aide(tm). Whats it you ya? Wanna fight about it?

Anyhoo, I wanted a system where I could use all of the goodness of git-am without having to actually use something other than my beloved gmail. So, using a little python, libgmail and a hacked up archive.py script that came with libgmail, I set out to do what I wanted. I am on a Mac, so I do get the added benefit of having all that unix email goodness built right in.

The basic idea is simple. When a patch comes in that I care about, I tag it with Patches in gmail. Then I drop to command line and run this script. It basically logs in to gmail, looks for any messages tagged as Patches and copies them to my local (and usually unused) unix users inbox. It then removes the Patches tag and adds the Old Patches tag.

The script looks like so:

#!/usr/bin/env python
#
# Grab email from a gmail label, load it into your local inbox, and
# change the label to something else.
#
# Author: ted@tedkulp.com
# Based on code by: follower@myrealbox.com
#
# License: GPL 2.0
#
import os
import sys
import logging
import time
import datetime
 
# Allow us to run using installed `libgmail` or the one in parent directory.
try:
	 import libgmail
	 logging.warn"Note: Using currently installed `libgmail` version."
except ImportError:
	 # Urghhh...
	 sys.path.insert1, os.path.realpathos.path.joinos.path.dirname__file__,os.path.pardir
 
if __name__ == "__main__":
	import libgmail
	import sys
	from getpass import getpass
 
	username = 'username'
	password = 'password'
	new_label = 'Patches'
	old_label = 'Old Patches'
	mbox_dir = '/var/mail/tedkulp' #Change to inbox for your user
 
	ga = libgmail.GmailAccountusername, password
 
	print "\nPlease wait, logging in..."
 
	try:
		ga.login
	except libgmail.GmailLoginFailure:
		print "\nLogin failed. (Wrong username/password?)"
	else:
		print "Log in successful.\n"
 
	result = ga.getMessagesByLabelnew_label, True
	print
	mbox = 
 
	if lenresult:
		for thread in reversedresult:
			print
			print thread.id, lenthread, thread.subject
 
			for msg in reversedthread:
				print "	 ", msg.id, msg.number, msg.subject
				source = msg.source.replace"\r","".lstrip
				mbox.appenddatetime.datetime.now.strftime"From - %a %b %d %H:%m:%S %Y\n"
				mbox.appendsource
				mbox.append"\n\n" #TODO:Check if we need either/both?
 
			thread.removeLabelnew_label
			thread.addLabelold_label
 
		openmbox_dir, "a".writelinesmbox
 
	else:
		print "No threads found in `%s`." % new_label

And then just like Linus does on http://www.kernel.org/pub/software/scm/git/docs/everyday.html, I can do stuff like:

$ mailx
& s 2 3 4 5 ./+to-apply
& d 2-5
& q
$ git checkout -b topic/one master
$ git am -3 -i -s -u ./+to-apply

Beautiful.

Edit

05/20/2008 - Ive updated the code a bit. There was a nesting issue that was causing messages to be pulled multiple times. Ive also added the current date at the time of the pull instead of the 1998 date, and also pulling them in opposite order so that they are pushed into the inbox in the order they were received.

Ted @ May 8, 2008

Leave a comment

XHTML: You can use these tags: <a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <cite> <code> <del datetime=""> <em> <i> <q cite=""> <strike> <strong>


Feed