Как сериализовать абстрактные базовые модели и подмодели в REST-фреймворке Django
У меня есть модель Complaint, которая может иметь множество Evidence.
Модель Evidence может быть Attachment или Link и является абстрактной базовой моделью .
from django.db import models
class Complaint(models.Model):
text = models.TextField()
class Evidence(models.Model):
complaint = models.ForeignKey(
Complaint,
related_name='%(class)s_evidences',
on_delete=models.CASCADE
)
is_attached = models.BooleanField()
class Meta:
abstract = True
class Attachment(Evidence):
file = models.FileField(upload_to='attachments')
class Link(Evidence):
url = models.URLField()
Я хочу иметь возможность принимать входные данные Complaint и все его Evidence из одного представления следующим образом:
{
"text": "Lorem ipsum",
"evidences": [
{
"description": "dolor sit amet",
"is_attached": false,
"url": "https://example.com"
},
{
"description": "consectetur adipisicing elit",
"is_attached": true,
"file": "http://localhost:8000/media/attachments/filename"
}
]
}
Вот что у меня есть в моем serializers.py на данный момент:
from rest_framework import serializers
from .models import Complaint, Evidence, Attachment, Link
class EvidenceSerializer(serializers.Serializer): # since ModelSerializer can not be used with abstract models
id = serializers.IntegerField(read_only=True)
is_attached = serializers.BooleanField()
class Meta:
abstract = True
model = Evidence
fields = ['id', 'is_attached']
class AttachmentSerializer(EvidenceSerializer, serializers.ModelSerializer):
class Meta:
model = Attachment
fields = EvidenceSerializer.Meta.fields + ['file']
class LinkSerializer(EvidenceSerializer, serializers.ModelSerializer):
class Meta:
model = Link
fields = EvidenceSerializer.Meta.fields + ['url']
class ComplaintSerializer(serializers.ModelSerializer):
evidences = EvidenceSerializer(many=True)
class Meta:
model = Complaint
fields = ['id', 'text', 'evidences']
При запросе к представлению жалобы POST (/lodge) возникает следующая ошибка:
TypeError at /lodge
Got a `TypeError` when calling `Complaint.objects.create()`. This may be because you have a writable field on the serializer class that is not a valid argument to `Complaint.objects.create()`. You may need to make the field read-only, or override the ComplaintSerializer.create() method to handle this correctly.
Внизу трассировки:
TypeError: Complaint() got an unexpected keyword argument 'evidences'
Как мне написать сериализаторы для этих моделей?
В сообщении об ошибке говорится о необходимости переопределить Complaint.objects.create, но я не знаю, как это сделать.
Я пытался следовать примеру, приведенному для записываемых вложенных сериализаторов в официальной документации, но он не использует абстрактные модели.