Django rest 框架 - 调用另一个基于类的视图

bla*_*fci 5 django django-views django-rest-framework

我仔细研究了几篇类似的帖子(并且从同一项目中的另一个应用程序调用基于类的应用程序视图似乎很有希望,但不起作用),但有些帖子较旧,对我来说没有什么用。这是我的设置(使用 Django==2.0.6,djangorestframework==3.8.2)

我有一个基本模型(此处简化):

from django.db import models
class Resource(models.Model):
    name = models.CharField(max_length=100, null=False)
Run Code Online (Sandbox Code Playgroud)

我有一个基本端点,可以在其中列出和创建Resource实例:

from rest_framework import generics, permissions
from myapp.models import Resource
from myapp.serializers import ResourceSerializer

class ListAndCreateResource(generics.ListCreateAPIView):
    queryset = Resource.objects.all()
    serializer_class = ResourceSerializer
    permission_classes = (permissions.IsAuthenticated,)
Run Code Online (Sandbox Code Playgroud)

(afaik,序列化程序的细节不相关,因此被忽略了)。

无论如何,除了那个基本端点之外,我还有另一个 API 端点,它执行一些操作,但也在Resource这个过程中创建一些对象。当然,我想利用ListAndCreateResource类中封装的功能,所以我只需要维护一个Resource创建s的地方。

我试过了:

尝试 1:

class SomeOtherView(generics.CreateAPIView):
    def post(self, request, *args, **kwargs):
        # ... some other functionality...
        # ...
        response = ListAndCreateResource().post(request, *args, **kwargs)
        # ... more functionality...
        return Response({'message': 'ok'})
Run Code Online (Sandbox Code Playgroud)

不幸的是,这对我不起作用。在我的跟踪中,我得到:

  File "/home/projects/venv/lib/python3.5/site-packages/rest_framework/generics.py", line 111, in get_serializer
    kwargs['context'] = self.get_serializer_context()
  File "/home/projects/venv/lib/python3.5/site-packages/rest_framework/generics.py", line 137, in get_serializer_context
    'request': self.request,
AttributeError: 'ListAndCreateResource' object has no attribute 'request'
Run Code Online (Sandbox Code Playgroud)

尝试 2:此尝试尝试使用as_view属于所有基于 Django 类的视图的方法:

class SomeOtherView(generics.CreateAPIView):
    def post(self, request, *args, **kwargs):
        # ... some other functionality...
        # ...
        response = ListAndCreateResource.as_view()(request, *args, **kwargs)
        # ... more functionality...
        return Response({'message': 'ok'})
Run Code Online (Sandbox Code Playgroud)

但这放弃了:

AssertionError: The `request` argument must be an instance of `django.http.HttpRequest`, not `rest_framework.request.Request`
Run Code Online (Sandbox Code Playgroud)

所以我的问题是......有没有一种直接的方法来做到这一点?我可以访问对象的_request属性rest_framework.request.Request(类型为django.http.HttpRequest,但是我没有包含在 DRFRequest对象中的任何身份验证详细信息(实际上,ListAndCreateResource如果我response = ListAndCreateResource().as_view()(request._request, *args, **kwargs)在上面的尝试 #2 中使用,我会返回 403 )。

提前致谢!

Ahm*_*yed 5

这似乎有点晚了,但以防万一有人想知道。

class SomeOtherView(generics.CreateAPIView):
    def post(self, request, *args, **kwargs):
        # ... some other functionality...
        # ...
        response = ListAndCreateResource.as_view()(request, *args, **kwargs)
        # ... more functionality...
        return Response({'message': 'ok'})
Run Code Online (Sandbox Code Playgroud)

as_view()函数在被调用时返回一个接受请求、*args、**kwargs 的函数。所以基本上,类视图是一个封装的函数视图。

  • @AmanSharma 使用 `request._request`,DRF 请求是 django `request` 的包装器,可以使用 `._request` 进行访问 (2认同)

Set*_*ti7 0

您可以访问基于类的视图requestself.request

  • 我可以通过链接该线程(提供一些替代方法)来了解您要去哪里,但我希望有一种更直接的方法,而不必求助于一堆重写的方法。不管怎么说,还是要谢谢你。 (2认同)