#20267: default form values (not just initial)
-------------------------------+--------------------------------------
Reporter: clime | Owner: nobody
Type: New feature | Status: closed
Component: Forms | Version: 1.5
Severity: Normal | Resolution: worksforme
Keywords: form, default | Triage Stage: Unreviewed
Has patch: 0 | Needs documentation: 0
Needs tests: 0 | Patch needs improvement: 0
Easy pickings: 0 | UI/UX: 0
-------------------------------+--------------------------------------
Comment (by clime):
Well my problem was that I have this form for filtering:
{{{
class CragFilter(forms.Form):
country =
forms.ChoiceField(choices=Country.objects.all().order_by('name').values_list('id',
'name'), required=False)
crag_type = forms.MultipleChoiceField(choices=crag_types,
initial=[str(BOULDER), str(ROUTE)], widget=forms.CheckboxSelectMultiple,
required=False)
order_by = forms.CharField(required=False, initial='crag')
order_asc = forms.BooleanField(required=False, initial=True)
}}}crag_filter = CragFilter(data)
Now there were actually two problems. The first one was with with the
initial value for crag_type. Filtering should be done by GET requests, I
believe, so I simply did this in my view:
{{{
def crag_list(request):
crag_filter = CragFilter(request.GET)
if crag_filter.is_valid():
filter_params = crag_filter.cleaned_data
crag_list = Crag.get_objects(filter_params)
context = {
'crag_filter': crag_filter,
'crag_list': crag_list,
}
return render(request, 'crags.html', context)
}}}
Seems quite natural to me. But I have found out that checkboxes in
frontend are not checked after the initial page load (without any query
params). And later I have found out it is because form has been bounded to
request.GET data. But mainly the crag_list was empty because the initial
values has been lost. So I have decided to do this in the view:
{{{
if request.GET:
crag_filter = CragFilter(request.GET)
else:
crag_filter = CragFilter()
}}}
which I don't like at all but it was the simplest solution.
But I have work on and discovered yet another problem with order_by and
order_asc fields. These fields are not part of the frontend form (by
graphic design and provided templates) but it seemed natural to put them
into the backend/logic form anyway so that I can simply pass these
parameters to model with others and then in models differentiate what to
put as param of .filter() and what to put as a param of .order_by(). This
approach simply makes view simpler (which is good, I think). Backend form
does not "match" the frontend form but it was possible to do it like this
without any javascript hacks and it all worked well. Except initial values
because checking if request.GET is empty before passing it to the filter
was no longer working. Basically, if querystring has not been populated,
submitting the form trashed initial values for filter params and
submitting the ordering trashed initial values filtering. In the end I
needed to do something like this in view:
{{{
data = request.GET.copy()
data.setlistdefault('crag_type', [str(BOULDER), str(ROUTE)])
data.setdefault('order_by', 'crag')
data.setdefault('order_asc', True)
crag_filter = CragFilter(data)
}}}
which was really painful. Maybe there is some other option with some
clean_[field_name] methods but that is painful too.
Well, allright I understand that I can't expect "the initial" values to
behave like "default values" (except I totally did when I was learning
about forms.) but I don't understand why there is not the "default
functionality" that would work in the same way like that one for models.
It would cover the "initial functionality" but also would be more solid,
robust and intuitive...basicall it would decouple frontend (rendering)
functionality from backend (logic) functionality.
--
Ticket URL: <https://code.djangoproject.com/ticket/20267#comment:2>
Django <https://code.djangoproject.com/>
The Web framework for perfectionists with deadlines.
--
You received this message because you are subscribed to the Google Groups
"Django updates" group.
To unsubscribe from this group and stop receiving emails from it, send an email
to [email protected].
To post to this group, send email to [email protected].
For more options, visit https://groups.google.com/groups/opt_out.