# Building query from non-empty search parameters only

**URL:** <https://forum.djangoproject.com/t/building-query-from-non-empty-search-parameters-only/26518>\
**Category:** Forms & APIs\
**Created:** [December 30, 2023, 10:08am UTC](https://forum.djangoproject.com/t/building-query-from-non-empty-search-parameters-only/26518 "2023-12-30T10:08:18Z")\
**Posts on this page:** 7\
**Page:** 1

<div class="post-metadata">

**Author:** ![janedenone](https://sea2.discourse-cdn.com/flex026/user_avatar/forum.djangoproject.com/janedenone/32/12025_2.png) [@janedenone](https://forum.djangoproject.com/u/janedenone)\
**Post date:** [December 30, 2023, 10:08am UTC](https://forum.djangoproject.com/t/building-query-from-non-empty-search-parameters-only/26518/1 "2023-12-30T10:08:18Z")

</div>

My search form contains three fields, one of which (`content`) is much more expensive than the others. So my search view adds each parameter to the query only if the user actually used the respective field:

```auto
def search(request):
	if request.method == 'POST':
		form = SearchForm(request.POST)
		if form.is_valid():
			formfields_parameters = [('page_content', 'content__icontains'), ('page_author', 'author__last_name__icontains'), ('page_title', 'title__icontains')]
			search_dict = {}
			for (formfield, parameter) in formfields_parameters:
				if form.cleaned_data[formfield]:
					search_dict[parameter] = form.cleaned_data[formfield]
			results = Page.objects.filter(**search_dict).defer('content').order_by('title')

```

This works well, but looks a little clumsy. Is there a better/more elegant way to achieve the same result?

---

<div class="post-metadata">

**Author:** ![jackroot7](https://sea2.discourse-cdn.com/flex026/user_avatar/forum.djangoproject.com/jackroot7/32/18015_2.png) [@jackroot7](https://forum.djangoproject.com/u/jackroot7)\
**Post date:** [December 30, 2023, 11:35am UTC](https://forum.djangoproject.com/t/building-query-from-non-empty-search-parameters-only/26518/2 "2023-12-30T11:35:09Z")

</div>

Can you share your SearchForm code.

And also, Is there any situation by which all three field maybe used to search … ?

---

<div class="post-metadata">

**Author:** ![KenWhitesell](https://sea2.discourse-cdn.com/flex026/user_avatar/forum.djangoproject.com/kenwhitesell/32/280_2.png) [@KenWhitesell](https://forum.djangoproject.com/u/KenWhitesell)\
**Post date:** [December 30, 2023, 12:11pm UTC](https://forum.djangoproject.com/t/building-query-from-non-empty-search-parameters-only/26518/3 "2023-12-30T12:11:54Z")

</div>

Side note: Whatever streamlining is done here will have negligible effect on the overall performance. The time required for the query itself is going to be orders of magnitude larger than any improvement you can achieve in building this query.

You can get “fancier”, but I’m not sure those options are any more elegent.

For example, you could build the `search_dict` incrementally, within the form, in the individual `clean_` methods of the form. You would create `clean_page_content`, `clean_page_author`, and `clean_page_title` methods - each checking for content and adding to the `search_dict`.

You could use the search terms as the names of the fields, and iterate over them in the form’s `clean` method. (This is only helpful if these three search fields are the only fields in that form.)

You could rewrite the code you posted here to use a dict-comprehension.

But, it’s up to _you_ to decide what best expresses the intent behind this, because _you_ are the person that’s going to need to come back to this in 6 - 12 months and try to remember what you were thinking when you wrote it.

---

<div class="post-metadata">

**Author:** ![janedenone](https://sea2.discourse-cdn.com/flex026/user_avatar/forum.djangoproject.com/janedenone/32/12025_2.png) [@janedenone](https://forum.djangoproject.com/u/janedenone)\
**Post date:** [December 30, 2023, 4:37pm UTC](https://forum.djangoproject.com/t/building-query-from-non-empty-search-parameters-only/26518/4 "2023-12-30T16:37:54Z")

</div>

Sure, it is very simple:

```auto
class SearchForm(forms.Form):
	page_title = forms.CharField(max_length=100, min_length=4, label = 'Titel', required=False)
	page_content = forms.CharField(max_length=100, min_length=4, label = 'Inhalt', required=False)
	page_author = forms.CharField(max_length=100, min_length=4, label = 'Autorin', required=False)

```

The user can fill out any combination of the three fields.

---

<div class="post-metadata">

**Author:** ![janedenone](https://sea2.discourse-cdn.com/flex026/user_avatar/forum.djangoproject.com/janedenone/32/12025_2.png) [@janedenone](https://forum.djangoproject.com/u/janedenone)\
**Post date:** [December 30, 2023, 4:41pm UTC](https://forum.djangoproject.com/t/building-query-from-non-empty-search-parameters-only/26518/5 "2023-12-30T16:41:13Z")

</div>

I am aware that my solution already addresses the actual bottleneck effectively. I was just wondering whether there is a more efficient solution, and will experiment with the options you pointed out. Thank you!

---

<div class="post-metadata">

**Author:** ![KenWhitesell](https://sea2.discourse-cdn.com/flex026/user_avatar/forum.djangoproject.com/kenwhitesell/32/280_2.png) [@KenWhitesell](https://forum.djangoproject.com/u/KenWhitesell)\
**Post date:** [December 30, 2023, 7:54pm UTC](https://forum.djangoproject.com/t/building-query-from-non-empty-search-parameters-only/26518/6 "2023-12-30T19:54:31Z")

</div>

> [@janedenone](#):
>
> I was just wondering whether there is a more efficient solution

Probably not - as I said in my previous reply, any difference in execution time between the solutions is going to be a rounding error compared to the time necessary for the query itself.

What I presented as solutions are an attempt to provide other implementations that would satisfy your original stated criteria:

> [@janedenone](#):
>
> Is there a better/more elegant way to achieve the same result?

… Which is _not_ the same thing.

---

<div class="post-metadata">

**Author:** ![janedenone](https://sea2.discourse-cdn.com/flex026/user_avatar/forum.djangoproject.com/janedenone/32/12025_2.png) [@janedenone](https://forum.djangoproject.com/u/janedenone)\
**Post date:** [December 30, 2023, 9:33pm UTC](https://forum.djangoproject.com/t/building-query-from-non-empty-search-parameters-only/26518/7 "2023-12-30T21:33:53Z")

</div>

You’re right – I mixed up (at least) two different goals, and probably should not invest too much time in improving maintainable code that works well.
