summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--django/db/models/sql/query.py9
-rw-r--r--docs/releases/3.0.7.txt4
-rw-r--r--tests/annotations/tests.py20
3 files changed, 31 insertions, 2 deletions
diff --git a/django/db/models/sql/query.py b/django/db/models/sql/query.py
index 638161afc2..329a6e16c0 100644
--- a/django/db/models/sql/query.py
+++ b/django/db/models/sql/query.py
@@ -2141,6 +2141,15 @@ class Query(BaseExpression):
# SELECT clause which is about to be cleared.
self.set_group_by(allow_aliases=False)
self.clear_select_fields()
+ elif self.group_by:
+ # Resolve GROUP BY annotation references if they are not part of
+ # the selected fields anymore.
+ group_by = []
+ for expr in self.group_by:
+ if isinstance(expr, Ref) and expr.refs not in field_names:
+ expr = self.annotations[expr.refs]
+ group_by.append(expr)
+ self.group_by = tuple(group_by)
self.values_select = tuple(field_names)
self.add_fields(field_names, True)
diff --git a/docs/releases/3.0.7.txt b/docs/releases/3.0.7.txt
index 9fc71d9aa2..5457e59b3d 100644
--- a/docs/releases/3.0.7.txt
+++ b/docs/releases/3.0.7.txt
@@ -11,3 +11,7 @@ Bugfixes
* Fixed a regression in Django 3.0 by restoring the ability to use field
lookups in ``Meta.ordering`` (:ticket:`31538`).
+
+* Fixed a regression in Django 3.0 where ``QuerySet.values()`` and
+ ``values_list()`` crashed if a queryset contained an aggregation and a
+ subquery annotation (:ticket:`31566`).
diff --git a/tests/annotations/tests.py b/tests/annotations/tests.py
index c39e8d3fbe..0cdc9178b0 100644
--- a/tests/annotations/tests.py
+++ b/tests/annotations/tests.py
@@ -1,10 +1,13 @@
import datetime
from decimal import Decimal
+from unittest import skipIf
from django.core.exceptions import FieldDoesNotExist, FieldError
+from django.db import connection
from django.db.models import (
- BooleanField, CharField, Count, DateTimeField, ExpressionWrapper, F, Func,
- IntegerField, NullBooleanField, OuterRef, Q, Subquery, Sum, Value,
+ BooleanField, CharField, Count, DateTimeField, Exists, ExpressionWrapper,
+ F, Func, IntegerField, Max, NullBooleanField, OuterRef, Q, Subquery, Sum,
+ Value,
)
from django.db.models.expressions import RawSQL
from django.db.models.functions import Length, Lower
@@ -619,3 +622,16 @@ class NonAggregateAnnotationTestCase(TestCase):
total_books=Subquery(long_books_qs, output_field=IntegerField()),
).values('name')
self.assertCountEqual(publisher_books_qs, [{'name': 'Sams'}, {'name': 'Morgan Kaufmann'}])
+
+ @skipIf(connection.vendor == 'oracle', 'See https://code.djangoproject.com/ticket/31584')
+ def test_annotation_exists_aggregate_values_chaining(self):
+ qs = Book.objects.values('publisher').annotate(
+ has_authors=Exists(Book.authors.through.objects.filter(book=OuterRef('pk'))),
+ max_pubdate=Max('pubdate'),
+ ).values_list('max_pubdate', flat=True).order_by('max_pubdate')
+ self.assertCountEqual(qs, [
+ datetime.date(1991, 10, 15),
+ datetime.date(2008, 3, 3),
+ datetime.date(2008, 6, 23),
+ datetime.date(2008, 11, 3),
+ ])