[drf] Tutorial 3: Class-based Views

Hyeseong·2021년 2월 19일
0

Tutorial 3: Class-based Views

함수 기반 뷰가 아닌 클래스 기반 뷰를 사용하여 API 뷰를 작성할 수도 있습니다. 일반적인 기능을 재사용하고 코드를 DRY 유지하는 데 도움이되는 강력한 패턴이에요 .

Rewriting our API using class-based views

클래스 기반 뷰를 사용하여 API 재작성 루트 뷰를 클래스 기반 뷰로 다시 작성하여 시작하겠습니다.
views.py

from snippets.models import Snippet
from snippets.serializers import SnippetSerializer
from django.http import Http404
from rest_framework.views import APIView
from rest_framework.response import Response
from rest_framework import status


class SnippetList(APIView):
    """
    List all snippets, or create a new snippet.
    """
    def get(self, request, format=None):
        snippets = Snippet.objects.all()
        serializer = SnippetSerializer(snippets, many=True)
        return Response(serializer.data)

    def post(self, request, format=None):
        serializer = SnippetSerializer(data=request.data)
        if serializer.is_valid():
            serializer.save()
            return Response(serializer.data, status=status.HTTP_201_CREATED)
        return Response(serializer.errors, status=status.HTTP_400_BAD_REQUEST)

단건 기능을 위한 Retrieve, Update, Delete를 작성해볼게요.

class SnippetDetail(APIView):
    """
    Retrieve, update or delete a snippet instance.
    """
    def get_object(self, pk):
        try:
            return Snippet.objects.get(pk=pk)
        except Snippet.DoesNotExist:
            raise Http404

    def get(self, request, pk, format=None):
        snippet = self.get_object(pk)
        serializer = SnippetSerializer(snippet)
        return Response(serializer.data)

    def put(self, request, pk, format=None):
        snippet = self.get_object(pk)
        serializer = SnippetSerializer(snippet, data=request.data)
        if serializer.is_valid():
            serializer.save()
            return Response(serializer.data)
        return Response(serializer.errors, status=status.HTTP_400_BAD_REQUEST)

    def delete(self, request, pk, format=None):
        snippet = self.get_object(pk)
        snippet.delete()
        return Response(status=status.HTTP_204_NO_CONTENT)

지금도 여전히 함수 기반 뷰와 매우 유사합니다.
또한 snippets/urls.py클래스 기반 뷰를 사용 하고 있으므로 약간 리팩토링해야합니다 .

snippets/urls.py

from django.urls import path
from rest_framework.urlpatterns import format_suffix_patterns
from snippets import views

urlpatterns = [
    path('snippets/', views.SnippetList.as_view()),
    path('snippets/<int:pk>/', views.SnippetDetail.as_view()),
]
urlpatterns = format_suffix_patterns(urlpatterns)

개발 서버를 실행하면 모든 것이 이전처럼 작동해야합니다.

Using mixins

클래스 기반 뷰 사용의 큰 장점 중 하나는 재사용 가능한 동작 비트를 쉽게 구성 할 수 있다는 것입니다.

지금까지 사용했던 생성 / 검색 / 업데이트 / 삭제 작업은 우리가 생성하는 모델 지원 API 뷰와 매우 유사 할 것입니다. 이러한 일반적인 동작은 REST 프레임 워크의 mixin 클래스에서 구현됩니다.

mixin 클래스를 사용하여 뷰를 구성하는 방법을 살펴 보겠습니다. 여기 views.py 모듈이 있습니다.

from snippets.models import Snippet
from snippets.serializers import SnippetSerializer
from rest_framework import mixins
from rest_framework import generics

class SnippetList(mixins.ListModelMixin,
                  mixins.CreateModelMixin,
                  generics.GenericAPIView):
    queryset = Snippet.objects.all()
    serializer_class = SnippetSerializer

    def get(self, request, *args, **kwargs):
        return self.list(request, *args, **kwargs)

    def post(self, request, *args, **kwargs):
        return self.create(request, *args, **kwargs)

GenericAPIView에 ListModelMixin, CreateModelMixin이 보이네요.

기본 클래스는 핵심 기능을 제공하고 mixin 클래스는 .list()및 .create()작업을 제공합니다 . 그런 다음 get및 post메서드를 적절한 작업에 명시적으로 바인딩합니다.

class SnippetDetail(mixins.RetrieveModelMixin,
                    mixins.UpdateModelMixin,
                    mixins.DestroyModelMixin,
                    generics.GenericAPIView):
    queryset = Snippet.objects.all()
    serializer_class = SnippetSerializer

    def get(self, request, *args, **kwargs):
        return self.retrieve(request, *args, **kwargs)

    def put(self, request, *args, **kwargs):
        return self.update(request, *args, **kwargs)

    def delete(self, request, *args, **kwargs):
        return self.destroy(request, *args, **kwargs)

GenericAPIView클래스를 사용하여 핵심 기능을 제공하고 믹스 인을 추가하여 .retrieve(), .update()및 .destroy()작업을 해볼게요.

Using generic class-based views

mixin 클래스를 사용하여 이전보다 약간 적은 코드를 사용하도록 뷰를 다시 작성했지만 이보다 더 한 단계 더 나아가 코드를 간결히 작성 할 수 있습니다. REST 프레임 워크는 views.py모듈을 훨씬 더 줄이는 데 사용할 수있는 이미 혼합 된 일반 뷰 세트를 제공합니다 .

from snippets.models import Snippet
from snippets.serializers import SnippetSerializer
from rest_framework import generics


class SnippetList(generics.ListCreateAPIView):
    queryset = Snippet.objects.all()
    serializer_class = SnippetSerializer


class SnippetDetail(generics.RetrieveUpdateDestroyAPIView):
    queryset = Snippet.objects.all()
    serializer_class = SnippetSerializer

다음 tutorial 4에서는 API에 대한 인증 및 권한을 처리하는 방법을 살펴 보겠습니다.

profile
어제보다 오늘 그리고 오늘 보다 내일...

0개의 댓글