Back-End
[Django] ModelViewSet에서 Retrieve의 동작 원리
APIView를 상속받는.. GenericAPIView를 상속받는.. GenericViewSet을 상속받는.. ModelViewSet은 mixins를 모두 상속받는다. 3단 추상화 .... Retrieve란? mixinx.RetrieveModelsMixin에 구현되어있는 메서드이다. 찾고자 하는 모델의 세부 정보를 반환한다. 어떻게 찾고자 하는 모델을 알 수 있을까? 우선 RESTful 규칙에 지키며 통신이 이루어진다고 가정하자. [GET] http://localhost/post/3 위와 같은 url은 id가 3인 post를 요청하는 것이다. 해당 url을 받아들일 수 있는 django의 urls.py를 보면 urlpatterns = [ path('post/', ...), ] 이런 식으로 되어있을 것이다..
[Django] Serializer와 validate (TIP!)
POST method로 새로운 글을 만들 때는 제목이 중복되면 안된다. 중복되면 안되는 필드가 있다고 생각하면 된다. 하지만 해당 글을 수정하고 저장할 때의 제목 중복여부는 수정 이전의 제목과 같을때만 허용해야 할 것이다. serailizer에서 중복을 허용하지 않기 위해서 다음과 같은 간단한 유효성 검사 메서드를 만들 수 있다. def validate(self, attrs): if Category.objects.filter(title=attrs['title']).exists(): raise ValidationError(_("Duplicated title.")) return super().validate(attrs) 여기서 validate는 serializer.is_valid()가 호출이 되면 실행이되는..
모놀리식 & 마이크로서비스 아키텍처(분산 시스템)
모놀리식 아키텍처 소프트웨어가 하나의 결합된 코드로 구성되기 때문에 초기에 설계가 용이하다. 개발도 단순하고, 코드 관리도 간편하다. 일단 개발이 단순하고 코드 관리가 간편하다는 것은 엄청난 장점이다. 하지만 서비스 운영중에 수정사항이 많아질 경우, 특정 서비스에서의 수정이 다른 서비스에 영향을 미쳐서 2개의 서비스가 모두 고장나버리는 사태가 발생할 수 있다. 또한 서비스가 점점 성장하면서 기능이 추가될수록 단순했던 서비스간의 관계도가 매우 복잡해 질 수 있다. 만약에 네이버웹툰, 네이버 증시, 네이버 메일, 네이버 페이 등의 서비스들이 모두 모놀리식 아키텍처로 한데 묶여있다고 가정해보자. 위 서비스들은 서로 관련이 전혀 없다고 볼 수 있다. 웹툰이 망가진다고 해서 네이버 메일을 못보내면 말이 안되는 것..
[Django] DRF 구조 이해 #1 (APIView)
APIView는 DRF에서 사용하는 GenericAPIView, Viewset과 같이 편리하게 사용할 수 있는 api 라이브러리들의 기반이 되는 클래스이다. 참고:) APIView 클래스 전체 더보기 class APIView(View): # The following policies may be set at either globally, or per-view. renderer_classes = api_settings.DEFAULT_RENDERER_CLASSES parser_classes = api_settings.DEFAULT_PARSER_CLASSES authentication_classes = api_settings.DEFAULT_AUTHENTICATION_CLASSES throttle_classes ..
MSA(MicroService Architecture)에 대한 내 생각 한 줌
백엔드 개발에 관심이 있다면 한 번쯤은 들어봤을 MSA 백엔드에 대해서 공부할수록 느껴지는 게 있다. 프레임워크를 능숙히 사용하고, 코드를 우아하게 짜고, 새로운 신기술을 사용하는 것.. 모두 정말 중요하다고 생각한다. 나는 스프링, 장고 같은 프레임워크를 깊이 이해해서 요구사항을 빠르고 쉽게 해결하고 싶다. 불필요한 중복을 최소화하면서 객체지향적인 코드를 짜고 싶다. 새로운 신기술을 도입해서 기술적 역량을 확장시키고 싶다. 근데 위 3가지를 연습하면서도 최종적으로 바라봐야 할 '숲' 같은 존재는 인프라/아키텍쳐 부분이라고 생각한다. 같은 프로젝트를 수행하더라도 더 확장하기 쉽고, 변경이 쉬운 구조를 설계하는 사람이 되고 싶다. 그런 설계 방식 중 하나가 마이크로 서비스 아키텍처이다. 한 단계 더 깊이 ..
[Django] django 기본 인증 시스템 커스텀(아이디, 이메일 로그인)
AUTHENTICATION_BACKENDS = ( 'django.contrib.auth.backends.ModelBackend', ) Django의 기본 인증시스템은 django.contrib.auth.backends.ModelBackend 를 사용한다. django session 기반의 인증 시스템이다. jwt인증을 구현했다고 하더라도 admin 페이지에서는 계속 기본 인증시스템을 사용한다. 인터넷을 사용하다 보면 사이트마다 로그인하는 방식이 다르다. 이메일 형식의 아이디 입력. 일반 단어 형식의 아이디 입력. 소셜 로그인 기타.. 처음에 회원가입을 할 때 아이디와 이메일을 모두 입력한다고 가정하자. 이때 아이디로도 로그인이 가능하고, 이메일로도 로그인이 가능하게 만들어보자. ## auth/authen..
[Django] DRF를 사용한 JWT Authentication #2
이번 포스팅에서는 JWT를 생성하고 로그인,로그아웃 기능을 구현하는 방법을 정리해 보려고 한다. 로그인 로직 클라이언트는 LoginApi를 호출하면서 {"username": "이름", "password": "비번"} 정보를 전달해준다. 서버는 username과 password를 가지고, 해당하는 유저를 찾은 다음 jwt_login을 수행한다. jwt_login에서는 access_token과 refresh_token을 생성한다. 생성된 access_token은 {"access_token": access_token}형태의 json으로 클라이언트에 전달되고, 생성된 refresh_token은 httpOnly=True 속성을 가진채로 cookie에 삽입된다. 로그아웃 로직 클라이언트에서 LogoutApi를 호출..
[Django] DRF를 사용한 JWT Authentication #1
이번 포스팅에서는 DRF를 사용해 JWT 인증시스템을 어떻게 구현하는지에 대해서 정리해보려고 한다. JWT란? JWT는 Json Web Token의 약자로 모바일이나 웹의 사용자 인증을 위해 사용하는 암호화된 토큰을 의미한다. JWT 정보(사용자 id, 토큰 생성시간, 만료시간)를 request에 담아 사용자의 정보 열람, 수정 등 개인적인 작업들을 수행할 수 있다. JWT를 사용해 인증시스템을 구축한 이유 1. 프론트엔드와 백엔드의 완전한 분리 Django의 세션기반 로그인을 사용하기 위해서는 Django Template을 사용해야한다. 이는 프론트엔드 개발인원들이 반드시 Django의 문법을 어느 정도 이해해야만 페이지를 구성할 수 있다는 뜻이다. 하지만 JWT를 사용한다면 클라이언트와 서버의 완전한..
[Django] Nested Serializer - Create
Writable nested serializers 기본적으로 nested serializer는 읽기 전용이다. 외래키로 연결되어 두개 이상의 모델이 중첩 된 serializer를 사용해 모델을 저장, 수정하려면 creat()또는 update()메서드를 만들어 외래키 관계를 저장하는 방법을 직접 구현해야 한다. Nested Model from django.db import models class BasePage(models.Model): created_time = models.DateTimeField('created time', auto_now_add=True) last_mod_time = models.DateTimeField('modified time', auto_now=True) class Meta: ..
[Django] django-debug-toolbar 안보임 오류 해결
degub-toolbar가 왜 안 나오는지 도저히 모르겠다면 꼭 해보세요. import mimetypes mimetypes.add_type("application/javascript", ".js", True) 위 코드를 settings.py가 있는 폴더의 urls.py에 추가해보자. from django.contrib import admin from django.conf import settings from django.urls import path, include urlpatterns = [ path('admin/', admin.site.urls), ... ] import mimetypes mimetypes.add_type("application/javascript", ".js", True) if se..