我想澄清django-rest-framework
关于创建模型对象的给定文档。到目前为止,我发现有3种方法可以处理此类事件。
Serializer的create()
方法。这是documentation
class CommentSerializer(serializers.Serializer):
def create(self, validated_data):
return Comment.objects.create(**validated_data)
ModelViewset create()
方法。 Documentation
class AccountViewSet(viewsets.ModelViewSet):
queryset = Account.objects.all()
serializer_class = AccountSerializer
permission_classes = [IsAccountAdminOrReadOnly]
ModelViewset perform_create()
方法。 Documentation
class SnippetViewSet(viewsets.ModelViewSet):
def perform_create(self, serializer):
serializer.save(owner=self.request.user)
这三种方法很重要,具体取决于您的应用环境。
但是我们什么时候需要使用每个create() / perform_create()
函数?另一方面,我发现有一个帐户,即为单个帖子请求调用了两个创建方法,模型视图的create()
和序列化程序的create()
。
希望任何人都能分享他们的一些知识来解释,这对我的开发过程肯定会非常有帮助。
答案 0 :(得分:68)
SUMPRODUCT
将任何额外的详细信息添加到对象中,然后将“prod”值保存到每个模型字段中,就像create(self, validated_data)
一样。理想情况下,您希望仅在一个位置执行此类形式的“刺激”,因此**validated_data
中的create
方法是最佳位置。除此之外,您可能还想在将帐户保存到自己的数据库之前调用外部apis来创建用户帐户。您应该将此CommentSerializer
功能与create
结合使用。总是想 - “薄视图,厚序列化器”。示例:
ModelViewSet
def create(self, validated_data):
email = validated.data.get("email", None)
validated.pop("email")
# Now you have a clean valid email
# You might want to call an external API or modify another table
# (eg. keep track of number of accounts registered.) or even
# make changes to the email format.
# Once you are done, create the instance with the validated data
return models.YourModel.objects.create(email=email, **validated_data)
中的create(self, request, *args, **kwargs)
函数在ModelViewSet
类中定义,该类是CreateModelMixin
的父级。 ModelViewSet
的主要功能是:
CreateModelMixin
如您所见,上面的def create(self, request, *args, **kwargs):
serializer = self.get_serializer(data=request.data)
serializer.is_valid(raise_exception=True)
self.perform_create(serializer)
headers = self.get_success_headers(serializer.data)
return Response(serializer.data, status=status.HTTP_201_CREATED, headers=headers)
def perform_create(self, serializer):
serializer.save()
函数负责在序列化程序上调用验证并生成正确的响应。这背后的美妙之处在于,您现在可以隔离您的应用程序逻辑,而不关心平凡和重复的验证调用以及处理响应输出:)。这与在序列化程序中找到的create
(您的特定应用程序逻辑可能驻留在其中)相结合非常有效。
create(self, validated_data)
函数!?!?那么,这背后的主要原因是在调用perform_create(self, serializer)
函数时允许自定义。您可能希望在调用save
之前提供额外数据(例如save
,如果我们没有serializer.save(owner=self.request.user)
,则您必须覆盖{{1而这恰好击败了让mixin做重而枯燥的工作的目的。希望这有帮助!