Nginx 리다이렉트 설정 가이드
Nginx는 가장 널리 사용되는 웹 서버 중 하나이며, 리다이렉트 설정은 운영의 기본입니다. 주요 도구인 return과 rewrite는 자주 혼동되어 비효율적이거나 잘못된 설정의 원인이 됩니다.
return과 rewrite 비교
return (권장)
return 301 https://example.com;
- ✅ 빠름 — 정규식 엔진 없이 HTTP 응답을 직접 전송
- ✅ 간단한 구문, 실수하기 어려움
- ✅ 대부분의 리다이렉트에서 공식 권장
- ❌ URL 세그먼트 캡처 및 재사용 불가
rewrite (강력하지만 느림)
rewrite ^/old-path/(.*)$ /new-path/$1 permanent;
- ✅ 정규식 캡처 그룹 지원
- ✅ URL 구조 변환 가능
- ❌
return보다 느림 - ❌ 복잡한 구문, 무한 루프 만들기 쉬움
💡 기본 원칙
가능한 한 return을 사용하세요. 정규식 캡처 그룹이나 복잡한 URL 변환이 필요한 경우에만 rewrite를 사용합니다.
기본 예제
301 영구 리다이렉트
server {
listen 80;
server_name old-domain.com;
return 301 https://new-domain.com$request_uri;
}
302 임시 리다이렉트
server {
listen 80;
server_name example.com;
location /maintenance {
return 302 /maintenance.html;
}
}
단일 페이지 리다이렉트
location = /old-page.html {
return 301 /new-page.html;
}
HTTP→HTTPS
권장: 별도의 server 블록
server {
listen 80;
server_name example.com www.example.com;
return 301 https://$host$request_uri;
}
server {
listen 443 ssl http2;
server_name example.com www.example.com;
ssl_certificate /path/to/fullchain.pem;
ssl_certificate_key /path/to/privkey.pem;
# 사이트 설정...
}
⚠️ if 디렉티브 사용 자제
Nginx 커뮤니티에는 "if는 악이다"라는 격언이 있습니다. if 디렉티브는 특정 컨텍스트에서 예상치 못한 동작을 일으킬 수 있습니다. HTTPS 리다이렉트에는 별도의 server 블록을 사용하세요.
www 정규화
non-www → www
server {
listen 80;
listen 443 ssl http2;
server_name example.com;
ssl_certificate /path/to/fullchain.pem;
ssl_certificate_key /path/to/privkey.pem;
return 301 https://www.example.com$request_uri;
}
www → non-www
server {
listen 80;
listen 443 ssl http2;
server_name www.example.com;
ssl_certificate /path/to/fullchain.pem;
ssl_certificate_key /path/to/privkey.pem;
return 301 https://example.com$request_uri;
}
경로 리다이렉트
# 디렉토리 리다이렉트 (접두사 제거)
location /blog/ {
rewrite ^/blog/(.*)$ /articles/$1 permanent;
}
# map을 사용한 대량 리다이렉트 (대규모 목록에 효율적)
map $uri $new_uri {
/old-page-1 /new-page-1;
/old-page-2 /new-page-2;
}
server {
if ($new_uri) { return 301 $new_uri; }
}
정규식 리다이렉트
# .html 확장자 제거
location ~ ^(.+)\.html$ {
return 301 $1;
}
# 날짜 기반 URL 접두사 제거
location ~ ^/\d{4}/\d{2}/\d{2}/(.+)$ {
return 301 /$1;
}
흔한 실수
1. rewrite 루프
# ❌ 무한 루프
location /old/ {
rewrite ^/old/(.*)$ /new/$1;
}
# ✅ permanent 플래그 또는 return 사용
location /old/ {
return 301 /new$request_uri;
}
2. 쿼리 문자열 손실
# ❌ 쿼리 문자열이 사라짐
location /old { return 301 /new; }
# ✅ 쿼리 문자열 유지
location /old { return 301 /new$is_args$args; }
3. HTTPS 대상의 SSL 설정 누락
HTTP → HTTPS로 리다이렉트하더라도 HTTPS server 블록에 유효한 인증서가 설정되어 있지 않으면 사용자는 연결 오류를 겪게 됩니다. 리다이렉트를 활성화하기 전에 반드시 HTTPS 블록의 존재와 인증서 유효성을 확인하세요.
성능 팁
rewrite보다return우선 — 정규식 엔진 오버헤드 없음- 리다이렉트 체인 단축: A → B → C가 아닌 A → C로 직접 리다이렉트
- 대량 리다이렉트 테이블에는
map사용 — 설정 로드 시 평가되며 요청마다가 아님 location블록에서 불필요한 정규식 피하기, 가능하면 접두사 또는 정확한 매칭 사용- 변경 후 반드시
nginx -t실행하여 리로드 전 구문 오류 감지
리다이렉트 설정 후 301check.com으로 검증하세요.