Last active
July 17, 2019 18:28
-
-
Save askcompany-kr/a55ec9a794ef23941000cfa66d3d9736 to your computer and use it in GitHub Desktop.
[Ask Company] django-rest-framework를 활용한 HTTP API 서버 만들기, 예시 코드
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| # | |
| # 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() | |
| data = [{'pk': post.pk, 'message': post.message} for post in qs] # 수동 JSON 직렬화 | |
| return JsonResponse(data, safe=False) | |
| elif request.method == 'POST': | |
| form = PostForm(request.POST) | |
| if form.is_valid(): | |
| post = form.save() | |
| return HttpResponse(status=201) | |
| data = form.errors | |
| return JsonResponse(data, status=400) | |
| @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'), | |
| ] |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| # | |
| # 모델 : myapp/models.py | |
| # | |
| from django.db import models | |
| class Post(models.Model): | |
| title = models.CharField(max_length=100) | |
| # | |
| # Serializer : myapp/serializers.py (Form과 유사) | |
| # | |
| from rest_framework import serializers | |
| from .models import Post | |
| 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 | |
| # | |
| # URL : myapp/urls.py | |
| # | |
| from django.conf.urls import include, path | |
| from rest_framework.routers import DefaultRouter | |
| from .views import PostViewSet | |
| router = DefaultRouter() | |
| router.register('post', PostViewSet) | |
| urlpatterns = [ | |
| path('', include(router.urls)), | |
| ] |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| import time | |
| from rest_framework.response import Response | |
| from django.core.signals import request_started, request_finished | |
| from .models import Post | |
| from .serializers import PostSerializer | |
| class PostViewSet(ModelViewSet): | |
| queryset = Post.objects.all() | |
| serializer_class = PostSerializer | |
| def perform_create(self, serializer): | |
| serializer.save( | |
| author=self.request.user, | |
| ip=self.request.META['REMOTE_ADDR']) | |
| def dispatch(self, request, *args, **kwargs): | |
| global cbv | |
| cbv = self | |
| dispatch_start = time.time() | |
| response = super().dispatch(request, *args, **kwargs) | |
| render_start = time.time() | |
| response.render() | |
| self.render_time = time.time() - render_start | |
| self.dispatch_time = time.time() - dispatch_start | |
| self.api_view_time = self.dispatch_time - (self.render_time + self.serializer_time + self.db_time) | |
| return response | |
| def list(self, request, *args, **kwargs): | |
| db_start = time.time() | |
| post_list = list(self.queryset) | |
| self.db_time = time.time() - db_start | |
| serializer_start = time.time() | |
| serializer = self.get_serializer(self.queryset, many=True) | |
| data = serializer.data | |
| self.serializer_time = time.time() - serializer_start | |
| return Response(data) | |
| def started_fn(sender, **kwargs): | |
| global started | |
| started = time.time() | |
| def finished_fn(sender, **kwargs): | |
| request_response_time = (time.time() - started) - cbv.dispatch_time | |
| total = cbv.db_time + cbv.serializer_time + cbv.api_view_time + cbv.render_time + request_response_time | |
| print('Database Lookup - db_time : {:.6f}s, {:>4.1f}%'.format(cbv.db_time, 100*(cbv.db_time/total))) | |
| print('Serialization - serializer_time : {:.6f}s, {:>4.1f}%'.format(cbv.serializer_time, 100*(cbv.serializer_time/total))) | |
| print('API View - api_view_time : {:.6f}s, {:>4.1f}%'.format(cbv.api_view_time, 100*(cbv.api_view_time/total))) | |
| print('Response rendering - render_time : {:.6f}s, {:>4.1f}%'.format(cbv.render_time, 100*(cbv.render_time/total))) | |
| print('Django request/response : {:.6f}s, {:>4.1f}%'.format(request_response_time, 100*(request_response_time/total))) | |
| request_started.connect(started_fn) # 요청 처리 시작 | |
| request_finished.connect(finished_fn) # 요청 처리 끝 |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment