1. DRF를 사용하는 이유?

Django만 사용하는 경우, Model을 불러올 때 Queryset의 형태로 가져오게 된다. 만약 프론트 앤드를 직접 개발하는 경우 이러한 방식이 문제가 되지 않지만, 실무에서는 그렇지 않은 경우가 더 많다. Django는 백앤드로만 사용하고 React 등을 사용하여 프론트를 개발하는 경우에는 이러한 Queryset 형태를 피하는 것이 좋다. 따라서 DRF를 사용하여 Queryset을 serialize하고 json 형태로 데이터를 받아오는 것이 확장성 측면에서 더 바람직한 개발이라고 할 수 있다.

image



2. DRF setting

본 포스팅은 기존에 accounts app과 Users Model이 존재한다고 가정하고 설명한다.

2-1) install DRF

우선, DRF를 설치하고, settings.py의 INSTALLED_APPS에 추가해준다. 그리고 나서 DEFAULT_PERMISSION_CLASSES를 설정해주어야 하는데, View를 호출하기 위한 권한을 설정해주는 것이다. 일단 단순 결과 확인을 위해 AllowAny로 설정하였다. 권한 설정은 언제든지 다시 바꿀 수 있다.

>>> pip install djangorestframework
INSTALLED_APPS = [
    ...
    'rest_framework',
]

...

# Restframework
REST_FRAMEWORK = {
    "DEFAULT_PERMISSION_CLASSES": [
        'rest_framework.permissions.AllowAny', 
    ]
}
  • DRF permission 종류
    • AllowAny : 디폴트로 지정된 전역 설정으로 인증 여부에 상관없이, View를 호출할 수 있다.

    • IsAuthenticated : 회원으로 인증된 요청에 한해서, View 호출

    • IsAdmin : staff 인증 요청에 한해서, View 호출

    • IsAuthenticatedOrReadOnly : 비인증된 요청에 대해서는 읽기 권한만 허용

    • rest_framework_api_key를 install하여 api key가 있는 경우에만 View를 호출할 수 있게 할수도 있음

        REST_FRAMEWORK = {
            "DEFAULT_PERMISSION_CLASSES": [
                "rest_framework_api_key.permissions.HasAPIKey",
            ]
        }
      


2-2) Serializers 선언

모델의 Queryset을 serialize 해줄 serializer를 선언해준다. 이 때, serializers.py는 django-app(accounts) 하위 디렉토리에 생성해주며, 권한별로 열람 범위를 제한하여 필요한 데이터만 뽑아서 사용할 수 있다. 사용할 수 있는 seriailizer에는 대표적으로 ModelSerializer와 HyperlinkedModelSerializer가 있으며(각각 M.S, H.S로 축약하겠다.), 본 포스팅에서는 H.S를 사용한다. H.S가 M.S와 다른점은, id 필드를 default로 가지지 않고, relationship으로 HyperlinkedRelatedField를 사용한다는 점인데, 현재는 해당 기능들을 사용하지 않으므로 관련 설명은 생략한다. 다만, 일반적으로 hyperlinking을 하는 것이 좋은 RESTful 디자인으로 알려져있다고 한다.

# accounts/serializers.py

from .models import Users
from rest_framework.serializers import HyperLinkedModelSerializer

class CommonUsersSerializer(HyperLinkedModelSerializer):
    class Meta:
        model = Users
        fields = ['email', 'pw']

class AdminUsersSerializer(HyperLinkedModelSerializer):
    class Meta:
        models = Users
        fields = '__all__' # 모든 필드 포함


2-3) View 함수 작성

DRF 관련 뷰 함수는 accounts/views/api.py에 작성해주었다. 다음과 같이 일반적인 동작은 ViewSets를 사용하여 그룹화하고, 필요한 동작이 있을 경우 개별 뷰로 나누어 사용할 수 있다. 또한 serializers.py에서 미리 지정한 열람 범위를 상황에 맞게 사용할 수 있으며, decorator를 사용하여 개별함수를 쉽게 제어할 수 있다. serializer의 CRUD 적용도 가능한데, 해당 내용은 다음 포스팅에서 설명하겠다.

# accounts/views/api.py
from accounts.models import Users
from accounts.serializers import *
from rest_framework import viewsets
from rest_framework.permissions import IsAuthenticated
from rest_framework.decorators import api_view, permission_classes

class UsersViewSet(viewsets.ModelViewSet):
    queryset = User.objects.all()
    serializer_class = AdminUsersSerializer
    permission_classes = [IsAuthenticated]

########
# 또는 #
#######
@api_view(['POST'])
@permission_classes([IsAuthenticated])
def changepwmodal(request):
    pw = request.POST.get('pw')
    email = request.POST.get('user')

    user = Users.objects.filter(email = email)[0]
    serializer = CommonUsersSerializer(user, many=True)

    if serializer.is_valid():
        ...


2-4) URL 연결

위에서 일반적인 동작은 ViewSet으로 묶었고, 다른 세부적인 동작은 개별 함수로 만들어 제어해주었다. 따라서 ViewSet은 router에 등록하여 URL conf가 자동으로 생성되게 하고, 개별 함수는 명시적으로 URL conf를 작성해준다.

from django.urls import path, include
from rest_framework import routers
from accounts.views import api

router = routers.DefaultRouter()
router.register(r'users', api.UsersViewSet)

urlpatterns = [
    path('api/', include(router.urls)),
    path('api/changpw/', api.changepwmodal),
    ...
]



3. 결과

image

image



댓글남기기