본문 바로가기
카테고리 없음

[Server] letsencrypt 인증서로 HTTPS 적용하기

by teamnova 2024. 2. 10.
728x90

오늘은 자신의 프로젝트에 https를 적용하는 방법을 알아보겠습니다.

 

먼저 HTTPS는 Hypertext Transfer Protocol Secure의 약자로 기존 HTTP 방식에 보안을 더하기 위해 클라이언트와 서버가 주고 받는 데이터를 암호화한 방식입니다.

기존 HTTP 방식에서는 데이터 암호화를 따로 해주는 게 아닌 이상 암호화되지 않은채로  서버로 전송되기 때문에 도중에 데이터가 오염될 가능성과 유출될 가능성이 있습니다. 그래서 HTTPS를 적용해야 하지만 꽤나 귀찮은 작업이기 때문에 오늘은 간단하게 HTTPS 인증서를 받아보고 적용하는 방법을 알아보겠습니다.

 

오늘 저희에게 필요한 것은 nginx 서버와 nip.io , Docker , Let's Encrypt , Cerbot 입니다.

서버를 제외하고 각각에 대해 간단히 설명드리면

 

nip.io : 일종의 와일드카드 DNS 서비스로 자신의 서버 ip를 도메인주소로 사용할 수 있게 해줍니다. 예를 들어 127.0.01.nip.io 라는 도메인 주소를 사용하면 127.0.0.1로 연결해주기 때문에 도메인 주소를 입력해야하는 테스트나 개발 환경에서 유용합니다.

 

Docker : 애플리케이션을 컨테이너라는 격리된 환경에서 실행하는 플랫폼으로 리눅스 상에서 효율적으로 이미지를 구축할 수 있게 해주고 그 이미지를 기반으로 컨테이너를 실행할 수 있고 다시 특정 컨테이너의 상태를 변경해 이미지로 만들 수 있습니다. 이 이미지는 도커만 있다면 필요할 때 언제 어디서나 컨테이너로 실행할 수 있습니다. 또 이러한 컨테이너를 사용하면 프로그램과 그 모든 종속성을 함께 포장하기 때문에 어떤 환경에서든 동일하게 작동합니다. 이는 "내 컴퓨터에서는 잘 작동하는데" 와 같은 의견이 나오는 문제들을 해결해줍니다.

 

Let's Encrypt : 무료, 자동화된 오픈 소스의 인증 기관으로 웹사이트에 SSL/TLS 인증서를 제공해 HTTPS를 통한 보안 연결을 가능하게 해줍니다.

 

Certbot : 위에서 발급한 인증서를 자동으로 설치하고 갱신하는 도구입니다. 웹 서버 소프트웨어와의 통합을 자동화해 SSL/TLS 인증서의 설치 및 갱신 프로세를 간소화해줍니다.

 

1. 서버 포트 개방

먼저 서버 SSL 인증서 발급을 위해 80 포트를 개방해야 합니다. 이 때 추가로 HTTPS에서 사용할 443 포트도 개방해줍니다. 저는 AWS에서 ec2를 사용하고 있기 때문에 AWS console에서 진행했습니다.

 

<AWS EC2 보안그룹 탭>

 

<HTTP(80), HTTPS(443) 포트 추가>

 

2. Docker 설치

SSL 인증서 발급 시 Docker를 사용해서 Certbot을 실행하기 때문에 먼저 Docker를 설치해줍니다.

이를 위해 서버 터미널로 접속해 다음 명령을 실행해줍니다.

curl -fsSL https://get.docker.com -o get-docker.sh
sudo sh get-docker.sh

 

3. Docker로 SSL 인증서 발급하기

Let's Encrypt 인증서를 발급할 때 Docker를 사용해 certbot + standalone 방식으로 발급해보겠습니다.

CertBot 도커 공식문서
https://eff-certbot.readthedocs.io/en/stable/install.html#alternative-1-docker

 

Get Certbot — Certbot 2.6.0 documentation

Note Certbot is most useful when run with root privileges, because it is then able to automatically configure TLS/SSL for Apache and nginx. Certbot is meant to be run directly on a web server, normally by a system administrator. In most cases, running Cert

