From 036f160733fcceb10975bf03c2fc9ffd9c114612 Mon Sep 17 00:00:00 2001 From: Bob Renwick Date: Tue, 6 Oct 2020 10:04:11 +0000 Subject: [PATCH] Refs #20577 -- Deferred filtering of prefetched related querysets by reverse m2o relation. --- .../db/models/fields/related_descriptors.py | 1 + tests/prefetch_related/tests.py | 21 +++++++++++-------- 2 files changed, 13 insertions(+), 9 deletions(-) diff --git a/django/db/models/fields/related_descriptors.py b/django/db/models/fields/related_descriptors.py index 7ade10ca6e9..872a4c98dc6 100644 --- a/django/db/models/fields/related_descriptors.py +++ b/django/db/models/fields/related_descriptors.py @@ -581,6 +581,7 @@ def create_reverse_many_to_one_manager(superclass, rel): queryset._add_hints(instance=self.instance) if self._db: queryset = queryset.using(self._db) + queryset._defer_next_filter = True queryset = queryset.filter(**self.core_filters) for field in self.field.foreign_related_fields: val = getattr(self.instance, field.attname) diff --git a/tests/prefetch_related/tests.py b/tests/prefetch_related/tests.py index 740e9cb1b58..c368e040eaf 100644 --- a/tests/prefetch_related/tests.py +++ b/tests/prefetch_related/tests.py @@ -294,17 +294,20 @@ class PrefetchRelatedTests(TestDataMixin, TestCase): def test_filter_deferred(self): """ - Related filtering of prefetched querysets is deferred until necessary. + Related filtering of prefetched querysets is deferred on m2m and + reverse m2o relations until necessary. """ add_q = Query.add_q - with mock.patch.object( - Query, - 'add_q', - autospec=True, - side_effect=lambda self, q: add_q(self, q), - ) as add_q_mock: - list(Book.objects.prefetch_related('authors')) - self.assertEqual(add_q_mock.call_count, 1) + for relation in ['authors', 'first_time_authors']: + with self.subTest(relation=relation): + with mock.patch.object( + Query, + 'add_q', + autospec=True, + side_effect=lambda self, q: add_q(self, q), + ) as add_q_mock: + list(Book.objects.prefetch_related(relation)) + self.assertEqual(add_q_mock.call_count, 1) class RawQuerySetTests(TestDataMixin, TestCase):