From 1155843a41af589a856efe8e671a796866430049 Mon Sep 17 00:00:00 2001 From: Marti Raudsepp Date: Thu, 5 Nov 2015 19:02:18 +0200 Subject: [PATCH] Fixed #25683 -- Allowed ModelChoiceField(queryset=...) to accept Managers. This fixes a regression from refs #25496. --- django/forms/models.py | 6 ++++-- docs/releases/1.8.7.txt | 4 ++++ tests/forms_tests/tests/tests.py | 14 ++++++++++---- 3 files changed, 18 insertions(+), 6 deletions(-) diff --git a/django/forms/models.py b/django/forms/models.py index 938535bf6a..8c0f2e97a6 100644 --- a/django/forms/models.py +++ b/django/forms/models.py @@ -1102,9 +1102,11 @@ class ModelChoiceIterator(object): def __iter__(self): if self.field.empty_label is not None: yield ("", self.field.empty_label) + queryset = self.queryset.all() # Can't use iterator() when queryset uses prefetch_related() - method = 'all' if self.queryset._prefetch_related_lookups else 'iterator' - for obj in getattr(self.queryset, method)(): + if not queryset._prefetch_related_lookups: + queryset = queryset.iterator() + for obj in queryset: yield self.choice(obj) def __len__(self): diff --git a/docs/releases/1.8.7.txt b/docs/releases/1.8.7.txt index f3cfc8e046..9e8f37f120 100644 --- a/docs/releases/1.8.7.txt +++ b/docs/releases/1.8.7.txt @@ -14,3 +14,7 @@ Bugfixes * Fixed a regression in 1.8.6 that caused database routers without an ``allow_migrate()`` method to crash (:ticket:`25686`). + +* Fixed a regression in 1.8.6 by restoring the ability to use ``Manager`` + objects for the ``queryset`` argument of ``ModelChoiceField`` + (:ticket:`25683`). diff --git a/tests/forms_tests/tests/tests.py b/tests/forms_tests/tests/tests.py index b3a1cd1f1d..74005ce6fe 100644 --- a/tests/forms_tests/tests/tests.py +++ b/tests/forms_tests/tests/tests.py @@ -60,17 +60,23 @@ class FileForm(Form): file1 = FileField() -class TestTicket12510(TestCase): - ''' It is not necessary to generate choices for ModelChoiceField (regression test for #12510). ''' - def setUp(self): - self.groups = [Group.objects.create(name=name) for name in 'abc'] +class TestModelChoiceField(TestCase): def test_choices_not_fetched_when_not_rendering(self): + """ + Generating choices for ModelChoiceField should require 1 query (#12510). + """ + self.groups = [Group.objects.create(name=name) for name in 'abc'] # only one query is required to pull the model from DB with self.assertNumQueries(1): field = ModelChoiceField(Group.objects.order_by('-name')) self.assertEqual('a', field.clean(self.groups[0].pk).name) + def test_queryset_manager(self): + f = ModelChoiceField(ChoiceOptionModel.objects) + choice = ChoiceOptionModel.objects.create(name="choice 1") + self.assertEqual(list(f.choices), [('', '---------'), (choice.pk, str(choice))]) + class TestTicket14567(TestCase): """