I have an alternate suggestion, an expansion of malcomt's idea, rather
than changing the machinery of the current url handlers, and which
should work in your existing code.  (note this is untested code, but I
believe it should work, barring any syntactical errors.)


First, we define a RestfulView base class, which leverages python's
__call__ functionality.


from django.http import HttpResponseNotAllowed

class RestfulView(object):
    def __call__(self, request, *args, **kw):
        # try and find a handler for the given HTTP method
        method = request.META['REQUEST_METHOD'].upper()
        handler = getattr(self, 'handle_%s' % method, None)

        if handler is None:
            # compile a list of all our methods and return an HTTP 405
            methods = []
            for x in dir(self):
                if x.startswith('handle_'):
                    methods.append(x[7:])
            return HttpResponseNotAllowed(methods)

        return handler(request, *args, **kw)



Now we define a "view" class which extends our RestfulView (again, I
didn't check to see if this works, I just tore apart an existing view
I have)   Note that the ability to use a class meant I was able to
define a helper method used by both the views.


class BlogComments(RestfulView):
    def _find_post(self, request, year, month, day, slug):
        """ Helper function used in all the comment views"""
        try:
            return Post.objects.find_post(year, month, day, slug)
        except Post.DoesNotExist:
            raise Http404()

    def handle_GET(self, request, year, month, day, slug):
        post = self._find_post(year, month, day, slug)
        posts = post.comment_set.filter(previewed=True)
        return render_to_response('blog/comments.html', {'posts': posts}

    def handle_POST(self, request, year, month, day, slug):
        post = self._find_post(year, month, day, slug):
        # do AddManipulator stuff here
        return render_to_response(..... )

# This line binds an instance of BlogComments to "comments".
# Since this code is at module-level it will be re-executed
# properly on a reload, which we want
comments = BlogComments()


Finally, we set up our urlconf:

urlpatterns = patterns('',
   
(r'^archive/(?P<year>\d+)/(?P<month>\d+)/(?P<day>\d+)/(?P<slug>[\w-]+)/comments/',
'myapp.blog.views.comments')

Note that since django trunk now supports directly referencing
callables, you could alternately do this:

from myapp.views.comments import BlogComments

urlpatterns = patterns('',
   
(r'^archive/(?P<year>\d+)/(?P<month>\d+)/(?P<day>\d+)/(?P<slug>[\w-]+)/comments/',
BlogComments())


The only caveat I see with this approach is that you have to
re-declare all the params in each of the request_FOO handlers, though
I don't really think that's a huge problem.  For implementing a large
multi-method thing, such as say webDAV, or some sort of RPC, this is a
very clear way of implementing things, without any nasty dicts.   You
can hide the RestfulView base class machinery away in another module,
and then just define your views which need it as classes, with zero
effect to your existing "traditional" views or to the base handler
machinery.    It also means you don't need to use any nasty dicts of
handlers :P

--~--~---------~--~----~------------~-------~--~----~
You received this message because you are subscribed to the Google Groups 
"Django developers" group.
To post to this group, send email to [email protected]
To unsubscribe from this group, send email to [EMAIL PROTECTED]
For more options, visit this group at 
http://groups.google.com/group/django-developers
-~----------~----~----~----~------~----~------~--~---

Reply via email to