New contribution announcement: RESTful model views.

27 views
Skip to first unread message

asmi...@gmail.com

unread,
Mar 17, 2007, 10:53:36 AM3/17/07
to Django users
I recently began a new project to implement (as much as possible) pure
REST within Django in a way that fits with Django's approach to Web
development:

django-restful-model-views
http://code.google.com/p/django-restful-model-views

It still needs a lot of work, but my ultimate goal is to only require
one change to Django's settings that will automatically configure
RESTful URLs that map to RESTful methods for each model. By default,
these methods would be implemented using generic views, and could also
be overridden easily.

When I began exploring these ideas, my only goal was to better
familiarize myself with Django and to better understand the REST
philosophy, not to build this contribution. So, I could really use
some constructive criticism, and I'm even prepared to hear that I'm
way off base with this approach. Alternately, if this contribution
looks promising, I could use the help of more experienced Django
developers to finish the work.

Even if I am on the right track with this approach, the question still
remains if implementing pure REST in Django is worth using this
contribution. I suspect the answer depends on how much you care about
REST, otherwise, the more natural, standard, semi-RESTful way of using
Django is pretty darn good, and much simpler. But, it may also be that
on large, complex applications, this approach may help more logically
organize application code.

I began writing about this in my blog, and although the entries are
long, they do represent the thought process that led me to this
particular solution:

Toward a RESTful Approach to Django Applications
http://www.stonemind.net/blog/2007/03/01/toward-a-restful-approach-to-django-applications/

Django REST Redux
http://www.stonemind.net/blog/2007/03/08/django-rest-redux/

Test Driving a RESTful Django Contribution
http://www.stonemind.net/blog/2007/03/15/test-driving-a-restful-django-contribution/

These posts contain the source code to an intentionally artificial
Django application that I used to test the REST code. In the first two
posts, the REST code is part of the application, while the application
in the third post uses the RESTful contribution.

Thanks in advance for any feedback you may wish to give.

adam

Malcolm Tredinnick

unread,
Mar 17, 2007, 12:26:19 PM3/17/07
to django...@googlegroups.com
On Sat, 2007-03-17 at 14:53 +0000, aj...@cornell.edu wrote:
> I recently began a new project to implement (as much as possible) pure
> REST within Django in a way that fits with Django's approach to Web
> development:
>
> django-restful-model-views
> http://code.google.com/p/django-restful-model-views
[...]

> Even if I am on the right track with this approach, the question still
> remains if implementing pure REST in Django is worth using this
> contribution. I suspect the answer depends on how much you care about
> REST, otherwise, the more natural, standard, semi-RESTful way of using
> Django is pretty darn good, and much simpler.

You seem to building a lot of your argument on a small strawman here and
it's important to realise that. You speak of "pure REST" and your code
makes it easy to expose model methods directly via a web interface. That
(equating front- and back-end entities) isn't a requirement, or even a
recommendation, of REST architecture methods. REST resource !=
middle-tier object (meaning "not always equal"). Sometimes? Yes, but
that's more accidental happenstance or thanks to a very simple system of
objects.

This can be a stumbling block for people trying to design REST
interfaces, because they spend a lot of time attempting such a mapping.
Having a web interface layer provides a good chance to
simplify/uniformise some of the complexity in the underlying object
model. I don't mean that always as "a chance to fix problems", but
sometimes the underlying model is complex of necessity, whereas the user
interface need not be.

