Fixed #30583 -- Fixed handling JSONFields in XML serializer.
Co-authored-by: Chason Chaffin <chason@gmail.com>
This commit is contained in:
parent
82da72b748
commit
47651eadb8
|
@ -1,7 +1,7 @@
|
||||||
"""
|
"""
|
||||||
XML serializer.
|
XML serializer.
|
||||||
"""
|
"""
|
||||||
|
import json
|
||||||
from xml.dom import pulldom
|
from xml.dom import pulldom
|
||||||
from xml.sax import handler
|
from xml.sax import handler
|
||||||
from xml.sax.expatreader import ExpatParser as _ExpatParser
|
from xml.sax.expatreader import ExpatParser as _ExpatParser
|
||||||
|
@ -75,8 +75,13 @@ class Serializer(base.Serializer):
|
||||||
|
|
||||||
# Get a "string version" of the object's data.
|
# Get a "string version" of the object's data.
|
||||||
if getattr(obj, field.name) is not None:
|
if getattr(obj, field.name) is not None:
|
||||||
|
value = field.value_to_string(obj)
|
||||||
|
if field.get_internal_type() == 'JSONField':
|
||||||
|
# Dump value since JSONField.value_to_string() doesn't output
|
||||||
|
# strings.
|
||||||
|
value = json.dumps(value, cls=field.encoder)
|
||||||
try:
|
try:
|
||||||
self.xml.characters(field.value_to_string(obj))
|
self.xml.characters(value)
|
||||||
except UnserializableContentError:
|
except UnserializableContentError:
|
||||||
raise ValueError("%s.%s (pk:%s) contains unserializable characters" % (
|
raise ValueError("%s.%s (pk:%s) contains unserializable characters" % (
|
||||||
obj.__class__.__name__, field.name, obj.pk))
|
obj.__class__.__name__, field.name, obj.pk))
|
||||||
|
@ -232,6 +237,9 @@ class Deserializer(base.Deserializer):
|
||||||
value = None
|
value = None
|
||||||
else:
|
else:
|
||||||
value = field.to_python(getInnerText(field_node).strip())
|
value = field.to_python(getInnerText(field_node).strip())
|
||||||
|
# Load value since JSONField.to_python() outputs strings.
|
||||||
|
if field.get_internal_type() == 'JSONField':
|
||||||
|
value = json.loads(value, cls=field.decoder)
|
||||||
data[field.name] = value
|
data[field.name] = value
|
||||||
|
|
||||||
obj = base.build_instance(Model, data, self.db)
|
obj = base.build_instance(Model, data, self.db)
|
||||||
|
|
|
@ -149,6 +149,21 @@ class TestSerialization(SimpleTestCase):
|
||||||
)[0].object
|
)[0].object
|
||||||
self.assertEqual(instance.value, value)
|
self.assertEqual(instance.value, value)
|
||||||
|
|
||||||
|
def test_xml_serialization(self):
|
||||||
|
test_xml_data = (
|
||||||
|
'<django-objects version="1.0">'
|
||||||
|
'<object model="model_fields.nullablejsonmodel">'
|
||||||
|
'<field name="value" type="JSONField">%s'
|
||||||
|
'</field></object></django-objects>'
|
||||||
|
)
|
||||||
|
for value, serialized in self.test_values:
|
||||||
|
with self.subTest(value=value):
|
||||||
|
instance = NullableJSONModel(value=value)
|
||||||
|
data = serializers.serialize('xml', [instance], fields=['value'])
|
||||||
|
self.assertXMLEqual(data, test_xml_data % serialized)
|
||||||
|
new_instance = list(serializers.deserialize('xml', data))[0].object
|
||||||
|
self.assertEqual(new_instance.value, instance.value)
|
||||||
|
|
||||||
|
|
||||||
@skipUnlessDBFeature('supports_json_field')
|
@skipUnlessDBFeature('supports_json_field')
|
||||||
class TestSaveLoad(TestCase):
|
class TestSaveLoad(TestCase):
|
||||||
|
|
Loading…
Reference in New Issue