patch()收到了意外的关键字参数

时间:2020-01-18 02:31:47

标签: python python-3.x http django-rest-framework

我正在尝试编写一个测试,其中使用patch更新对象。

class Search(models.Model):
    id_search = models.AutoField(primary_key=True)
    id_user = models.IntegerField(null=False)
    .
    .
    archive = models.BooleanField(default=False)
 def test_archive_search(self):

        user = User(id_user=75720912,
                    login='Client:75720912',
                )
        user.save()

        search = Search(
                        id_user=75720912,
                        .
                        .
                        archive=False
                )
        search.save()

        url = reverse('search-update', kwargs={'id_search':1})
        data = {'archive': True}
        response = self.client.patch(url, data, format='json')
        self.assertEqual(response.status_code, status.HTTP_201_CREATED)
url(r'^search-update/(?P<id_search>\d+)$', SearchUpdateView.as_view(), name='search-update')

class SearchUpdateView(generics.UpdateAPIView):
    serializer_class = SearchSerializer
    def get_object(self,id_search):
        return Search.objects.get(id_search=id_search)

    def patch(self, request):
        id_search = self.request.query_params.get('id_search', None)

        search_object = self.get_object(id_search=id_search)
        serializer = SearchSerializer(search_object, data=request.data, partial=True) 

        if serializer.is_valid():
            serializer.save()
            return Response(serializer.data, status=status.HTTP_201_CREATED)
        return Response(serializer.data, status=status.HTTP_400_BAD_REQUEST)

并收到此错误:

TypeError: patch() got an unexpected keyword argument 'id_search'

有趣的是,网址是:

url(r'^search-update/$', SearchUpdateView.as_view(), name='search-update')

SearchUpdateView在给定的查询参数下可以正常工作。

编辑

我发现在测试中将id_search传递到patch可以解决此问题,但会破坏工作视图。

class SearchUpdateView(generics.UpdateAPIView):
    serializer_class = SearchSerializer
    def get_object(self, id_search):
        return Search.objects.get(id_search=id_search)

    def patch(self, request, id_search):
        #id_search = self.request.query_params.get('id_search', None) 


        search_object = self.get_object(id_search=id_search)
        serializer = SearchSerializer(search_object, data=request.data, partial=True) 

        if serializer.is_valid():
            serializer.save()
            return Response(serializer.data, status=status.HTTP_201_CREATED)
        return Response(serializer.data, status=status.HTTP_400_BAD_REQUEST)

仍然我不知道如何将其组合在一起。

1 个答案:

答案 0 :(得分:2)

如果您以这种方式定义url,则补丁方法将获得id_search参数作为关键字参数,如错误所示。

相反,您将其作为查询参数来检索,即它不是URL路径的一部分,而是search-update?id_search=

鉴于您在获取None时将其作为默认值传递,因此在您省略时可以使用。

因此,选择要走的路。

如果url定义正确,则将id_search参数添加到patch方法的签名中 并删除手动检索它的代码。

或者按照上述注释中的建议,通过为参数指定默认值None并从请求中获取默认值(如果它不是路径的一部分)来实现两者