Метод создания сериализатора с many=True
У меня есть следующий сериализатор модели с методом create
.
class ActivatedCapacitySerializer(serializers.Serializer):
class Meta:
model = ActivatedCapacity
fields = '__all__'
def create(self, validated_data):
activated_capacity = ActivatedCapacity.objects.update_or_create(
user_id=validated_data['user_id'],
capacity_id=validated_data['capacity_id'],
defaults = {
'active': validated_data['active']
}
)
return activated_capacity
Models.py
class ActivatedCapacity(models.Model):
user_id = models.IntegerField()
capacity_id = models.IntegerField()
active = models.BooleanField(default=False)
Когда я пытаюсь создать экземпляры массово с помощью many=True
, у меня возникает ошибка KeyError: 'user_id'
.
Поскольку я использовал many=True
, подтвержденные данные сериализатора представляют собой список OrderedDict
, поэтому я должен итерировать этот список в методе create
для создания экземпляров? Разве Django Rest Framework не должен справиться с этим сам? Если да, то как мне это сделать?
Попробуйте изменить class ActivatedCapacitySerializer(serializers.Serializer):
на class ActivatedCapacitySerializer(serializers.ModelSerializer):
и проверьте.
Сериализатор используется так же, как и Form в обычном django. Способ, которым вы передаете сериализатор, задается как ModelSerializer с Meta.fields и Meta.model.
Для лучшего понимания вы можете посмотреть документацию здесь.
Теперь для метода create() вы можете попробовать следующий подход:
def create(self, validated_data):
activated_capacity = ActivatedCapacity.objects.update_or_create(**validated_data)
activated_capacity.active = True
return activated_capacity
У вас также могут возникнуть проблемы с подключением к соответствующей модели:
class ActivatedCapacity(models.Model):
"""
You also 'maight need' to point the corresponding model,
if you are trying to pass id from other object.
"""
user_id = models.ForeigKey(User, on_delete=models.CASCADE)
capacity_id = models.ForeigKey(Capacity, on_delete=models.CASCADE)
active = models.BooleanField(default=False)