Django.rest_framework: How to serialize one to many to many?
django, django-queryset, django-rest-framework, python, serialization
Solution
If I'm understanding you correctly, you want the `SchoolSerializer` to return a nested structure 2 levels deep, but skipping the intermediate model. To do this, I would create a method in your `School` model to retrieve the `Desk` instances:
class School(models.Model):
...
def get_desks(self):
rooms = Room.objects.filter(school=self)
desks = Desk.objects.filter(room__in=rooms)
return desks
Then, in your `SchoolSerializer` include a field that uses that method and renders the returned instances as you wish via your `DeskSerializer`:
class SchoolSerializer(serializers.ModelSerializer):
...
desks = DeskSerializer(
source='get_desks',
read_only=True
)
class Meta:
field = (name, desks)
The key to understanding how this works is that the model method used as the value for the `source` argument must simply return instances of that serializer's model. The serializer takes it from there, rendering the object(s) however you defined them within that serializer (in this case the `DeskSerializer`).
Hope this helps.
Problem
I have some troubles serializing with django. I have three models, let's say a School, a Room and a Desk (dummy name for example). Each School have multiple Room, and each Room have multiple Desk. The classes and their relations look like this : ``` class School(models.Model): name = models.CharField() class Room(models.Model): name = models.CharField() school_id = models.ForeignKey(School) class Desk(models.Model): row = models.IntegerField() col = models.IntegerField() room_id = models.ForeignKey(Room) ``` I want to be able to serialize a list of School, each directly containing all the desks inside. The closet I got was by writing in my serialize.py three serializer : ``` class DeskSerializer(serializers.ModelSerializer): class Meta: field = (row, col,) class RoomSerializer(serializers.ModelSerializer): desks = DeskSerializer(source='desk_set', many=True) class Meta: field = (desks,) class SchoolSerializer(serializers.ModelSerializer): rooms = RoomSerializer(source='room_set', many=True) class Meta: field = (name, rooms,) ``` Which return a list of school containing a list of room containing a list of desk, when I want a list of School containing a list of desk Which source should I use in the School serializer to return directly the desk? Something like source='room_set.desk_set'? Or maybe by using a transform_ function? PS: the code is write from scratch on the post, please ignore the possible syntax errors