get_permissions: HTTP 메서드별로 다른 권한 클래스 적용하기

get_permissions() 메서드를 오버라이드하여 HTTP 메서드나 액션에 따라 동적으로 다른 권한 클래스를 적용하는 방법

동작 원리

DRF의 요청 처리 흐름에서 인증 후 권한 확인 단계에서 get_permissions()가 호출되어 권한 클래스 인스턴스 리스트를 반환하고, 각 권한 클래스의 has_permission() 메서드를 실행하여 권한을 검사

기본 구현 방법

def get_permissions(self):
    if self.request.method == 'GET':
        permission_classes = [AllowAny]
    else:
        permission_classes = [IsAuthenticated, IsOwnerOrReadOnly]
    
    return [permission() for permission in permission_classes]
  • self.request.method를 기준으로 if/elif 분기 처리

  • 반드시 권한 클래스의 인스턴스 리스트를 반환 ([AllowAny()])

ViewSet과 action 활용

def get_permissions(self):
    action_permissions = {
        'list': [AllowAny],
        'retrieve': [AllowAny], 
        'create': [IsAuthenticated],
        'update': [IsOwnerOrReadOnly],
        'destroy': [IsOwnerOrReadOnly],
        'publish': [IsAdminUser]  # 커스텀 액션
    }
    
    permission_classes = action_permissions.get(self.action, [IsAuthenticated])
    return [permission() for permission in permission_classes]
  • self.action을 기준으로 권한 제어 (list, create, retrieve, update 등)

  • 딕셔너리 매핑으로 가독성과 유지보수성 향상

  • 커스텀 @action 메서드도 동일하게 처리 가능

실무 팁

  • 팀 내 일관된 패턴(딕셔너리 매핑) 사용 권장

  • 각 사용자 타입과 액션에 대한 권한 테스트 코드 작성 필수

  • get_permissions()는 인증 완료 후 호출되므로 self.request.user 활용 가능

Last updated