简体   繁体   English

Django REST Framework:将过滤器应用于列表视图,但不应用于详细信息视图

[英]Django REST Framework: apply filter to list view but not detail view

With Django REST Framework is there a way, when using a ModelViewSet , to filter only the list results but not the detail results? 使用Django REST Framework时,有没有一种方法,当使用ModelViewSet ,仅过滤列表结果而不过滤详细结果?

I have a list of objects that have an owner and I only want users to see the objects they own when they access the objects list. 我有一个拥有所有者的对象列表,我只希望用户在访问对象列表时看到他们拥有的对象。 For that purpose I implemented a new filter backend based on rest_framework.filters.BaseFilterBackend , which works fine for the list. 为此,我基于rest_framework.filters.BaseFilterBackend实现了一个新的过滤器后端,该过滤器在列表中可以正常使用。

The problem arises when I try to access an object that doesn't belong to my user: I get a "404 not found" instead of a "403 forbidden". 当我尝试访问不属于我的用户的对象时,就会出现问题:我收到“找不到404”而不是“ 403禁止”。

In other words, filtering seems to be applied not only to the list but also to the detail view. 换句话说,过滤似乎不仅应用于列表,而且还应用于细节视图。 Is there a way to change this, so that I get the expected 403 when accessing an object which I'm not authorized to see? 有没有一种方法可以更改此设置,以便在访问未经授权查看的对象时得到预期的403?

I already have a permission class in place which prevents a user from seeing objects he doesn't own but it's not even being called unless I comment out the filter_backends property on the viewset class. 我已经有一个权限类,可以防止用户看到他不拥有的对象,但是除非我在viewset类上注释掉filter_backends属性,否则它甚至不会被调用。

Another way to think about this is that I only want to list objects that the user has permission to see. 考虑这种情况的另一种方法是,我只想列出用户有权查看的对象。

The rest_framework exception that you'd want to raise is PermissionDenied to return a 403 , so do this instead of get_object_or_404 . 您要引发的rest_framework异常是PermissionDenied以返回403 ,因此请执行此操作,而不是get_object_or_404

Apply the logic you want, and raise the exception when the User should not be at that DetailView endpoint. 应用所需的逻辑,并在User不应该位于该DetailView端点处引发异常。

from rest_framework.exceptions import PermissionDenied

class UserViewSet(viewsets.ViewSet):

    model = User

    def retrieve(self, request, pk=None):
        try:
            return self.model.objects.filter(foo='bar').get(pk=pk)
        except User.DoestNotExist:
            # can't find the User based upon the filter foo='bar'
            # that represents a object permissions filter
            raise PermissionDenied("message to accompany the 403 error if desired")

You could check to see if pk is in the view kwargs 您可以检查pk是否在视图kwargs中

class MyFilterBackend(BaseFilterBackend):
    def filter_queryset(self, request, queryset, view):
        if 'pk' not in view.kwargs:
            queryset = queryset.filter(...)
        return queryset

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

相关问题 Django Rest Framework列表和详细信息视图重叠 - Django Rest Framework list and detail view overlap 收到“ detail”:“未找到”以获取Django Rest Framework的详细信息视图 - Receive “detail”: “not found” for detail view with Django Rest Framework 连接列表视图和详细视图-django - connecting list view and detail view -django Django Rest Framework视图集URL过滤器错误 - Django Rest Framework view set url filter errors django rest framework - 使用detail_route和detail_list - django rest framework - using detail_route and detail_list Django Rest框架-通用视图 - Django Rest framework - generic view 当 force_login() 在详细视图上时,Django Rest Framework 在单元测试中给出 302? - Django Rest Framework gives 302 in Unit tests when force_login() on detail view? Django rest框架:使用主键整数id以外的字段获取详细信息视图 - Django rest framework: Get detail view using a field other than primary key integer id 如何在django-rest-framework中使用查询参数进行详细视图查找? - How do I use a query parameter for a detail view lookup with django-rest-framework? Django Rest Framework:当默认排序字段可为空时,详细视图中的 Paginaion 会中断 - Django Rest Framework: Paginaion in detail view breaks when default ordering field is nullable
 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM