eelseungmin

[Nginx] HTTPS 적용하기

by eelseungmin

배경

리버스 프록시로 자주 활용되는 Nginx 웹 서버의 경우 정적 페이지 호스팅, 로드밸런싱, Cashing 등의 역할을 수행한다. 뿐만 아니라 HTTPS를 적용할 수 있다는 장점도 가지고 있다.

 

이번에 내가 개발에 참여 중인 프로젝트에서 로드밸런싱과 HTTPS를 적용하기 위해 리버스 프록시로 Nginx를 활용하게 되었고, HTTPS를 적용하게 되어 그 과정을 간단하게 정리했다.(사실 로드밸런싱을 당장 적용한 건 아니지만 혹시라도 우리 서비스의 사용자가 많아져서 컨테이너를 여러 대 돌려야하는 상황이 생길 수도 있다는 행복회로를 돌려보았다...)

 

HTTPS란?

인터넷 통신을 할 때 TCP/IP 기반의 HTTP 프로토콜을 이용하게 되는데, 이때는 중간에 제3자가 주고 받는 데이터를 가로챌 수 있다. 따라서 공개키 암호화 방식이 적용된 SSL을 추가하여 이러한 단점을 보완한 것이 HTTPS이다.

 

적용 과정

무료로 SSL 인증서를 발급해주는 Let's Encrypt라는 곳의 서비스를 이용하여 발급했다. 다만 90일마다 인증서를 갱신해주어야 한다는 특징이 있는데, 이 부분은 글 후반부에 자세히 언급하겠다.

 

다음 과정은 Ubuntu 22.04 기준이다.(Ubuntu 18.04부터 동일)

 

1.  SSL 인증서를 발급하기 위해 certbot을 설치한다.

$ sudo apt install certbot

# Nginx 웹 서버에 certbot을 작동시키기 위해 필요
$ sudo apt install python3-certbot-nginx

 

2. Nginx 웹 서버에 HTTPS를 적용한다.

# certbot이 알아서 모든 과정을 처리해준다.
sudo certbot --nginx

# 인증서만 발급하고 Nginx 설정 파일을 직접 수정하고 싶다면 다음과 같이 입력한다.
sudo certbot certonly --nginx

 

3. 2번 명령어를 입력하면 인증서 발급과 관련된 내용이 출력될 텐데, 이메일을 입력하고, HTTPS를 적용할 도메인을 입력하는 등의 과정이다. 전부 입력해주자.

 

4. Success라는 문장과 함께 인증서와 인증 키가 발급된 위치가 출력되며 과정이 종료된다. 이제 본인의 Nginx 설정 파일에 들어가보자. 참고로 내가 사용한 설정 파일 경로는 /etc/nginx/conf.d/default.con이다.(최근 추천되는 방식은 이렇게 conf.d에 .conf 확장자를 가진 설정 파일을 두는 것이라고 한다. 예전 방식은 /etc/nginx/sites-available에 설정 파일을 두고, /etc/nginx/sites-enabled에 해당 설정 파일의 심볼릭 링크를 추가하는 것이다.)

server {
    include /etc/nginx/conf.d/service-url.inc;

    server_name domain.com;

    # /api, /api-docs, /swagger-ui 경로로 들어오는 요청에 대한 설정
    location ~ ^/(api|api-docs|swagger-ui) {
        proxy_pass $service_url;
        proxy_set_header Host $host;
        proxy_set_header X-Real-IP $remote_addr;
        proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
        proxy_set_header X-Forwarded-Host $server_name;
    }

    listen [::]:443 ssl ipv6only=on; # managed by Certbot
    listen 443 ssl; # managed by Certbot
    ssl_certificate /etc/letsencrypt/live/domain.com/fullchain.pem; # managed by Certbot
    ssl_certificate_key /etc/letsencrypt/live/domain.com/privkey.pem; # managed by Certbot
    include /etc/letsencrypt/options-ssl-nginx.conf; # managed by Certbot
    ssl_dhparam /etc/letsencrypt/ssl-dhparams.pem; # managed by Certbot

}
server {
    if ($host = domain.com) {
        return 301 https://$host$request_uri;
    } # managed by Certbot



    listen 80 default_server;
    listen [::]:80 default_server;

    server_name domain.com;
    return 404; # managed by Certbot


}

 

certbot이 알아서 설정 파일을 건드려서 HTTPS를 적용해주었다. certbot이 바꾼 부분은 '# managed by Certbot'이라는 주석이 추가되어 있는 모습을 확인할 수 있다. 설정 파일에서 보듯 이제 해당 도메인은 HTTPS로 접근할 수 있을 뿐만 아니라, HTTP로 접근하더라도 자동적으로 HTTPS로 리다이렉트가 이루어진다.

 

SSL 인증서 자동 갱신?

기본적으로 Let's Encrypt에서 제공하는 무료 인증서에는 90일 기한이 있다. 따라서 90일마다 새로 갱신해서 인증서를 교체해주는 귀찮은 절차가 필요하지만, 공식 문서에 따르면 대부분의 경우에는 자동 갱신 기능이 포함되어 있다고 한다.

물론 자동 갱신이 되지 않는 경우도 존재하므로, 아래 내용에 포함된 링크에 들어가서 안내 절차에 관련 내용이 존재하지 않는다면 자동 갱신이 포함되어 있으니 추가 조치를 취하지 않아도 된다는 모양이다.

Automated Renewals
Most Certbot installations come with automatic renewals preconfigured. This is done by means of a scheduled task which runs certbot renew periodically.

If you are unsure whether you need to configure automated renewal:

Review the instructions for your system and installation method at https://certbot.eff.org/instructions. They will describe how to set up a scheduled task, if necessary. If no step is listed, your system comes with automated renewal pre-installed, and you should not need to take any additional actions.

 

자동 갱신이 포함되어 있지 않거나, 포함되어 있다는 사실에 확신이 안 생긴다면 리눅스의 crontab을 활용한 수동 갱신 설정 가이드를 참조해보자.

https://eff-certbot.readthedocs.io/en/latest/using.html#setting-up-automated-renewal

만약 이러한 추가 작업을 하지 않더라도 90일이 되기 직전에 등록했던 이메일로 안내 메일이 발송되므로 서비스에 갑자기 접속이 안 되는 불상사는 피할 수 있을 듯 하다. 

 

참조

https://nginxstore.com/blog/nginx/lets-encrypt-%EC%9D%B8%EC%A6%9D%EC%84%9C%EB%A1%9C-nginx-ssl-%EC%84%A4%EC%A0%95%ED%95%98%EA%B8%B0/

https://eff-certbot.readthedocs.io/en/latest/using.html#setting-up-automated-renewal

'Note > Infra' 카테고리의 다른 글

무중단 배포  (0) 2024.04.28
[Docker] Docker Compose로 Container에 환경변수 주입하기  (0) 2024.01.14

블로그의 정보

eel.log

eelseungmin

활동하기