代码之家  ›  专栏  ›  技术社区  ›  Kim Stacks

如何创建与模型类中的put和executes函数相对应的自定义操作端点?

  •  1
  • Kim Stacks  · 技术社区  · 7 年前

    Am使用Django Rest框架:v3.7和Django v1.11以及Dynamic Rest v1.9.2

    我的MyModel类中包含以下内容:

    class MyModel():
        # .. fields declared here..
    
        def change_status(self):
            #... other code not crucial
            allowed = self.status in possible_new_states
            if allowed:
                return self.save()
            return True
    

    我有以下视图集

    from dynamic_rest.viewsets import DynamicModelViewSet
    # from rest_framework.decorators import action # for DRF 3.8
    from rest_framework.decorators import detail_route # for DRF 3.7
    from rest_framework.permissions import IsAuthenticated
    from rest_framework.response import Response
    
    class MyModelViewSet(DynamicModelViewSet):
        """
        VendorQuotations API.
        """
        permission_classes = (IsAuthenticated,)
        queryset = MyModel.objects.all()
        serializer_class = MyModelSerializer
    
        @detail_route(methods=['put']) # use this for DRF 3.7
        # @action(detail=True, methods=['put']) # use this for DRF 3.8 and above
        def status(self, request, pk=None):
            """Update the status."""
    

    和以下序列化程序:

    class VendorQuotationSerializer(DynamicModelSerializer):
    

    这个 DynamicModelSerializer 继承自 serializers.ModelSerializer 和 DyanmicModelViewSet 继承自 viewsets.ModelViewSet

    我希望有一个像/my_models/:id/change_status这样的端点指向 status 方法,然后以某种方式执行 change_status 方法在模型级别。

    change_password 但我不知道如何连接视图集和模型之间的点。

    请告知

    2 回复  |  直到 7 年前
        1
  •  2
  •   ruddra    7 年前

    您可以这样尝试:

    from rest_framework.response import Response
    from rest_framework import status, viewsets
    ...
    
    @action(detail=True, methods=['put'], name='Change Status',  url_path='change-status', url_name='change_status')
    def status(self, request, pk):
        try:
           obj = MyModel.objects.get(pk=pk)
           changed_status = obj.change_status()
           return Response({'success':True, "status_changed": changed_status}, status=status.HTTP_200_OK)
        except MyModel.DoesNotExists:
           return Response({'success':False}, status=status.HTTP_400_BAD_REQUEST)
    
        2
  •  2
  •   Kim Stacks    7 年前

    @ruddra的答案很好,但是您应该使用现有的 get_object() 已处理的方法 404

    from rest_framework import status
    
    # from rest_framework.decorators import action # for DRF 3.8
    from rest_framework.decorators import detail_route # for DRF 3.7
    
    @detail_route(methods=['put']) # use this for DRF 3.7
    # @action(detail=True, methods=['put']) # use this for DRF 3.8 and above
    def status(self, request, pk):
       obj = self.get_object()
       changed_status = obj.change_status()
       return Response({'success':True, "status_changed": changed_status},status=status.HTTP_200_OK) 
    
    推荐文章