[DRF] 인스타그램 클론코딩하기- Permission

Cherry·2022년 1월 31일
1
post-thumbnail

Permission

django 에서의 권한

django 는 user에서 기본적인 권한들을 제공해주고 있다.

  • is_superuser : createsuper 로 생성한 user 에 대해 True, True일 경우 별도 permission 없이 모든 권한 허용

  • is_staff : True 일 경우 admin 페이지 접속가능, 나머지는 일반 유저와 동일

  • is_active : False 일 경우 모든 권한 불허, 로그인도 불가능

Permission이란?

어떠한 사용자가 API에 접근해 특정 작업을 수행하려 할 때, request에 담겨오는
user의 정보에 따라 작업의 권한을 줄지 말지 결정하는 것이다

Permission 종류

DRF 에서 기본제공하는 Permission 은 다음과 같다.

  • AllowAny(default) : 인증여부에 상관없이 무조건 허용 (default)

  • IsAuthenticated : 인증된 사용자에 대한 작업 권한을 허용하고 인증되지 않은 사용에 대한 액세스를 거부

  • IsAdminUser : Staff 인증 요청에 한해서 허용

  • IsAuthenticatedOrReadOnly : 인증된 사용자에게는 전체 액세스를 허용하지만 인증되지 않은 사용자에게는 읽기만 허용

  • DjangoModelPermissions : 인증된 요청에 한해서만 액세스 허용, 추가로 유저별 인증 권한체크를 수행

  • DjangoModelPermissionsOrAnonReadOnly : DjangoModelPermissions 와 유사하나 비인증 요청에 대해서는 읽기 권한만 허용

  • DjangoObjectPermissions : 비인증된 요청 거부, 인증된 레코드 접근에 대한 권한체크를 추가로 수행

  • Custom Permission: 개발자가 custom 하게 permission을 만들어서 사용할 수도 있음

class PostViewSet(ModelViewSet):
    serializer_class = PostSerializer
    queryset = Post.objects.all()
    filter_backends = [DjangoFilterBackend]
    filter_class = PostFilter
    permission_classes = [IsAuthenticatedOrReadOnly]

ViewSet 내부의 permission_classes 에 추가

Custom Permission

위에서 언급한대로 개발자는 자기 입맛대로 액세스 허용권한을 커스텀할 수 있도록 장고가 여러 기능들을 제공해준다.

우선 우선 프로젝트 내부에 permissions.py라는 파일을 생성해준다.

permissions.py

from rest_framework import permissions

class IsAuthorOrReadOnly(permissions.BasePermission):
# 인증된 유저에 대해 목록 조회 / 포스팅 등록 허용
    def has_permission(self, request, view):
        return request.user.is_authenticated
    # 작성자에 한해 Post에 대한 수정 / 삭제 허용

    def has_object_permission(self, request, view, obj):
        # 읽기 권한 요청이 들어오면 허용
        if request.method in permissions.SAFE_METHODS:
            return True
        
        # PUT, DELETE 요청에 한해, 작성자에게만 허용, 요청자(request.user)가 객체(Post)의 user와 동일한지 확인
        return obj.user == request.user

IsAuthorOrReadOnly라는 이름의 permission을 하나 만들어준다.
해당 권한은 우선 SAFE_METHOD(GET, HEAD, OPTIONS)로 요청이 들어온 경우에는 method를 허용을 해주고, 그 외(PUT, PATCH, DELETE)에는 게시글의 user와 로그인된 user가 동일한 경우에만 권한을 허용해준다.

class PostViewSet(ModelViewSet):
    serializer_class = PostSerializer
    queryset = Post.objects.all()
    filter_backends = [DjangoFilterBackend]
    filter_class = PostFilter
    permission_classes = [IsAuthorOrReadOnly]
    
    def perform_create(self, serializer):
        serializer.save(author=self.request.user)

완성~~!!

0개의 댓글