django rest framework는 REST API 컨셉을 쉽게 만들 수 있도록 도와주지만, 이것이 REST API의 전부는 아니다.
아래는 DRF를 사용하지 않고 API서버를 구현하는 방법이다.
#
# myapp/models.py
#
from django.db import models
class Post(models.Model):
message = models.TextField()
#
# myapp/forms.py
#
from django import forms
from .models import Post
class PostForm(forms.ModelForm):
class Meta:
model = Post
fields = '__all__'
#
# myapp/views.py
#
from django.http import HttpResponse, JsonResponse
from django.http import QueryDict
from django.shortcuts import get_object_or_404
from django.views.decorators.csrf import csrf_exempt
from .models import Post
from .forms import PostForm
@csrf_exempt
def post_list(request):
if request.method == 'GET':
qs = Post.objects.all()
# 수동 JSON 직렬화
data = [{'pk': post.pk, 'message': post.message} for post in qs]
return JsonResponse(data, safe=False)
elif request.method == 'POST':
form = PostForm(request.POST)
if form.is_valid():
post = form.save()
return HttpResponse(status=201) # created status code
data = form.errors
return JsonResponse(data, status=400) # bad request status code
@csrf_exempt
def post_detail(request, pk):
post = get_object_or_404(Post, pk=pk)
if request.method == 'GET':
return JsonResponse({'pk': post.pk, 'message': post.message})
elif request.method == 'PUT':
put = QueryDict(request.body)
form = PostForm(put, instance=post)
if form.is_valid():
post = form.save()
data = {'pk': post.pk, 'message': post.message}
return JsonResponse(data=data, status=201)
return JsonResponse(form.errors)
elif request.method == 'DELETE':
post.delete()
return HttpResponse('', status=204)
#
# myapp/urls.py
#
from django.conf.urls import url
from .views import post_list, post_detail
urlpatterns = [
url(r'^post/$', post_list, name='post-list'),
url(r'^post/(?P<pk>\d+)/$', post_detail, name='post-detail'),
]DRF는 REST API 구현을 도와주는 "Class Based View"를 제공해주는 프레임워크이다. 먼저 DRF를 사용하기 위해 django REST framework를 설치한다.
$ pip install djangorestframework그리고 settings.py에 INSTALLED_APPS 부분에도 'rest_framework'를 추가하고 코드를 구현해본다.
DRF에서는 forms.py파일 대신 serializers.py를 사용한다. serialize를 한다는 것은 객체와 같은 보기 힘든 데이터를 JSON이나 XML처럼 보기 쉬운 데이터로 바꾸어 통신하게 해주는 것을 말한다.
DRF에서는 views.py에서 ViewSet이라는 class를 사용해서 편하게 작성할 수 있다. ViewSet에서는 @csrf_exempt 토큰을 빼주어야 한다.
또한, view 대신에 viewset을 사용해서 자동적으로 URLconf를 우리의 API에 생성할 수 있기 때문에 urls.py에서도
그냥 라우터 클래스에 등록해주기만 하면 된다. 또, API URL들을 기본 제공하는 기능보다 더 추가하고싶다면 URL conf를 명시해주면 된다.
#
# myapp/models.py
#
from django.db import models
class Post(models.Model):
title = models.CharField(max_length=100)
#
# myapp/serializers.py (Form과 유사)
#
from rest_framework import serializers
from .models import Post
# ModelForm 대신에 ModelSerializer
class PostSerializer(serializers.ModelSerializer):
class Meta:
model = Post
fields = '__all__'
#
# myapp/views.py
#
from rest_framework import viewsets
from .models import Post
from .serializers import PostSerializer
class PostViewSet(viewsets.ModelViewSet):
queryset = Post.objects.all()
serializer_class = PostSerializer
#
# myapp/urls.py
#
from django.conf.urls import include
from rest_framework.routers import DefaultRouter
from .views import PostViewSet
router = DefaultRouter()
router.register(r'post', PostViewSet)
urlpatterns = [
url(r'', include(router.urls)),
]