One of the great aspects of CloudCrowd is that the code base is so small and readable. A big part of that comes by virtue of using the Sinatra Web application framework for the master and slave daemon processes. Sinatra is much closer to the GAE webapp framework than CherryPy (by default), in that you define methods that correspond to the HTTP verbs (GET, PUT, POST, DELETE and HEAD). Sinatra differs in that the method’s first argument is the route that the method services. The GAE webapp framework instead forces you to define a class that the defines the HTTP verbs, and later map those classes to some route. Let’s take a look at “Hello World!” to illustrate the difference. Here is the GAE webapp version
from google.appengine.ext import webapp
from google.appengine.ext.webapp.util import run_wsgi_app
class HelloWorld(webapp.RequestHandler):
def get(self):
self.response.out.write("Hello World!")
app = webapp.WSGIApplication([("/",HellowWorld)])
def main():
run_wsgi_application(app)
if __name__ == "main":
main()
Now here is the version in Sinatra:
require "rubygems" # RubyGems is optional, depending on your setup require "sinatra" get '/' do "Hello World!" end
Much more readable and concise. Here is a version of HellWorld in CherryPy, using the default MethodDispatcher, for comparison:
import cherrypy
class HelloWorld:
exposed = True
def GET(self):
return "Hello World!"
app = HelloWorld()
d = cherrypy.dispatch.MethodDispatcher()
conf = {'/': {'request.dispatch': d}}
cherrypy.tree.mount(root, "/", conf)
Better, but you are still separating the the mapping of the root URL “/” to the HelloWorld class outside of the class. I started digging around the interwebz for Python frameworks that would work closer to the lightweight Sinatra and found Bottle. Bottle is small, self-contained and uses python decorators to map a function to a route. Brilliant. Here is the example using Bottle:
from bottle import route, run
@route("/") # assumes GET method
def hello():
return "Hello world!"
run() # This starts the HTTP server
Now that’s what I’m talking about! Deploying a Bottle application to GAE is covered in their documentation. We’ll be using Bottle for cu3w0rx to create the master and slave daemons in later posts.

2 comments
October 28, 2009 at 3:15 pm
Nick Johnson
I’m looking forward to reading the rest of the series! You might want to consider submitting your posts to the App Engine reddit (http://reddit.com/r/appengine), for some extra attention. I’ve already submitted this post and the previous one.
October 29, 2009 at 3:28 pm
delagoya
Thanks Nick. I’ll do that.