[NextJS] Middleware 개념 알기
1️⃣ Middleware 란?
미들웨어(Middleware)는 말 그대로 중간에서 처리하는 코드이다. 웹 애플리케이션에서 클라이언트의 요청(Request)을 서버가 처리해서 응답(Response)을 보내는 과정 중에, 그 "중간"에서 실행되는 로직을 미들웨어라고 부른다.
📌 미들웨어가 하는 일
미들웨어는 클라이언트의 요청을 서버가 처리하기 전에 요청을 가로채서 수정하거나, 추가적인 처리를 하는 역할을 한다.
예를 들어, 요청을 보낸 사용자가 인증된 사용자만 접근할 수 있는 페이지에 들어가려고 할 때, 미들웨어가 요청을 가로채고 사용자가 인증되었는지 확인한 후, 인증되지 않았다면 로그인 페이지로 리다이렉트 할 수 있다.
📌 미들웨어가 필요한 이유
인터넷을 사용할 때, 클라이언트와 서버는 서로 계속해서 요청(Request)과 응답(Response)을 주고받는다.
여기서 중요한 점은! 서버는 하나 뿐인데, 클라이언트는 수백, 수천 개가 될 수 있다는 사실이다.
수천 명의 사용자가 동시에 요청을 보낸다고 생각해 보자, 모든 요청을 하나의 서버에서 직접 처리하는 것은 비효율적이고, 서버에 큰 부담을 줄 수 있다. 이때, 미들웨어가 중요한 역할을 한다. 미들웨어는 요청이 서버에 도달하기 전에 미리 필터링하거나, 필요한 데이터를 추가하는 등의 작업을 수행함으로써, 서버 자원의 낭비를 줄일 수 있다.
또한, 서버가 직접 처리하지 않아도 되는 반복적인 작업들을 미들웨어에서 처리할 수 있다. 예를 들어, 로그인 상태를 확인하는 작업, 요청을 로깅하는 작업, API 요청을 가로채서 데이터를 변경하는 작업 등을 미들웨어에서 일괄적으로 처리할 수 있다.
2️⃣ 서버 미들웨어 / 클라이언트 미들웨어
서버 미들웨어는 서버에서 실행된다. 클라이언트가 보낸 요청이 서버에 도달하기 전에, 서버에서 요청을 처리하거나 응답을 수정하는 역할을 한다. 예를 들어, 사용자가 요청한 데이터가 중요한 정보를 포함하고 있다면, 서버 미들웨어는 이 요청을 차단하거나 인증을 확인한다. 서버의 리소스를 낭비하지 않기 위해 불필요한 요청을 처리하지 않도록 할 수도 있다.
클라이언트 미들웨어는 클라이언트(브라우저)에서 실행된다. 클라이언트가 서버에 요청을 보내기 전에, 요청을 수정하거나 추가적인 작업을 한다. 예를 들어, API 요청을 보낼 때 클라이언트에서 인증 토큰을 추가하거나, 서버 응답을 클라이언트에서 처리하여 UI 에 맞게 변환하는 작업을 한다.
📌 예시
서버 미들웨어
인증되지 않은 사용자가 특정 페이지에 접근하려고 하면, 서버 미들웨어는 해당 요청을 거부하거나 로그인 페이지로 리다이렉션한다.
// 서버 미들웨어 예시: 인증 확인
export function middleware(req) {
const isLoggedIn = checkUserAuth(req);
if (!isLoggedIn) {
return NextResponse.redirect('/login');
}
return NextResponse.next(); // 요청을 계속 진행
}
클라이언트 미들웨어
API 요청을 보낼 때 인증 토큰을 추가하거나, 응답으로 받은 데이터를 UI 에 맞게 변환하여 렌더링 할 수 있다.
// 클라이언트 미들웨어 예시: 요청 헤더 추가
const fetchWithAuth = async (url, options = {}) => {
const token = localStorage.getItem('auth_token');
const response = await fetch(url, {
...options,
headers: {
...options.headers,
'Authorization': `Bearer ${token}`,
},
});
return response.json();
};
📌 차이점
항목 | 서버 미들웨어 | 클라이언트 미들웨어 |
실행 위치 | 서버 (Node.js 등) | 클라이언트 (브라우저) |
주요 역할 | 요청을 서버에 전달하기 전에 처리, 응답을 수정 | 요청을 보내기 전에 클라이언트에서 처리, 응답을 수정 |
예시 | 인증 확인, 요청 필터링, 응답 헤더 수정 | API 요청 전처리, 응답 데이터 처리, UI 에 맞게 데이터 변형 |
주요 사용 | 로그인 확인, API 보호, 서버 리소스 최적화 | UI 개선, 네트워크 요청 전처리, 캐시 및 상태 관리 |
적용 범위 | 서버에만 적용, 서버의 모든 요청에 적용 가능 | 브라우저 환경에만 적용, 클라이언트 애플리케이션에서 사용 |
상호작용 | 클라이언트 요청을 서버가 처리하기 전에 개입 | 클라이언트가 서버로 보내는 요청을 수정하거나 처리 |
3️⃣ Next.js 에서의 미들웨어
Next.js 에서의 미들웨어는 서버 측에서 실행되는 함수로, 클라이언트의 요청이 서버에 도달하기 전에 또는 서버가 응답을 클라이언트로 반환하기 전에 요청과 응답을 가로채고 수정하는 중간 처리 로직이다.
📌 동작 방식
Next.js 에서 미들웨어는 Request 객체를 받아서 Response 객체를 반환하는 중간 처리 함수로 동작한다.
- 클라이언트가 요청을 보냄
- 요청이 Next.js 서버로 전달되기 전에, 미들웨어가 요청을 가로챔
- 미들웨어는 요청을 수정하거나 추가 작업을 할 수 있음
- 서버가 요청을 처리하고, 응답을 반환
- 응답은 다시 미들웨어를 지나면서 수정될 수 있음
- 최종적으로 클라이언트로 응답이 전달됨
📌 기본 사용법
미들웨어는 middleware.js 또는 middleware.ts 라는 파일 이름으로 루트 디렉토리나 특정 경로에 작성할 수 있고, NextResponse 와 NextRequest 를 import 해줘야 한다.
기본
// middleware.ts
import { NextRequest, NextResponse } from 'next/server';
// 미들웨어 함수 정의
export function middleware(req: NextRequest): NextResponse {
console.log('미들웨어가 실행되었습니다!');
// 요청을 계속 진행하도록 반환
return NextResponse.next();
}
리다이렉션
// middleware.ts
import { NextRequest, NextResponse } from 'next/server';
export function middleware(req: NextRequest): NextResponse {
// 쿠키에서 'auth_token' 값을 가져옴
const token = req.cookies.get('auth_token');
// 인증되지 않으면 로그인 페이지로 리디렉션
if (!token) {
// URL을 상대적으로 지정하여 로그인 페이지로 리디렉션
return NextResponse.redirect(new URL('/login', req.url));
}
// 인증되었으면 요청을 계속 진행
return NextResponse.next();
}
특정 경로에만 미들웨어를 적용
// middleware.ts
import { NextRequest, NextResponse } from 'next/server';
export function middleware(req: NextRequest): NextResponse {
console.log('미들웨어가 실행되었습니다!');
return NextResponse.next();
}
// 특정 경로에만 미들웨어를 적용
export const config = {
matcher: ['/dashboard/*', '/profile/*'], // 이 경로들에만 미들웨어를 적용
};
📖 정리
- Middleware : 클라이언트 요청과 서버 응답 사이에서 실행되는 중간 처리 코드
- 미들웨어는 요청을 가로채서 수정, 필터링, 데이터 추가 등의 작업을 수행
- 서버의 부담을 줄이고 반복적인 작업을 처리하는 데 사용
- 서버 미들웨어 : 서버에서 실행되며 요청을 처리하거나 응답을 수정
- 클라이언트 미들웨어 : 브라우저에서 실행되며 요청을 처리하거나 응답을 수정
💡 참고 자료
https://nextjs-ko.org/docs/app/building-your-application/routing/middleware
Middleware – Nextjs 한글 문서
Learn how to use Middleware to run code before a request is completed.
nextjs-ko.org