Opened 11 years ago
Closed 10 years ago
#24196 closed Bug (duplicate)
Filtering __in a sliced queryset with a 0 limit raises an unexpected error
| Reported by: | Bertrand Bordage | Owned by: | nobody |
|---|---|---|---|
| Component: | Database layer (models, ORM) | Version: | 1.7 |
| Severity: | Normal | Keywords: | |
| Cc: | Triage Stage: | Accepted | |
| Has patch: | no | Needs documentation: | no |
| Needs tests: | no | Patch needs improvement: | no |
| Easy pickings: | no | UI/UX: | no |
Description
AnyModel.objects.filter(pk__in=AnyModel.objects.all()[i:i]) (where i is a positive integer) raises a ProgrammingError at least on Django 1.6 and 1.7. It most certainly affects all other Django versions too.
That’s because the ORM avoids converting AnyModel.objects.all()[:0] to a SQL query, while .filter(in___=…) tries to include that inexistant SQL query. The resulting SQL looks like SELECT * FROM any_model WHERE id IN (), which is invalid.
A working fix is to change line 91 of compiler.py to raise EmptyResultSet instead of return '', ().
WhereNode.as_sql then catches this exception and notes that it should select nothing. However, I’m not sure that it doesn’t break something else. I can make a pull request with a unit test if you want.
In the meantime, a workaround is to detect whether the inner QuerySet verifies queryset.query.low_mark == queryset.query.high_mark, and do something relevant if it does.
Attachments (1)
Change History (3)
comment:1 by , 11 years ago
| Triage Stage: | Unreviewed → Accepted |
|---|
by , 11 years ago
| Attachment: | 24196-test.diff added |
|---|
I could reproduce this on PostgreSQL (but not SQLite) with the attached test.