Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Empty querysets in Django

Tags:

I have a ListView in Django whose get_queryset() method will sometimes need to return no results. I've tried three ways to do this:

  1. return EmptyQuerySet()
  2. return Model.objects.none()
  3. return Model.objects.filter(pk=-1)

Each one of these returns a slightly different object.

  1. django.db.models.query.EmptyQuerySet with its model attribute set to None
  2. django.db.models.query.EmptyQuerySet with its model attribute set to Model
  3. django.db.models.query.QuerySet with its model attribute set to Model

Only the third option works with the class based ListView. The other options crash on an attribute error when the ListView tries to access the model attribute. This surprises me and is a pain as it requires me to import Model in places where that can cause MRO issues.

What am I doing wrong/what should I be doing differently?

Update: The question then is, what is the right way to return an empty queryset via the class view method get_queryset()?

Update: Here is the line in Django's generic views that hits an attribute error when trying access the model attribute: https://github.com/django/django/blob/stable/1.5.x/django/views/generic/list.py#L166.

like image 476
Erik Avatar asked Apr 28 '13 05:04

Erik


People also ask

What are QuerySets in Django?

A QuerySet is a collection of data from a database. A QuerySet is built up as a list of objects. QuerySets makes it easier to get the data you actually need, by allowing you to filter and order the data.

How do I join QuerySets in Django?

Use union operator for queryset | to take union of two queryset. If both queryset belongs to same model / single model than it is possible to combine querysets by using union operator. One other way to achieve combine operation between two queryset is to use itertools chain function.


1 Answers

I think the best way to accomplish this is to call none() on objects for your respective model, and return the result. Assuming your model is named Entry:

queryset = Entry.objects.none() 
like image 191
Harel Avatar answered Oct 21 '22 14:10

Harel