나는 이렇게 학습한다/Framework

Django 에서 middleware 추가하기

daco2020 2023. 9. 26. 14:36

Django 에서 middleware 추가하기

장고에서 미들웨어를 추가하는 방법에는 함수형과 클래스형이 있는데 이 글에서는 클래스형에 대해서 설명하겠다.

 

먼저 미들웨어 클래스를 정의하고 __init__ 메서드와 __call__ 메서드를 다음과 같이 추가하자.

from django.http import HttpRequest, HttpResponse


class CustomMiddleware:
    def __init__(self, get_response):
        self.get_response = get_response

    def __call__(self, request: HttpRequest) -> HttpResponse:

        some_function() # 요청에 영향을 줄 수 있는 로직

        response = self.get_response(request) # 실제 요청을 처리

        some_function() # 응답에 영향을 줄 수 있는 로직

        return response

 

이렇게 만든 미들웨어를 사용하기 위해, 장고의 settings.py 파일에서 MIDDLEWARE 설정에 이 클래스의 경로를 문자열로 추가한다.

# settings.py
MIDDLEWARE = [
    ...
    'path.CustomMiddleware',  # 여기에 새로 만든 미들웨어 경로를 문자열로 추가
]

 

이제 장고 서버로 요청이 들어올 때 마다 CustomMiddleware 미들웨어가 작동할 것이다.

 

 

 

특정 앱이나 URL 에서만 동작시키려면?

장고의 모든 앱이 아닌 특정 앱 혹은 URL 에서만 원하는 로직을 동작시킬 수 있다. __call__ 메서드 내부에서 요청 객체(request)를 검사하여 원하는 조건에 맞을 때에만 동작을 수행하는 방법이다.

 

예를 들어, URL 경로를 기반으로 특정 앱에만 적용하고 싶다면 이렇게 할 수 있다.

def __call__(self, request: HttpRequest) -> HttpResponse:
    if '/some_app' in request.path:  # '/some_app'이 URL에 포함되어 있을 경우에만 적용
        some_function()

    response = self.get_response(request)
    return response

 

특정 HTTP 메서드에만 적용하고 싶으면 이렇게 할 수 있다.

def __call__(self, request: HttpRequest) -> HttpResponse:
    if request.method == 'POST':  # POST 요청만 처리
        some_function()

    response = self.get_response(request)
    return response

 

물론 여러 조건을 조합해서 복잡한 필터를 구현할수도 있다.

def __call__(self, request: HttpRequest) -> HttpResponse:
    if '/some_app' in request.path and request.method == 'POST':
        some_function()

    response = self.get_response(request)
    return response

 

이렇게 하면 앱이나 URL 등 원하는 조건에 맞는 요청에만 동작을 수행할 수 있다.

 

 

 

미들웨어란?

미들웨어(Middleware)는 그 자체로는 애플리케이션은 아니지만, 두 개 이상의 애플리케이션 혹은 레이어 사이에서 데이터를 중개하거나 특정 기능을 수행해주는 소프트웨어 컴포넌트를 말한다.

 

웹 개발에서는 미들웨어가 주로 클라이언트와 서버, 또는 서버와 데이터베이스 사이에서 다양한 역할을 수행하는데 예를 들어, 인증, 로깅, 캐싱, CORS 설정 등을 처리할 수 있다.

 

장고에서는 미들웨어가 웹 요청이 들어와서 실제 뷰가 처리되기 전과 후에 여러 가지 추가 작업을 할 수 있다. 예를 들면, 모든 요청에 공통으로 적용되어야 하는 로직을 미들웨어에서 처리할 수 있고, 이게 바로 예제에 나와있는 __call__ 메서드에서 일어나는 일이다.

 

간단하게 말해서 미들웨어는 애플리케이션의 입력과 출력 사이에서 여러 작업을 수행하는 중간자라고 볼 수 있다.