mirror of
https://github.com/encode/django-rest-framework.git
synced 2025-08-06 05:20:12 +03:00
Merge branch 'recursion'
This commit is contained in:
commit
9969dc0e68
|
@ -1269,6 +1269,7 @@ class HiddenField(Field):
|
|||
def to_internal_value(self, data):
|
||||
return data
|
||||
|
||||
|
||||
class RecursiveField(Field):
|
||||
"""
|
||||
A field that gets its representation from its parent.
|
||||
|
@ -1281,27 +1282,33 @@ class RecursiveField(Field):
|
|||
Above all, beware of cyclical references.
|
||||
|
||||
Examples:
|
||||
|
||||
|
||||
class TreeSerializer(self):
|
||||
children = ListField(child=RecursiveField())
|
||||
|
||||
class ListSerializer(self):
|
||||
next = RecursiveField(allow_null=True)
|
||||
next = RecursiveField()
|
||||
"""
|
||||
|
||||
def __init__(self, *args, **kwargs):
|
||||
kwargz = {'required': False}
|
||||
kwargz.update(kwargs)
|
||||
super(RecursiveField, self).__init__(*args, **kwargz)
|
||||
|
||||
def _get_parent(self):
|
||||
if hasattr(self.parent, 'child') and self.parent.child is self:
|
||||
# Recursive field nested inside of some kind of composite list field
|
||||
return self.parent.parent
|
||||
else:
|
||||
return self.parent
|
||||
|
||||
|
||||
def to_representation(self, value):
|
||||
return self._get_parent().to_representation(value)
|
||||
|
||||
def to_internal_value(self, data):
|
||||
return self._get_parent().to_internal_value(data)
|
||||
|
||||
|
||||
class SerializerMethodField(Field):
|
||||
"""
|
||||
A read-only field that get its representation from calling a method on the
|
||||
|
|
|
@ -313,7 +313,7 @@ class TestRecursiveField:
|
|||
'name': 'first',
|
||||
'next': {
|
||||
'name': 'second',
|
||||
'next':{
|
||||
'next': {
|
||||
'name': 'third',
|
||||
'next': None,
|
||||
}
|
||||
|
@ -328,17 +328,17 @@ class TestRecursiveField:
|
|||
# test deserialization
|
||||
serializer = self.link_serializer(data=value)
|
||||
assert serializer.is_valid(), \
|
||||
'cannot validate on deserialization'
|
||||
'cannot validate on deserialization: %s' % dict(serializer.errors)
|
||||
assert serializer.validated_data == value, \
|
||||
'deserialized data does not match input'
|
||||
|
||||
def test_node_serializer(self):
|
||||
value = {
|
||||
'name': 'root',
|
||||
'name': 'root',
|
||||
'children': [{
|
||||
'name': 'first child',
|
||||
'children': [],
|
||||
},{
|
||||
}, {
|
||||
'name': 'second child',
|
||||
'children': [],
|
||||
}]
|
||||
|
@ -350,9 +350,9 @@ class TestRecursiveField:
|
|||
'serialized data does not match input'
|
||||
|
||||
# deserialization
|
||||
serializer = self.link_serializer(data=value)
|
||||
serializer = self.node_serializer(data=value)
|
||||
assert serializer.is_valid(), \
|
||||
'cannot validate on deserialization'
|
||||
'cannot validate on deserialization: %s' % dict(serializer.errors)
|
||||
assert serializer.validated_data == value, \
|
||||
'deserialized data does not match input'
|
||||
|
||||
|
|
Loading…
Reference in New Issue
Block a user