Django Rest Framework custom permissions per view

别等时光非礼了梦想. 提交于 2021-02-06 12:44:46

问题


I want to create permissions in Django Rest Framework, based on view + method + user permissions.

Is there a way to achieve this without manually writing each permission, and checking the permissions of the group that the user is in?

Also, another problem i am facing with, is that permission objects are tied up to a certain model. Since i have views that affect different models, or i want to grant different permissions on the method PUT, depending on what view i accessed (because it affects different fields), i want my permissions to be tied to a certain view, and not to a certain model.

Anyone know how this can be done?

I am looking for a solution in the sort of:

1) Create a Permissions object with the following parameters: View_affected, list_of_allowed_methods(GET,POST,etc.)

2) Create a Group object that has that permission associated

3) Add a user to the group

4) Have my default permission class take care of everything.

From what i have now, the step that is giving me problems is step1. Because i see no way of tying a Permission with a View, and because Permissions ask for a model, and i do not want a model.

Any help would be greatly appreciated!


回答1:


Well, the first step could be done easy with DRF. See http://www.django-rest-framework.org/api-guide/permissions#custom-permissions.

You must do something like that:

from functools import partial

from rest_framework import permissions

class MyPermission(permissions.BasePermission):

    def __init__(self, allowed_methods):
        super().__init__()
        self.allowed_methods = allowed_methods

    def has_permission(self, request, view):
        return request.method in self.allowed_methods


class ExampleView(APIView):
    permission_classes = (partial(MyPermission, ['GET', 'HEAD']),)



回答2:


Custom permission can be created in this way, more info in official documentation( https://www.django-rest-framework.org/api-guide/permissions/):

from rest_framework.permissions import BasePermission


# Custom permission for users with "is_active" = True.
class IsActive(BasePermission):
    """
    Allows access only to "is_active" users.
    """
    def has_permission(self, request, view):
        return request.user and request.user.is_active

# Usage
from rest_framework.views import APIView
from rest_framework.response import Response

from .permissions import IsActive   # Path to our custom permission

class ExampleView(APIView):
    permission_classes = (IsActive,)

    def get(self, request, format=None):
        content = {
            'status': 'request was permitted'
        }
        return Response(content)



回答3:


thanks, I took this idea and got it to work like so:

class genericPermissionCheck(permissions.BasePermission):

def __init__(self, action, entity):
    self.action = action
    self.entity = entity

def has_permission(self, request, view):
    print self.action
    print self.entity
    if request.user and request.user.role.access_rights.filter(action=self.action,entity=self.entity):
        print 'permission granted'            
        return True
    else:
        return False

I used partial in the decorator for the categories action in my viewset class like so:

@list_route(methods=['get'],permission_classes=[partial(genericPermissionCheck,'Fetch','Categories')])
def Categories(self, request):

BTW, "access_rights" maps to an array of objects with a pair of action and object e.g. 'Edit' and 'Blog'



来源:https://stackoverflow.com/questions/23716855/django-rest-framework-custom-permissions-per-view

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!