<aside>
💡 백엔드와 프론트엔드 간의 통신규약(response code
, response format
)을 정의합니다
</aside>
success
{
status : "success",
data : { "post" : { "id" : 2, "title" : "Another blog post", "body" : "More content" }}
}
fail
{
"status" : "fail",
"data" : { "title" : "A title is required" }
}
error
{
"status" : "error",
"message" : "Unable to communicate with database",
"code" : "error code num"
}
# settings.py
REST_FRAMEWORK = {
'DEFAULT_RENDERER_CLASSES': [
# 여기에 custom한 renderer class를 import
'custom_json_renderer.ResponseRenderer',
'rest_framework.renderers.JSONRenderer',
'rest_framework.renderers.BrowsableAPIRenderer'
],
}
# custom_json_renderer.py
import json
from rest_framework import renderers
from rest_framework.status import is_success, is_client_error, is_server_error
class ResponseRenderer(renderers.JSONRenderer):
# media_type = 'application/json'
# format = 'json'
charset = 'utf-8'
# JsonResponse를 rendering하는 메소드를 오버라이딩하여 사용
def render(self, data, accepted_media_type=None, renderer_context=None):
response_context = renderer_context.get('response')
code = response_context.status_code
# 응답이 성공한 경우(200, 201, 204)
if is_success(code):
return json.dumps({'status': 'success', 'data': data})
# 응답이 실패한 경우(400, 401, 403, 404, 405)
if is_client_error(code):
if isinstance(data, list):
_data = [item for item in data].pop()
elif isinstance(data, dict):
_data = [value for key, value in data.items()].pop()
else:
_data = data
return json.dumps({'status': 'fail', 'data': _data})
# 요청 처리 간에 서버 오류가 발생한 경우(500)
if is_server_error(code):
return json.dumps({'status': 'error', 'message': data, 'code': code})
# 서비스에서 정의하지 않은 오류가 발생한 경우(is_informational, is_redirect)
return json.dumps({'status': 'undefined', 'message': '정의되지 않은 종류의 에러입니다'})