[Django] REST API 만들어보기

YSW_dev ㅣ 2024. 2. 6. 03:05

Django는 서버 만들기 좋은 프레임워크이므로 API역시 쉽게 만들 수 있습니다.

그 중에서 REST한 API를 만들어보겠습니다.

 

근데 REST는 대체 무엇일까요?

 

GPT4한테 물어본 결과 그렇다고 하네요

 

쉽게 말해서 특정 기능만을 수행하는 특정 엔드포인트(url)에 특정 값과 함께 요청을 보내면 특정 값을 돌려보내주는

그런 API를 말한다고 합니다.

 

저만의 코드(표준을 곁들인)와 경로를 설정해놓고 서버로 구축하면 경로를 통해 응답을 주고받을 수 있는 것입니다.

마치 지구를 도는 인공위성처럼 말이죠.

 

 

 

django에서는 REST_framework란 기능을 지원합니다.

$ pip install djangorestframework

 

 

설치한 후에 명령어로 api 요청을 처리할 앱을 한 개 만들어줍니다.

$ python manage.py startapp api

 

 

그리고 이를 잘 사용하기 위해선 settings.py에도 추가를 해줘야 합니다.

INSTALLED_APPS = [
    ...
    'rest_framework',
    'api',
]

 

 

마지막으로 api가 받아온 데이터를 잘 소화할 수 있도록 데이터를 잘 풀어헤쳐줄 Serializer가 필요합니다.

API요청을 주고 받을때는 보통 JSON형식의 데이터를 많이 사용합니다.

받아온 JSON 형식의 데이터를 serializer에 넣으면 딕셔너리나 원하는 모델의 인스턴스 등 먹기 좋은 형태로 나옵니다.

 

첫 앱을 생성할 경우 serializer는 생성이 안되므로 api 디렉토리 안에 serializers.py 파일을 만들어 줍시다

#api/serializers.py
from rest_framework import serializers

class mySerializer(serializers.Serializer):
    food = serializers.CharField(max_length=50)
    ...


#특정 모델을 기반으로 사용하고 싶다면 아래처럼
class MyModelSerializer(serializers.ModelSerializer):
    class Meta:
        model = MyModel
        fields = ['field1', 'field2', ...]

 

 

완료되었으면 이제 view를 만들 차례입니다.

api 기능 중 요청을 알맞게 처리하는 몸통 부분에 해당합니다.

#api/views.py
from rest_framework.views import APIView
from rest_framework import status
from rest_framework.response import Response
from .serializers import mySerializer


class MyApiViewSet(APIView):
    def get(self, request, format=None): 
    #함수명이 곧 요청의 형태 (GET, POST..)
        serialized_data = mySerializer(data=request.GET)
        #request.data로 요청된 데이터에 접근
        if serialized_data.is_valid():
        #받아온 데이터가 유효한지 확인
            my_data = serialized_data.data.get("food")
            #데이터는 딕셔너리의 형태로 변경됨 => {"food": "hamburger"} 등
            
            if my_data == "hamburger":
                my_response = "good"
            elif my_data == "cucumber":
                my_response = "bad"
            else:
                my_response = "anything else"
            #알맞게 처리하는 코드

            return Response({"answer": my_response}, status=status.HTTP_200_OK)
            #알맞은 응답을 반환하기 위한 코드
            #Response 함수가 딕셔너리 형태로 된 데이터를 알아서 Json으로 바꿔줌
            #HTTP 200 응답으로 OK 알림

        else:
            return Response({"answer": "error"}, status=status.HTTP_400_BAD_REQUEST)
            #데이터 값이 유효하지 않을 경우 응답 반환
            #HTTP 400 응답으로 !OK 알림

 

 

이제 이 api에 접근할 경로만 만들어주면 끝입니다.

#api/urls.py
from django.urls import path
from .views import MyApiViewSet

urlpatterns = [
    path("get-data", MyApiViewSet.as_view()),
    # api/get-data
]

####################################################################
#메인 디렉토리의 urls.py
from django.urls import path, include

urlpatterns = [
    path("api/", include("api.urls"))
    # url => api/ 이후의 경로들은 모두 api.urls파일의 url로 처리하겠다는 뜻
]

 

 

서버를 실행시켜서 api를 호출해 보겠습니다.

 

나는 오이가 싫다

 

아무것도 입력 안하고 호출할 경우 400 응답

 

 

엔드포인트는 로컬에서 서버를 실행했기 때문에 localhost:8000을 포함하지만 이후 온라인상에 배포를 한 뒤에는 localhost:8000대신 제 서버만의 url로 대체가 됩니다.