[Grok-dev] REST branch ready for review
faassen at startifact.com
Tue Oct 16 08:57:18 EDT 2007
I'd like people to take a look at the REST branch before I merge it.
The branch is:
What this branch does is add support for REST protocol implementations.
Following a suggestion by Michael Kerrin such a REST protocol is exposed
as a special kind of skin-like thing. This allows us to separate REST
requests from other requests on an objects, so that you can have a
normal UI with views on a set of objects in parallel to the
implementation of one or more REST protocols.
First, let's see how you define a REST protocol. Similar to the way
skins work, first you need to define a layer:
We now can put a REST object in this layer:
return "GET request, retrieve container listing"
return "POST request, add something to container"
return "PUT request, replace complete contents"
return "DELETE request, delete this object entirely"
To get to the body of the request, there's a special attribute on 'self'
that contains this as a string:
return "This is the body: " + self.body
This body should be parsed accordingly by your REST protocol implementation.
To actually issue REST requests over a URL, you need to define a REST
protocol that uses this layer:
grok.name('atompub') # a nicer name
Now you can access the object with the REST protocol, through requests
like this (issuing GET, POST, PUT or DELETE):
If you don't like the ++rest++ bit you can also provide the layer
manually to the request during traversal (just like with skins), or of
course institute a few rewrite rules in Apache.
If you don't actually use a layer for a REST subclass, it'll use the
grok.IRESTLayer by default. This layer is the base of all REST layers.
Security works with all this: you can use @grok.require() on the REST
methods to shield them from public use.
What I don't like about this branch is that I have to handle GET and
POST differently than PUT and DELETE. GET and POST are handled by the
BrowserPublication, while PUT and DELETE fall back on the HTTP
publication. I tried to hide this from the end user and so far the only
visible difference is that a content type of text/plain is sent back in
case of errors with GET and POST and not in the case of PUT and DELETE.
Implementation-wise, I wish there were a better way. Normally you'd just
register another kind of publisher to handle REST requests, analogous to
how XMLRPC requests work. Unfortunately there is nothing in the
enviroment of a REST request (before the request itself is born) to
recognize that it *is* a REST request. We don't want there to be, as
it's important a REST protocol implementation can be browsed using a
normal web browser without having to set special headers and such (as
this would seriously hamper debuggability). Still, it would be nice if
there were a cleaner way to implement this.
When you review the branch, make sure to read the test code in
More information about the Grok-dev