Django session + dynamic form + model form

214 views
Skip to first unread message

voss

unread,
Aug 2, 2011, 2:15:12 PM8/2/11
to django...@googlegroups.com
Hello all,

I have a dynamic form as follows:

class myForm(forms.Form):
    Question = forms.ModelMultipleChoiceField(queryset=Model.objects.none(), widget=forms.RadioSelect())
    def __init__(self, request, *args, **kwargs):
        super(myForm, self).__init__(*args, **kwargs)
        self.fields['Question'].choices = Model.objects.filter(**request.session['filter_dict']).values_list('city', 'city').distinct()


In views.py I have

def myAnswer(request):
        Answer = myForm(request.GET or None)
        if Answer.is_valid():
            ...........................................................
            ...........................................................

I am getting the "'QueryDict' object has no attribute 'session'" error, and I believe it is because of the "Ans = myForm(request.GET or None)" line. Could anyone please let me know how to fix it ?

Many thanks!

Daniel Roseman

unread,
Aug 2, 2011, 3:39:50 PM8/2/11
to django...@googlegroups.com
You've defined your form to expect a `request` argument, but then you haven't passed that argument.

    answer = MyForm(request, request.GET or None) 
--
DR.

sasa...@gmail.com

unread,
Aug 2, 2011, 11:57:06 PM8/2/11
to django...@googlegroups.com
Thank you, DR. But I tried that before and it did not work for some
reason. It basically skips "if Answer.is_valid():" and goes to "else".

voss

You've defined your form to expect a `request` argument, but then you
haven't passed that argument.
>
> answer = MyForm(request, request.GET or None)
> --
> DR.

> --
> You received this message because you are subscribed to the Google
> Groups "Django users" group.
> To view this discussion on the web visit
> https://groups.google.com/d/msg/django-users/-/3eYgahTEsy8J.
> To post to this group, send email to django...@googlegroups.com.
> To unsubscribe from this group, send email to
> django-users...@googlegroups.com.
> For more options, visit this group at
> http://groups.google.com/group/django-users?hl=en.

Tom Evans

unread,
Aug 3, 2011, 6:40:38 AM8/3/11
to django...@googlegroups.com
On Wed, Aug 3, 2011 at 4:57 AM, sasa...@gmail.com <sasa...@gmail.com> wrote:
> Thank you, DR. But I tried that before and it did not work for some reason.
> It basically skips "if Answer.is_valid():" and goes to "else".
>
>    voss
>

I think this is because you are abusing your model form, and hence it
is not valid.

You should not be setting choices on a ModelMultipleChoiceField, you
should be supplying a queryset that describes the choices you want.
When validating the form, django will check that the submitted values
are contained in the ModelMultipleChoiceField's queryset.

Furthermore, ModelMultipleChoiceField will normally have id ->
description mapping, where as you have description -> description, eg
it should generate this HTML - <option value="2">London</option>,
where as you have it generating <option
value="London">London</option>. It's just wrong. I guess you are
trying to do this to control the label generated - you should be doing
this[1].

So recap:
Don't assign choices to a ModelMultipleChoiceField, assign a queryset
Use a custom ModelMultipleChoiceField subclass to control how each
model is displayed.

Cheers

Tom

[1] https://docs.djangoproject.com/en/1.3/ref/forms/fields/#modelchoicefield

I can't link to the block of text directly, look for this:

"""
The __unicode__ method of the model will be called to generate string
representations of the objects for use in the field's choices; to
provide customized representations, subclass ModelChoiceField and
override label_from_instance. This method will receive a model object,
and should return a string suitable for representing it.
"""

voss

unread,
Aug 3, 2011, 5:38:17 PM8/3/11
to django...@googlegroups.com
Thank you, Tom. You are right! I shouldn't assign choices to a ModelMultipleChoiceField. That's what caused the problem. But instead of constructing a custom ModelMultipleChoiceField subclass, I abandoned "Model Form" and simply did the following, which worked!

class myForm(forms.Form):
    Question = forms.ChoiceField(choices=[], widget=forms.RadioSelect())

    def __init__(self, request, *args, **kwargs):
        super(myForm, self).__init__(*args, **kwargs)
        self.fields['Question'].choices = Model.objects.filter(**request.session['filter_dict']).values_list('city', 'city').distinct()

And in views.py,

def myAnswer(request):
        Answer = myForm(request, request.GET or None)
        if Answer.is_valid():
            ...........................................................
            ...........................................................

Once again, thank you for pointing out such important concept. It helped a lot!

cheers,

   voss 
Reply all
Reply to author
Forward
0 new messages