request.POST binding to wrong parameter in forms

This is a common idiom in a view.:

def view_func(request):
    form = FormClass()
    if request.method == 'POST':
    payload = {'form':form}
    return render_to_response(...)

Now suppose we edited our form class to:

class FormClass(forms.Form):
    def __init__(self, user = None, *args, **kwargs):

request.POST will bind to user, when we meant to be the POST data.


Rewrite the gotcha line as


Using form.cleaned_data before calling form.is_valid

Even if you are sure your form passes validation, you still need to call is_valid. form.cleaned_data is calculated after form.is_valid is called, which you probably are using in your

Overriding in ModelForms:

Similar to, are often (wrongly) overriden as

    super(FormCLass, self).save()

This won’t work in many cases, for example


Always save as:

def, *args, **kwargs):
    super(FormClass, self).save(*args, **kwargs)

Not calling superclass __init__

You might want to change the widget of a particular form field and this can be done by overriding Form’s __init__.:

from django.contrib.admin.widgets import AdminFileWidget

class FormClass(forms.ModelForm):

    class Meta:
        model = Profile

    def __init__(self, *args, **kwargs):
        self.fields['picture'].widget = AdminFilewidget() #Gotcha

self.fields is populated after __init__ of ModelForm has executed. So, make sure to call superclass __init__ before accessing self.fields.:

def __init__(self, *args, **kwargs):
    super(FormClass, self).__init__(*args, **kwargs)
    self.fields['picture'].widget = AdminFilewidget()