DRF:将附加信息注入request.data的通用方法

时间:2019-02-16 17:07:42

标签: django django-rest-framework django-rest-viewsets

我处于一个端点samples可以通过sample代表模型ModelViewSet的情况。

我的目标是,当用户通过该数据向该端点发送POST

喜欢

{
    "a":1,
    "b":2 ,
    "c":3
}

我希望能够在request.data方法中将key:value对覆盖/添加到存储在create中的此传入有效载荷中。

这不能通过简单地访问request.data来完成,因为它是不可更改的QueryDict

此外,由于我可能注入的数据对于验证至关重要,因此我无法在perform_create()方法中实现这一目标。

目前,我坚持使用以下解决方案,该解决方案要求我重写完整的create()方法:

class MyViewSet(viewsets.ModelViewSet):
    queryset = Sample.objects.all()
    serializer_class = MSampleSerializer
    name = "samples"

    def add_info(self, request):
        ...
        <acquire_info>
        ...
        data = request.data.dict()
        data["s"] = <info1>
        data["r"] = <info1>
        data["t"] = <info1>
        return data


    def create(self, request, *args, **kwargs):
        data = self.add_info(request)
        serializer = self.get_serializer(data=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
        )
  1. 在称为request.datacreate()的任何操作方法之前,是否有一种通用的方法来编辑put()

  2. 如果不是1.);有其他可能性吗?

谢谢。

1 个答案:

答案 0 :(得分:1)

如果不想每次都重写整个视图,则可以使用序列化器的.to_representation().to_internal_value()方法。

并且由于您也想验证数据,因此.to_representation()可能是解决问题的方法。

从文档中

  

如果您需要更改序列化程序类的序列化或反序列化行为,则可以通过重写.to_representation().to_internal_value()方法来实现。

     

.to_representation(self, obj)接受需要序列化的对象实例,并且应返回原始表示形式。通常,这意味着返回内置Python数据类型的结构。可以处理的确切类型取决于您为API配置的呈现类。

示例:

def to_representation(self, instance):
    """Convert `username` to lowercase."""
    ret = super().to_representation(instance)
    ret['username'] = ret['username'].lower()
    return ret

请参见Advanced serializer usage: Overriding serialization and deserialization behavior

相关问题