Django REST Framework-permissions séparées par méthode

j'écris une API en utilisant Django REST Framework et je me demande si je peux spécifier des permissions par méthode en utilisant des vues basées sur la classe.

Lecture de la documentation je vois que c'est assez facile à faire si vous écrivez des vues basées sur des fonctions, en utilisant simplement le @permission_classes décorateur sur la fonction des vues que vous voulez protéger avec des permissions. Cependant, je ne vois pas de façon de faire la même chose lorsque vous utilisez CBVs avec le APIView classe, parce que je spécifie alors les autorisations pour la classe complète avec le permission_classes attribut, mais qui sera appliqué alors à toutes les méthodes de classe (get,post,put...).

ainsi, est-il possible d'avoir les vues API écrites avec CBVs et aussi de spécifier des permissions différentes pour chaque méthode d'une classe de vue?

34
demandé sur José L. Patiño 2013-11-04 21:48:48

2 réponses

les Permissions sont appliquées à l'ensemble de la classe View, mais vous pouvez prendre en compte des aspects de la requête (comme la méthode GET ou POST) dans votre décision d'autorisation.

Voir le haut -IsAuthenticatedOrReadOnly un exemple:

SAFE_METHODS = ['GET', 'HEAD', 'OPTIONS']

class IsAuthenticatedOrReadOnly(BasePermission):
    """
    The request is authenticated as a user, or is a read-only request.
    """

    def has_permission(self, request, view):
        if (request.method in SAFE_METHODS or
            request.user and
            request.user.is_authenticated()):
            return True
        return False
35
répondu Kevin Stone 2013-11-05 08:21:57

j'ai rencontré le même problème en utilisant des CBV, car j'ai une logique de permissions assez complexe en fonction de la méthode de requête.

la solution que j'ai trouvée était d'utiliser l'application rest_condition de tiers listée au bas de cette page

http://www.django-rest-framework.org/api-guide/permissions

https://github.com/caxap/rest_condition

j'ai juste divisé la logique de flux de permissions pour que chaque branche s'exécute, en fonction de la méthode de requête.

from rest_condition import And, Or, Not

class MyClassBasedView(APIView):

    permission_classes = [Or(And(IsReadOnlyRequest, IsAllowedRetrieveThis, IsAllowedRetrieveThat),
                             And(IsPostRequest, IsAllowedToCreateThis, ...),
                             And(IsPutPatchRequest, ...),
                             And(IsDeleteRequest, ...)]

ainsi le' ou 'détermine quelle branche des permissions doit s'exécuter en fonction de la méthode de requête et le' et ' enveloppe les permissions relatives à la méthode de requête acceptée, donc tout doit passer pour que la permission soit accordée. Vous pouvez également mélanger 'ou', ' et ' et ' non ' à l'intérieur de chaque flux pour créer des permissions encore plus complexes.

les classes de permission pour exécuter chaque branche ressemblent simplement cette,

class IsReadyOnlyRequest(permissions.BasePermission):

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


class IsPostRequest(permissions.BasePermission):

    def has_permission(self, request, view):
        return request.method == "POST"


... #You get the idea
40
répondu james 2014-01-29 12:01:45