summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorJon Dufresne <jon.dufresne@gmail.com>2017-01-31 06:41:51 -0800
committerTim Graham <timograham@gmail.com>2017-01-31 09:41:51 -0500
commit6d8979f4c2fbfb9fd5db92acd72489cbbcbdd5d1 (patch)
tree3f372d8c32e3a0396536783ae920399ca5859f2e
parent3b2e28fc85c26dc50d4cc16b7c586f7f0994f752 (diff)
Fixed #27758 -- Reallowed AdvancedModelIterator pattern after template widget rendering.
-rw-r--r--django/forms/widgets.py4
-rw-r--r--tests/model_forms/tests.py37
2 files changed, 38 insertions, 3 deletions
diff --git a/django/forms/widgets.py b/django/forms/widgets.py
index eef90a3bd4..c32653a245 100644
--- a/django/forms/widgets.py
+++ b/django/forms/widgets.py
@@ -552,8 +552,6 @@ class ChoiceWidget(Widget):
for option_value, option_label in chain(self.choices):
if option_value is None:
option_value = ''
- else:
- option_value = force_text(option_value)
if isinstance(option_label, (list, tuple)):
index = groups[-1][2] + 1
@@ -569,7 +567,7 @@ class ChoiceWidget(Widget):
for subvalue, sublabel in choices:
selected = (
- subvalue in value and
+ force_text(subvalue) in value and
(has_selected is False or self.allow_multiple_selected)
)
if selected is True and has_selected is False:
diff --git a/tests/model_forms/tests.py b/tests/model_forms/tests.py
index 9dd8e79513..afe94890c3 100644
--- a/tests/model_forms/tests.py
+++ b/tests/model_forms/tests.py
@@ -15,6 +15,7 @@ from django.forms.models import (
ModelChoiceIterator, ModelFormMetaclass, construct_instance,
fields_for_model, model_to_dict, modelform_factory,
)
+from django.forms.widgets import CheckboxSelectMultiple
from django.template import Context, Template
from django.test import SimpleTestCase, TestCase, skipUnlessDBFeature
@@ -1704,6 +1705,42 @@ class ModelChoiceFieldTests(TestCase):
field = CustomModelChoiceField(Category.objects.all())
self.assertIsInstance(field.choices, CustomModelChoiceIterator)
+ def test_modelchoicefield_iterator_pass_model_to_widget(self):
+ class CustomModelChoiceValue:
+ def __init__(self, value, obj):
+ self.value = value
+ self.obj = obj
+
+ def __str__(self):
+ return str(self.value)
+
+ class CustomModelChoiceIterator(ModelChoiceIterator):
+ def choice(self, obj):
+ value, label = super().choice(obj)
+ return CustomModelChoiceValue(value, obj), label
+
+ class CustomCheckboxSelectMultiple(CheckboxSelectMultiple):
+ def create_option(self, name, value, label, selected, index, subindex=None, attrs=None):
+ option = super().create_option(name, value, label, selected, index, subindex=None, attrs=None)
+ # Modify the HTML based on the object being rendered.
+ c = value.obj
+ option['attrs']['data-slug'] = c.slug
+ return option
+
+ class CustomModelMultipleChoiceField(forms.ModelMultipleChoiceField):
+ iterator = CustomModelChoiceIterator
+ widget = CustomCheckboxSelectMultiple
+
+ field = CustomModelMultipleChoiceField(Category.objects.all())
+ self.assertHTMLEqual(
+ field.widget.render('name', []),
+ '''<ul>
+<li><label><input type="checkbox" name="name" value="%d" data-slug="entertainment" />Entertainment</label></li>
+<li><label><input type="checkbox" name="name" value="%d" data-slug="its-test" />It&#39;s a test</label></li>
+<li><label><input type="checkbox" name="name" value="%d" data-slug="third-test" />Third</label></li>
+</ul>''' % (self.c1.pk, self.c2.pk, self.c3.pk),
+ )
+
def test_modelchoicefield_num_queries(self):
"""
Widgets that render multiple subwidgets shouldn't make more than one