Lions and tigers, and Pythons and Rabbits, oh my!

We've recently been doing some great work on projects using Google App Engine, a highly scalable framework for building web apps in Python or Java. We've posted before about our friendly talking robot rabbit, Nabaztag. I thought it would be fun (and vaguely useful) to make our rabbit announce when new code was pushed to our repositories on GitHub.

GitHub has a feature called post-receive hooks which you can set up for any repository. You can provide a URL which will receive an HTTP POST with a JSON object describing details of the pushed commits. Here's an example payload:

  1. {
  2. "before": "5aef35982fb2d34e9d9d4502f6ede1072793222d",
  3. "repository": {
  4. "url": "http://github.com/defunkt/github",
  5. "name": "github",
  6. "description": "You're lookin' at it.",
  7. "watchers": 5,
  8. "forks": 2,
  9. "private": 1,
  10. "owner": {
  11. "email": "chris@ozmm.org",
  12. "name": "defunkt"
  13. }
  14. },
  15. "commits": [
  16. {
  17. "id": "41a212ee83ca127e3c8cf465891ab7216a705f59",
  18. "url": "http://github.com/defunkt/github/commit/41a212ee83ca127e3c8cf465891ab7216a705f59",
  19. "author": {
  20. "email": "chris@ozmm.org",
  21. "name": "Chris Wanstrath"
  22. },
  23. "message": "okay i give in",
  24. "timestamp": "2008-02-15T14:57:17-08:00",
  25. "added": ["filepath.rb"]
  26. },
  27. {
  28. "id": "de8251ff97ee194a289832576287d6f8ad74e3d0",
  29. "url": "http://github.com/defunkt/github/commit/de8251ff97ee194a289832576287d6f8ad74e3d0",
  30. "author": {
  31. "email": "chris@ozmm.org",
  32. "name": "Chris Wanstrath"
  33. },
  34. "message": "update pricing a tad",
  35. "timestamp": "2008-02-15T14:36:34-08:00"
  36. }
  37. ],
  38. "after": "de8251ff97ee194a289832576287d6f8ad74e3d0",
  39. "ref": "refs/heads/master"
  40. }

I used the Nabazlib library by Ricardo Varela to deal with communicating with the Nabaztag. One of the nice things about Python is there's almost always a package for whatever you're trying to achieve!

I also chose to use Google's WebApp framework. This makes the app really simple! Here's app.yaml:

  1. application: nabazhook
  2. version: 1
  3. runtime: python
  4. api_version: 1
  5.  
  6. handlers:
  7. - url: .*
  8. script: main.py
  9.  

Here's the main.py. The constructor to webapp.WSGIApplication accepts a list of url patterns. This maps the URL / to the Hook class. Then I defined a method post on the class which will be called whenever GitHub POSTs data to the URL.

  1. from google.appengine.ext import webapp
  2. from google.appengine.ext.webapp.util import run_wsgi_app
  3. from django.utils import simplejson as json
  4.  
  5. from nabazlib.Nabaztag import Nabaztag
  6.  
  7. class Hook(webapp.RequestHandler):
  8.  
  9. def post(self):
  10.  
  11. #get the credentials for the nazaztag
  12. u = self.request.get("id")
  13. p = self.request.get("secret")
  14.  
  15. #get the JSON payload. this is stored in the POST variable "payload"
  16. jsonstr = self.request.get("payload")
  17.  
  18. #parse it
  19. obj = json.loads(jsonstr)
  20.  
  21. #read out some interesting data
  22. reponame = obj['repository']['name']
  23. author = obj['commits'][0]['author']['name']
  24. msg = obj['commits'][0]['message']
  25. numcommits = len(obj['commits'])
  26.  
  27. #construct the string we want to send to the rabbit
  28. txt = "Git alert! Git alert! %s just pushed %d commits to %s" %(author,numcommits,reponame)
  29. self.response.out.write(txt)
  30.  
  31. #construct the nabaztag object and send the text
  32. myNabaztag = Nabaztag(u,p)
  33. myNabaztag.say(txt,voice='US-Liberty')
  34.  
  35. application = webapp.WSGIApplication([
  36. ('/', Hook)
  37. ], debug=True)
  38.  
  39. def main():
  40. run_wsgi_app(application)
  41.  
  42. if __name__ == '__main__':
  43. main()
  44.  

I deployed a test version of the app to http://nabazhook.appspot.com/ - so by adding a post-receive URL to any repository like this, I can make Nabaztag talk.

And that's all there is to it! The code is available on GitHub if you want to play around with it. If you have any more suggestions of things to do with Nabby, do share them in the comments...

Matt Mayer

Matt Mayer is a founder at ReignDesign. Matt is from the UK and was based in Shanghai for ten years. He is now living in Bangkok, Thailand.

Leave a Reply

Your email address will not be published. Required fields are marked *