Andy McKay

Apr 21, 2010

Avoiding some generic views


As I wrote this, I realised I seemed to be on a roll with negative blog posts. Sorry, I will get positive again soon, I'm sure.

If you follow through the Django tutorial, you'll get to stage 4 which encourages you to move to generic views. Generic views are a neat way of removing the view part of the equation. Instead of a standard URL > view > template, you have URL > template.

There's documentation on all the generic views and there's quite a few.

The problem

Here's the conversation that goes on in #django IRC about once every day or so. Abbreviated, its normally more long winded than this.

djangodood: can I pass parameters to a query in templates?

others: no

djangodood: well how do I do this then? I tried doing it in urls.py and that didn't work

others: do it in your view

...usually a break of a few minutes.

djangodood: but I want to use my generic views

others bang heads on table

Logic for a template should be done mostly in the view. If its very model specific, doing it in the model might make sense. But the key is keep the template as simple as possible. The templating language reinforces this by not allowing parameters.

Using generic views for things like object_list gives you a problem, you need to put the logic somewhere, so you either try pushing it up into urls.py or down into the template. We all know why the template is the wrong place (hopefully). So then urls.py starts to get really complicated. If you urls.py is full of logic for the view, wouldn't it just be better to push that back into a view?

In practice I've found using generic views that a few things will happen: 1) I write a pile of generic views, 2) my urls.py gets complicated and then 3) as the site gets more complicated I have to start removing generic views. In a non-trivial site, the generic views quickly get removed.

What does make sense

The direct_to_template or the redirect_to make sense to me. These generic views don't involve passing any new data to the templates, different querysets or parsed data - that means most of the time they work just fine.

Writing a wrapper that uses the generic view, as James Bennet shows.

In the tutorial, the generic views seem to say "hey skip writing this bit of Python". Chances are you'll be better off just writing that bit of Python as you'll need to go back to it. And it will stop you trying to do too much work in the template.