(There's also a minor point in your first blog post that you seem to
associate REST with "things done through a web browser", which is a bit
of an artificially limiting constraint. There are a lot of useful
REST-based interfaces around that are designed to be talked to by other
software that isn't a web browser.)

Django neither enforces nor discourages REST-inspired access patterns.
However, it does make it easy to build them (so it does encourage that
style). See the examples below for why the URL <-> model method mapping
is too restrictive for all REST applications. I think, therefore, it's
an error to write that what you have developed is pure REST and Django
is semi-RESTful.

What you have done (with a nice design, by the looks of it), is provide
a relatively low-effort way for people who want to directly expose model
methods in this fashion.

> But, it may also be that
> on large, complex applications, this approach may help more logically
> organize application code.

The danger is that it also might encourage people to put methods on
their models that do more than just affect that model (see examples).
It's not a given that this leads to more logical application code and we
could debate that all day without reaching a firm conclusion, since one
man's logical is likely to get that same man fired for writing
unmanageable code in another scenario.

A couple of concrete examples to illustrate the points I'm trying to
make above:

(1) The Atom Publishing Protocol (APP) provides a resource (called the
Service Document) one can retrieve which acts as a way to discover the
available publishing endpoints. This does not really correspond to any
concrete object at the storage layer, although you could do it with a
configuration object, I guess. In a version I've written in Django, most
of this information is auto-discovered by a view function, so the
resource returned has no concrete back-end representation.

(2) Imagine a blog posting system. The creation of an entry might
require sending a multipart form containing a couple of file uploads
(images), and the text and then all this has to split up so that
articles go to one model, images go somewhere else, images need to have
their correct URL put into the post, links may be split out so that they
can be checked for validity later on (I have a blog system that stores
links in a separate model to make it easy to check them even months
later and it automatically checks all existing links periodically) and
so on. None of these actions are the responsibility of just a single
model, so forcing it into that mode is not really brilliant software
design. However, it does use REST architecture as far as creating,
editing, retrieving and deleting resources goes. However, clearly the
web-provided interface's idea of resource is not in one-to-one
correspondence with the database and ORMs' idea of an object/resource.

There are plenty of equivalents to the second example as well, just in
case it might sound like the blog post idea is contrived. Sending an
image to an APP-enabled system is one case (the system would create a
Media Resource and a Media Link Resource). Everybody's favourite travel
booking system example (the generic REST example) has similar cases.

There are also situations where the response to a POST or a PUT,
particularly, might need the HTTP headers set in some fashion. So, if
you were going to do this all in the model, suddenly the model method
isn't just working with the model ("self"). It's also having to be aware
of (and receive) the "request" object and have knowledge of HTTP.

Having written all of the above, I think what you have written (based on
my reading of your blog postings. I haven't read the source code yet),
is a reasonable implementation of an HTTP-visible CRUD (create,
retrieve, update, delete) interface for the ORM. In the past when people
have proposed this, I've always quietly thought it isn't appropriate for
Django's core (or contrib/) because I'm not comfortable with exposing
the middle tier like that and it's only applicable in limited cases.
However, it might be that there is a wide wish for that particular set
of cases and the code you've written seems like a well thought-out
attempt to provide the interface (after all, the same limitation applies
to Django's generic views and it's not like they are unpopular). I'm
going to read through the code when I get a chance, because it's nice
that this has been implemented: we can point everybody else towards it
when they ask.

Your approach to providing an interface for model CRUD-related methods
looks reasonable and non-repetitive for the user, but I wanted to make
clear that I think that's what you have done, not any kind of solution
to "how to fix REST in Django" (which would beg the question, for a
start). Avoiding misconceptions by using accurate naming and terminology
is pretty important in Open Source projects. Despite what we might hope,
there's a lot of the proverbial judging of reading material by their
outer containing pages.

In conclusion, thanks for writing and announcing this piece of code,
regardless of the impression I may have given above about your
nomenclature.

Best wishes,
Malcolm


asmi...@gmail.com

unread,
Mar 17, 2007, 2:05:49 PM3/17/07
to Django users
Malcolm,

Thank you for your thoughtful reply, although I think its going to
take me several re-readings to get a handle on it all. If I have the
gist of it, it sounds like you're saying that a good design based on a
thorough understanding of REST and a few conventions or best practices
using the capabilities that Django already provides may be a simpler
way to achieve the same goal? I have to admit that throughout working
on this, I have wondered, and still wonder, if that isn't the better
approach.

I also just want to make sure I haven't misled anyone about what I
think I am doing--I am just learning both Django and REST, and fully
admit that this work has been a stretch for me on both fronts. In
fact, a large part of my motivation for blogging about this and
writing the contribution was to elicit exactly the kind of response
you gave. In my research into how to design a human facing Web
application RESTfully, I haven't found a lot of explicit, practical
information about how to do this. (Either that, or I just didn't
understand it when I saw it.)

In particular, I think your characterization here is right on the
money:

> Your approach to providing an interface for model CRUD-related methods
> looks reasonable and non-repetitive for the user, but I wanted to make
> clear that I think that's what you have done, not any kind of solution
> to "how to fix REST in Django" (which would beg the question, for a
> start).

In struggling to understand REST, models and their related forms were
the most obvious group of "nouns" I could see, and that's what
ultimately led me to Charlie Savage's blog post on a RESTful Rails
controller, which was a big inspiration for this work. As a result, I
did quickly focus on model CRUD related methods, but I recognize this
is only addressing one possible aspect of REST. (That's why for
example, I didn't feel like I could replace all urlpatterns with the
ones I was creating.)

I also want to be clear that I didn't start this because I think
Django is broken in any way, nor would I presume to be the one to fix
it even if it was. I am actually really jazzed about Django (insert
groan here) and REST too, and wouldn't be spending my time trying to
understand how to do this if I wasn't. But ultimately, this
contribution is me thinking out loud about these issues, and I won't
be surprised to learn that I got a lot of it wrong.

So, with all that weaseling out of the way, let me just say again that
I appreciate the time you took to look at what I did and correct some
of the misconceptions I have. I hope you do get a chance to look at
the code for the contribution and let me know if you think there is
something worth salvaging from this.

adam

Malcolm Tredinnick

unread,
Mar 17, 2007, 2:39:29 PM3/17/07
to django...@googlegroups.com
On Sat, 2007-03-17 at 18:05 +0000, aj...@cornell.edu wrote:
> Malcolm,
>
> Thank you for your thoughtful reply, although I think its going to
> take me several re-readings to get a handle on it all. If I have the
> gist of it, it sounds like you're saying that a good design based on a
> thorough understanding of REST and a few conventions or best practices
> using the capabilities that Django already provides may be a simpler
> way to achieve the same goal? I have to admit that throughout working
> on this, I have wondered, and still wonder, if that isn't the better
> approach.

I'm not really trying say to that. Rather, don't try to compartmentalise
things too much. Phrases like "good design" and "more easily" don't make
sense absent a context of *what* you are trying to design. I was trying
to raise a caution that in your enthusiasm you hadn't carefully defined
the particular problem space that you were addressing. It's smaller than
"all web applications with REST access patterns", which was the
impression I got from initially reading your email.

That's all. I realise I spent a lot of time making that point, but I
wanted to throw in some examples that illustrated the logic.

> I also just want to make sure I haven't misled anyone about what I
> think I am doing--I am just learning both Django and REST, and fully
> admit that this work has been a stretch for me on both fronts. In
> fact, a large part of my motivation for blogging about this and
> writing the contribution was to elicit exactly the kind of response
> you gave. In my research into how to design a human facing Web
> application RESTfully, I haven't found a lot of explicit, practical
> information about how to do this. (Either that, or I just didn't
> understand it when I saw it.)

Yeah, I can sympathise with the last sentence here. It is hard to learn
and every time you think you have a handle on it, somebody with some
apparent credibility in the field comes along and says "no, that's not
right". By the way, I'm not one of those people; I just dabble in the
shallow end a lot of the time.

There's a lot of experimentation required. You seem to have approached
things in the sensible way, though, doing a lot of reading and
follow-ups. At this point, I would suggest to also try and deliberately
challenge your own assumptions. If you think you have a handle on
something, seek out viewpoints that don't seem to fit your mental model
and then try to work whether they are not quite valid or whether your
mental model needs adjusting.

You seem to be getting a handle on things and willing to stick your nose
out with real code, so don't be put off by the fact that there's a
learning curve. I don't think the curve ever flattens out completely. It
hasn't for me, yet.

Best wishes,
Malcolm

asmi...@gmail.com

unread,
Mar 17, 2007, 3:22:18 PM3/17/07
to Django users
Thanks for the encouragement. In retrospect, I probably was being too
haphazard with terminology in my email, and elsewhere. I'll definitely
think about the examples you gave and keep trying to make sense of
REST.

On Mar 17, 2:39 pm, Malcolm Tredinnick <malc...@pointy-stick.com>
wrote:

Aaron...@gmail.com

unread,
Mar 17, 2007, 5:09:10 PM3/17/07
to Django users
PUT v POST

I've been using REST APIs for a while. My flash developers have some
issues with calling a PUT on older codebases. I have to break
religion a bit and allow POST to work as a PUT to keep the flash
simple. It is really easy to call POST/GET from actionscript 2.0

I'm looking forward to testing this out

asmi...@gmail.com

unread,
Mar 22, 2007, 7:15:24 PM3/22/07
to Django users
Malcolm,

I have re-read your response several times, and although I'm sure I
haven't fully digested everything yet, it definitely got me thinking
of the contribution in new ways. I actually posted my reactions to
your message, along with other REST musings, on my blog, as its rather
long, and the subject matter a little esoteric I suspect:
http://www.stonemind.net/blog/2007/03/22/evolving-a-restful-django-contribution/

Besides, I needed to put something on the blog this week, and this is
the subject I'm most obsessed with at the moment.

I did my best to accurately characterize some of the points you made,
so hopefully, if you read it, it won't make you cringe too much.

Thanks again for helping me re-visualize what I could be doing with
the contribution. I don't know how clearly I expressed my ideas in the
blog post, but I'd be very interested in hearing your thoughts on it.

adam

johnny

unread,
Apr 7, 2007, 8:44:21 PM4/7/07
to Django users
I am python newb. But I came across this thread. It sound like
someone has attempted it and it's in google source.
http://groups.google.com/group/django-users/browse_thread/thread/2f2840572fc99fc3/e045e3ef43b2a607?lnk=gst&q=raw_post_data&rnum=2#

Reply all
Reply to author
Forward
0 new messages