There are examples how to create a writable nested serializer like this and then how to serialize a generic foreign key (here).
But I cannot find how to do both at the same time, i.e how to create a nested writable serializer for a generic foreign key field.
In my models there is a Meeting model with a GenericForeignKey which can be either DailyMeeting or WeeklyMeeting like:
class Meeting(models.Model):
# More fields above
content_type = models.ForeignKey(ContentType, on_delete=models.CASCADE)
object_id = models.PositiveIntegerField()
recurring_meeting = GenericForeignKey('content_type', 'object_id')
class DailyMeeting(models.Model):
meeting = GenericRelation(Meeting)
# more fields
class WeeklyMeeting(models.Model):
meeting = GenericRelation(Meeting)
# more fields
Then I created a custom field in my serializers.py:
class RecurringMeetingRelatedField(serializers.RelatedField):
def to_representation(self, value):
if isinstance(value, DailyMeeting):
serializer = DailyMeetingSerializer(value)
elif isinstance(value, WeeklyMeeting):
serializer = WeeklyMeetingSerializer(value)
else:
raise Exception('Unexpected type of tagged object')
return serializer.data
class MeetingSerializer(serializers.ModelSerializer):
recurring_meeting = RecurringMeetingRelatedField()
class Meta:
model = Meeting
fields = '__all__'
I am passing a JSON which looks like:
{
"start_time": "2017-11-27T18:50:00",
"end_time": "2017-11-27T21:30:00",
"subject": "Test now",
"moderators": [41],
"recurring_meeting":{
"interval":"daily",
"repetitions": 10,
"weekdays_only": "True"
}
}
But the problem is that I am getting the following error:
AssertionError: Relational field must provide a
querysetargument, overrideget_queryset, or set read_only=True.
Why does the Relational field has to be read_only? If I set it as read_only then it is not passed in the data in the serializer.
And what type of queryset do I have to provide?
read_onlyread_onlythere is nothing in thevalidated_datapassed to thecreate()method. So, in this case the recurring_meeting is totally ignored.