summaryrefslogtreecommitdiff
path: root/tests/custom_lookups
diff options
context:
space:
mode:
authorJacob Walls <jacobtylerwalls@gmail.com>2024-12-29 01:13:48 -0800
committerSarah Boyce <42296566+sarahboyce@users.noreply.github.com>2025-08-04 10:14:01 +0200
commit8914f4703cf03e2a01683c4ba00f5ae7d3fa449d (patch)
tree5331d4fac059c893d16875710dc8539ff91bdc81 /tests/custom_lookups
parent079d31e698fa08dd92e2bc4f3fe9b4817a214419 (diff)
Fixed #35972 -- Fixed lookup crashes after subquery annotations.
Diffstat (limited to 'tests/custom_lookups')
-rw-r--r--tests/custom_lookups/tests.py42
1 files changed, 38 insertions, 4 deletions
diff --git a/tests/custom_lookups/tests.py b/tests/custom_lookups/tests.py
index 6728c49afd..db985240d7 100644
--- a/tests/custom_lookups/tests.py
+++ b/tests/custom_lookups/tests.py
@@ -5,6 +5,7 @@ from datetime import date, datetime
from django.core.exceptions import FieldError
from django.db import connection, models
from django.db.models.fields.related_lookups import RelatedGreaterThan
+from django.db.models.functions import Lower
from django.db.models.lookups import EndsWith, StartsWith
from django.test import SimpleTestCase, TestCase, override_settings
from django.test.utils import register_lookup
@@ -17,15 +18,15 @@ class Div3Lookup(models.Lookup):
lookup_name = "div3"
def as_sql(self, compiler, connection):
- lhs, params = self.process_lhs(compiler, connection)
+ lhs, lhs_params = self.process_lhs(compiler, connection)
rhs, rhs_params = self.process_rhs(compiler, connection)
- params.extend(rhs_params)
+ params = (*lhs_params, *rhs_params)
return "(%s) %%%% 3 = %s" % (lhs, rhs), params
def as_oracle(self, compiler, connection):
- lhs, params = self.process_lhs(compiler, connection)
+ lhs, lhs_params = self.process_lhs(compiler, connection)
rhs, rhs_params = self.process_rhs(compiler, connection)
- params.extend(rhs_params)
+ params = (*lhs_params, *rhs_params)
return "mod(%s, 3) = %s" % (lhs, rhs), params
@@ -249,6 +250,39 @@ class LookupTests(TestCase):
self.assertSequenceEqual(qs1, [a1])
self.assertSequenceEqual(qs2, [a1])
+ def test_custom_lookup_with_subquery(self):
+ class NotEqual(models.Lookup):
+ lookup_name = "ne"
+
+ def as_sql(self, compiler, connection):
+ lhs, lhs_params = self.process_lhs(compiler, connection)
+ rhs, rhs_params = self.process_rhs(compiler, connection)
+ # Although combining via (*lhs_params, *rhs_params) would be
+ # more resilient, the "simple" way works too.
+ params = lhs_params + rhs_params
+ return "%s <> %s" % (lhs, rhs), params
+
+ author = Author.objects.create(name="Isabella")
+
+ with register_lookup(models.Field, NotEqual):
+ qs = Author.objects.annotate(
+ unknown_age=models.Subquery(
+ Author.objects.filter(age__isnull=True)
+ .order_by("name")
+ .values("name")[:1]
+ )
+ ).filter(unknown_age__ne="Plato")
+ self.assertSequenceEqual(qs, [author])
+
+ qs = Author.objects.annotate(
+ unknown_age=Lower(
+ Author.objects.filter(age__isnull=True)
+ .order_by("name")
+ .values("name")[:1]
+ )
+ ).filter(unknown_age__ne="plato")
+ self.assertSequenceEqual(qs, [author])
+
def test_custom_exact_lookup_none_rhs(self):
"""
__exact=None is transformed to __isnull=True if a custom lookup class