[4.0.x] Fixed #33130 -- Restored form errors to be a dict.

Regression in 456466d932.

Backport of 7fe9b6f6df from main
This commit is contained in:
Jaap Roes 2021-09-22 13:28:49 +02:00 committed by Mariusz Felisiak
parent 5d36af6f6f
commit 25cfa5db0f
3 changed files with 51 additions and 4 deletions

View File

@ -1,5 +1,5 @@
import json
from collections import UserDict, UserList
from collections import UserList
from django.conf import settings
from django.core.exceptions import ValidationError
@ -84,7 +84,7 @@ class RenderableErrorMixin(RenderableMixin):
return self.render(self.template_name_ul)
class ErrorDict(UserDict, RenderableErrorMixin):
class ErrorDict(dict, RenderableErrorMixin):
"""
A collection of errors that knows how to display itself in various formats.
@ -94,8 +94,8 @@ class ErrorDict(UserDict, RenderableErrorMixin):
template_name_text = 'django/forms/errors/dict/text.txt'
template_name_ul = 'django/forms/errors/dict/ul.html'
def __init__(self, data=None, renderer=None):
super().__init__(data)
def __init__(self, *args, renderer=None, **kwargs):
super().__init__(*args, **kwargs)
self.renderer = renderer or get_default_renderer()
def as_data(self):

View File

@ -67,6 +67,7 @@ class FormsTestCase(SimpleTestCase):
self.assertTrue(p.is_bound)
self.assertEqual(p.errors, {})
self.assertIsInstance(p.errors, dict)
self.assertTrue(p.is_valid())
self.assertHTMLEqual(p.errors.as_ul(), '')
self.assertEqual(p.errors.as_text(), '')

View File

@ -1,4 +1,5 @@
import copy
import json
from django.core.exceptions import ValidationError
from django.forms.utils import ErrorDict, ErrorList, flatatt
@ -162,3 +163,48 @@ class FormsUtilsTestCase(SimpleTestCase):
e = ErrorList(['Invalid username.'])
self.assertTrue(hasattr(ErrorList, '__html__'))
self.assertEqual(str(e), e.__html__())
def test_error_dict_is_dict(self):
self.assertIsInstance(ErrorDict(), dict)
def test_error_dict_is_json_serializable(self):
init_errors = ErrorDict([
('__all__', ErrorList([
ValidationError('Sorry this form only works on leap days.')
])),
('name', ErrorList([ValidationError('This field is required.')])),
])
min_value_error_list = ErrorList([
ValidationError('Ensure this value is greater than or equal to 0.')
])
e = ErrorDict(
init_errors,
date=ErrorList([
ErrorDict({
'day': min_value_error_list,
'month': min_value_error_list,
'year': min_value_error_list,
}),
]),
)
e['renderer'] = ErrorList([
ValidationError(
'Select a valid choice. That choice is not one of the '
'available choices.'
),
])
self.assertJSONEqual(json.dumps(e), {
'__all__': ['Sorry this form only works on leap days.'],
'name': ['This field is required.'],
'date': [
{
'day': ['Ensure this value is greater than or equal to 0.'],
'month': ['Ensure this value is greater than or equal to 0.'],
'year': ['Ensure this value is greater than or equal to 0.'],
},
],
'renderer': [
'Select a valid choice. That choice is not one of the '
'available choices.'
],
})