问题描述
我的Django模型中有一个ItemCollection和Items,我希望能够通过UI从集合中删除Items。在REST PUT请求中,我为每个项目添加了一个额外的布尔字段已删除
,表示该项目应该被删除。
正确的处理方式似乎在Serializer的 我目前的示例代码如下。有没有人知道更好的方法? 模型: 序列化器: 另请参见PUT请求中的json示例: 您可以通过覆盖更新
方法中。
我的问题是,这个非模型删除的
字段在验证过程中被删除,所以它不再可用了。将删除
作为 SerializerMethodField
没有帮助。现在我从序列化器的 initial_data
属性中获取了我的删除的信息,但这不是正确的。 p>
class ItemCollection (models.Model):
description = models.CharField(max_length = 256)
类项目(models.Model):
collection = models.ForeignKey( ItemCollection,related_name =items)
_ pre> from django.shortcuts import get_object_or_404
from rest_framework.views import APIView
from rest_framework.response import Response
from rest_framework import serializers
从模型导入项目,ItemCollection
class ItemSerializer(serializers.ModelSerializer):
class Meta:
model = Item
class ItemCollectionSerializer(serializers.ModelSerializer):
items = ItemSerializer(many = True,read_only = False)
class Meta:
model = ItemCollection
def update(self,instance,validated_data):
instance.description = validated_data ['description']
for item,item_obj in zip(
self.initial_data ['items'],validated_data ['items']):
如果item ['delete']:
instance.items.filter(id = item ['id'])。delete()
return instance
class ItemCollectionView(APIView):
def get(self,request,ic_id):
item_collection = get_object_or_404(ItemCollection ,pk = ic_id)
serialized = ItemCollectionSerializer(item_collection).data
return响应(序列化)
def put(self,request,ic_id):
item_collection = get_object_or_404(ItemCollection,pk = ic_id)
serializer = ItemCollectionSerializer(
item_collection,data = request.data)
如果serializer.i s_valid(raise_exception = True):
serializer.save()
return响应(serializer.data)
{
id: 2,
items:[
{
id:3,
collection:2,
delete:true
}
],
description:mycoll
}
to_internal_value
fn:
添加非模型字段$ _ code> def to_internal_value(self,data):
internal_value = super(MySerializer,self).to_internal_value(data)
my_non_model_field_raw_value = data.get(my_non_model_field )
my_non_model_field_value = ConvertRawValueInSomeCleverWay(my_non_model_field_raw_value)
internal_value.update({
my_no n_model_field:my_non_model_field_value
})
return internal_value
然后你可以处理它但是您需要在创建
或更新
。
I have an ItemCollection and Items in my Django models and I want to be able to remove Items from the collection through the UI. In a REST PUT request I add an extra boolean field deleted
for each Item to signal that an Item should be deleted.
The correct way to handle this seems to be in the update
method of the Serializer.My problem is that this non-model deleted
field gets removed during validation, so it is not available anymore. Adding deleted
as a SerializerMethodField
did not help. For now I get my deleted
information from the initial_data
attribute of the Serializer, but that does not feel right.
My current example code is below. Does anybody know a better approach?
Models:
class ItemCollection(models.Model):
description = models.CharField(max_length=256)
class Item(models.Model):
collection = models.ForeignKey(ItemCollection, related_name="items")
Serializers:
from django.shortcuts import get_object_or_404
from rest_framework.views import APIView
from rest_framework.response import Response
from rest_framework import serializers
from models import Item, ItemCollection
class ItemSerializer(serializers.ModelSerializer):
class Meta:
model = Item
class ItemCollectionSerializer(serializers.ModelSerializer):
items = ItemSerializer(many=True, read_only=False)
class Meta:
model = ItemCollection
def update(self, instance, validated_data):
instance.description = validated_data['description']
for item, item_obj in zip(
self.initial_data['items'], validated_data['items']):
if item['delete']:
instance.items.filter(id=item['id']).delete()
return instance
class ItemCollectionView(APIView):
def get(self, request, ic_id):
item_collection = get_object_or_404(ItemCollection, pk=ic_id)
serialized = ItemCollectionSerializer(item_collection).data
return Response(serialized)
def put(self, request, ic_id):
item_collection = get_object_or_404(ItemCollection, pk=ic_id)
serializer = ItemCollectionSerializer(
item_collection, data=request.data)
if serializer.is_valid(raise_exception=True):
serializer.save()
return Response(serializer.data)
And an example of the json in the PUT request:
{
"id": 2,
"items": [
{
"id": 3,
"collection": 2,
"delete": true
}
],
"description": "mycoll"
}
You can add non-model fields back by overwriting the to_internal_value
fn:
def to_internal_value(self, data):
internal_value = super(MySerializer, self).to_internal_value(data)
my_non_model_field_raw_value = data.get("my_non_model_field")
my_non_model_field_value = ConvertRawValueInSomeCleverWay(my_non_model_field_raw_value)
internal_value.update({
"my_non_model_field": my_non_model_field_value
})
return internal_value
Then you can process it however you want in create
or update
.
这篇关于无法在Django Rest Framework序列化程序的validated_data中获取非模型字段的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!