eff-certbot.readthedocs.io

 

 

certbot 도커 이미지를 실행할 때 standalone 방식으로 발급하면 80번 포트가 필요해 도커에서 80번 포트를 열어주면서 실행하겠습니다.

docker run -it --rm --name certbot \
            -v "/etc/letsencrypt:/etc/letsencrypt" \
            -v "/var/lib/letsencrypt:/var/lib/letsencrypt" \
            -p 80:80 \
            certbot/certbot certonly

 

그 다음 실행이 되면 standalone 과 webroot 방식 중 standalone 방식을 선택하겠습니다.

대신 해당 사이트의 네트워킹을 이용해서 사이트 유효성을 확인하고 지급하는 방식이라 발급 전에 서버를 중단하고 발급 완료 후 서버를 다시 시작해야 한다.

How would you like to authenticate with the ACME CA?
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
1: Runs an HTTP server locally which serves the necessary validation files under
the /.well-known/acme-challenge/ request path. Suitable if there is no HTTP
server already running. HTTP challenge only (wildcards not supported).
(standalone)
2: Saves the necessary validation files to a .well-known/acme-challenge/
directory within the nominated webroot path. A seperate HTTP server must be
running and serving files from the webroot path. HTTP challenge only (wildcards
not supported). (webroot)
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Select the appropriate number [1-2] then [enter] (press 'c' to cancel): 1

 

그러면 이메일 주소랑 약관들을 입력해준 뒤 도메인을 물어보는 데 이때 아까 말한 nip.io를 사용해서 도메인 주소를 입력해주면 됩니다.

Please enter the domain name(s) you would like on your certificate (comma and/or
space separated) (Enter 'c' to cancel): 127.0.0.1.nip.io

 

도메인을 입력하고 나면 자동으로 인증을 거치고 인증서 발급에 성공했다고 나옵니다.

인증서는 /etc/letsencrypt/live/<domain>/fullchain.pem
개인키는 /etc/letsencrypt/live/<domain>/privkey.pem 에서 찾을 수 있습니다.

참고로 이 인증서는 90일마다 갱신해줘야 하고, 인증서 갱신도 CertBot을 사용해서 할 수 있습니다.

 

4. 인증서 적용하기

먼저 nginx 설정 파일을 엽니다.

cd /etc/nginx/sites-available 
sudo vim default

 

그 후 설정 파일을 다음과 같이 설정해줍니다.

server {
    
    # https(ssl) 접속에 대한 설정.
    listen 443 ssl http2;
    server_name  <도메인 주소> www.<도메인 주소>;
    

		
        # 발급 받은 인증서 파일에 대한 경로 설정.
		# managed by Certbot(SSL)
		ssl_certificate /etc/letsencrypt/live/<도메인 주소>/fullchain.pem; 
		ssl_certificate_key /etc/letsencrypt/live/<도메인 주소>/privkey.pem; 
		# include /etc/letsencrypt/options-ssl-nginx.conf;
		# ssl_dhparam /etc/letsencrypt/ssl-dhparams.pem;
        	

    charset utf-8;
    access_log  /var/log/nginx/access.log  main;
    error_log   /var/log/nginx/error.log   warn;

    location / {
        proxy_redirect     off;
        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-Proto $scheme;

        proxy_pass http://127.0.0.1:13000;
    }

    # redirect server error pages to the static page /50x.html
    error_page   500 502 503 504  /50x.html;
    location = /50x.html {
        root   /usr/share/nginx/html;
    }
}
# ========= 추가된 부분 =========
# http로 접속 시에 (일반적으로 80포트) https로 리다이렉트 되도록 설정.
server {
    listen        80;
    server_name   <도메인 주소> www.<도메인 주소>;
    return 301 https://<도메인 주소>$request_uri;
}

 

다음 중단했던 서버를 다시 실행해주겠습니다.

service nginx start

 

이러고 웹브라우저를 통해 사이트에 들어가 주소창 왼쪽 버튼을 클릭하면 인증서가 적용된 걸 확인할 수 있습니다.