#19173 closed Uncategorized (fixed)
"query" param for Model.objects.none() queryset has unexpected value.
Reported by: | Owned by: | nobody | |
---|---|---|---|
Component: | Uncategorized | Version: | 1.4 |
Severity: | Normal | Keywords: | |
Cc: | Triage Stage: | Unreviewed | |
Has patch: | no | Needs documentation: | no |
Needs tests: | no | Patch needs improvement: | no |
Easy pickings: | no | UI/UX: | no |
Description
- Create Django model:
class Location(models.Model): name = models.CharField(max_length=100)
- Get a null set
res = Location.objects.none()
- Check the SQL relating to this set:
print(res.query.sql_with_params()) >> ('SELECT "name" FROM "location", ())
The SQL above would actually return all the records in the database. My expectation is that I'd get the same result here as when I do the following:
query = Location.objects.filter(id__in=[]) print(query.sql_with_params())
This, in fact, throws an EmptyResultSet error which seems reasonable as there's really no SQL statement to go along with a purposefully empty set.
Change History (5)
comment:1 by , 12 years ago
comment:2 by , 12 years ago
We really should get rid of the whole none() -> EmptyQuerySet. We would get 150 lines worth of DRY code removal. The code would be more robust (EmptyQS has had its problems, see the altered tests...). Still one more bonus point is that a query which has had .none() applied works exactly like normal queries (for example qs.none().filter(nonexistingfield=someval) would raise exception correctly.
The cost of this is speed penalty from QuerySet cloning. The fix for this is making cloning cheaper.
The biggest problem might be that .none() documentation explicitly mentions EmptyQuerySet. There is no reason the docs need to mention EQS. Seems like leaking implementation detail to me. My opinion is to not make a backwards compatibility issue out of this. Just noting that EQS has been removed should be enough IMO.
Implementation available here: https://github.com/akaariai/django/commit/915cf9e495f033a07feb6c9aaece44d735d7fe70
comment:3 by , 12 years ago
I created another ticket for emptyqs removal - see #19184.
I am going to close this ticket. As Alex said qs.query isn't part of public API, so we don't have to guarantee it works like in qs.filter(pk__in=[])
. If we want to fix this IMO the proper fix is to just remove the emptyqs altogether which ensures qs.none() will work like qs.filter(pk__in=[])
works in every case - not just str(qs.query) case.
comment:4 by , 12 years ago
Resolution: | → wontfix |
---|---|
Status: | new → closed |
Closing the ticket per Anssi's comment.
comment:5 by , 12 years ago
Resolution: | wontfix → fixed |
---|
.query
isn't a public API, so I'm not sure we care.