코딩마을방범대
CertBot으로 SSL 인증서 발급받기 본문
https 에 취소선이 그어져 있는 경우
https는 http와 다르게 SSL/TSL 보안 방식(암호화 기반 인터넷 보안 프로토콜)을 사용한다 (관련 포스트) SSL과 TSL 원래 웹에서의 데이터는 가로채면 누구나 읽을 수 있는 일반 텍스트 형태로 전송되었
sweet-rain-kim.tistory.com
일전에 위와 같은 포스트를 작성한 적이 있다.
이 때는 원인만 알아봤다면 이번엔 실질적으로 해결 방안을 진행해볼 것이다.
CertBot을 통해 let's encrypt 인증서를 발급 받아서 적용 시킬 예정이다.
- certbot 가이드: https://certbot.eff.org/instructions?ws=nginx&os=ubuntuxenial (nginx, ubuntu16)
CertBot은 인증서 발급을 진행하기 위해 아래 과정을 진행한다.
- Certbot 인증서 요청
- 요청한 도메인 소유주 확인
- 인증서 발급
위 세가지 방법 중 요청 도메인의 소유주를 확인할 수 있는 방법은 아래와 같이 세가지가 있다.
- standalone - 가상 웹서버를 가동하여 도메인 소유주 확인
- webroot - 자신의 웹서버가 제공하는 특정 파일로 도메인 소유주 확인
- dns - dns 레코드에 특정 값을 작성하여 도메인 소유주 확인
standalone
- 80번포트가 개방되어야함 -> 이미 실행중인 서비스, 데몬이 존재시, 이를 중단해야함
- 와일드카드 서브도메인 사용불가 (*.example.com)
- 도메인이 자신의 서버에 연결되어야함 (A레코드를 자신의 서버로)
- 와일드카드 서브도메인 인증서가 필요하지 않다면 권장
webroot
- 서버 중단없이 발급
- 와일드카드 서브도메인 사용불가 (*.example.com)
- 웹서버에 사전 세팅이 필요
dns
- 도메인이 연결된 DNS에 TXT 레코드를 생성해서 인증서를 발급하는 방식
- 와일드카드 서브도메인 사용 가능 (*.example.com)
- 인증서 발급 과정에 웹 서버가 필요 없음
- 외부에서 TXT 레코드를 입력할 수 있도록 DNS가 API를 제공하는 경우에는 갱신 과정을 자동으로 처리할 수 있음
사전 준비
1. 서버에 Nginx, Apache 등 구축 (webroot를 이용할 경우)
아래 포스트를 참고하여 Nginx, Apache 구축하기
우분투에서 Nginx 구축
웹서버 Nginx & Apache (이전 포스트) 1. Nginx 설치 apt 업데이트 후 Nginx 설치 Nginx 설치 시 자동으로 실행됨 $ sudo apt update $ sudo apt-get install nginx Nginx 실행 $ sudo service nginx start # or $ sudo systemctl start nginx
sweet-rain-kim.tistory.com
우분투에서 Apache를 이용해 WAS 연동하기
Apache와 Nginx의 차이점 포스트 우분투에서 Nginx 구축하기 포스트 웹서버(Apache)와 미들웨어(Tomcat) 연동하기 연동 방법 세가지 AJP Apache 웹서버가 외부 시스템과 연동하기 위한 프로토콜 연결 방식
sweet-rain-kim.tistory.com
2. snapd 설치
CertBot 설치 페이지에서 snapd 로 설치하는 것을 권장하고 있으므로 설치 진행
// 설치
$ sudo apt-get install snapd
$ sudo snap install core;
// 최신 버전으로 업데이트
$ sudo snap refresh core;
설치 완료 후 버전 확인
$ snap version
3. CertBot이 설치되어 있을 경우 삭제
apt, dnf, yum 같은 OS 패키지 관리자를 통해 CertBot이 설치돼있는 경우
충돌로 인해 snap의 CertBot이 아닌 패키지 관리자의 CertBot이 실행되지 않게 하기 위해 삭제 진행
// apt
$ sudo apt-get remove certbot
// dnf
$ sudo dnf remove certbot
// yum
$ sudo yum remove certbot
4. CertBot 설치
$ sudo snap install --classic certbot
반대로 삭제는?
$ sudo snap remove certbot
5. CertBot 구동 가능 여부 확인
$ sudo ln -s /snap/bin/certbot /usr/bin/certbot
소유주 확인 방법에 따른 인증서 발급 방법 (CertOnly일 경우)
모든 명령어는 실행 후 약관 동의 등의 절차가 필요함
- 이메일 주소 입력
- 약관 동의 ( Y / N )
- 이메일을 통해 Let's Encrypt 프로젝트 정보를 받아볼지 ( Y / N )
- 인증서를 발급할 도메인 입력 ( 도메인 입력 시 아래와 같이 여러개 입력 가능 )
example.com www.exapme.com subdomain1.example.com subdomain2.example.com
인증서는 /etc/letsencrypt/live 폴더에 위치한다.
※ 인증서 발급 시 자동으로 https를 구성하지 않고 인증서만 발급 받는 방법 ( 수동 설정 시 )
certbot 뒤에 certonly를 붙여서 실행
$ sudo certbot certonly --nginx
standalone
별도의 서비스를 이용하지 않고 80번 포트를 이용하는 방법
1. 인증서 발급
$ sudo certbot certonly --standalone
webroot
서비스를 이용하여 서버 중단 없이 발급 가능한 방법
1. 인증서 발급
// apache
$ sudo certbot certonly --apache
//nginx
$ sudo certbot certonly --nginx
2. 서비스 conf 파일 수정
// nginx
$ sudo vi /etc/nginx/conf.d/default.conf
$ sudo vi /etc/nginx/nginx.conf
// apahce
$ sudo vi /etc/apache2/sites-available/default-ssl.conf
내용 ( Nginx )
server {
listen 80;
listen 443 ssl;
server_name [도메인];
ssl_certificate /etc/letsencrypt/live/[도메인]/fullchain.pem;
ssl_certificate_key /etc/letsencrypt/live/[도메인]/privkey.pem;
location / {
root /usr/share/nginx/html;
index index.html index.htm;
}
location = /50x.html {
root /usr/share/nginx/html;
}
}
내용 ( Apache )
※ 아래처럼 ProxyPass 가능
<VirtualHost *:443>
ServerName [도메인]:443
ServerAdmin [메일 주소]
DocumentRoot /var/www/[도메인]
SSLEngine on
# ssl 인증서
SSLCertificateFile "/etc/letsencrypt/live/[도메인]/cert.pem"
# 개인키
SSLCertificateKeyFile "/etc/letsencrypt/live/[도메인]/privkey.pem"
# 중간CA증명서 (없으면 안해도됨)
SSLCertificateChainFile "/etc/letsencrypt/live/[도메인]/fullchain.pem"
<Location "/test/url">
RewriteEngine on
RewriteCond %{HTTP:UPGRADE} ^websocket$ [NC]
RewriteCond %{HTTP:CONNECTION} Upgrade [NC]
RewriteRule .* ws://[ip주소:포트번호]%{REQUEST_URI} [P]
ProxyPass http://[ip주소:포트번호]/test/url/
ProxyPassReverse http://[ip주소:포트번호]/test/url/
</Location>
</VirtualHost>
3. 문법 이상 유무 확인
$ sudo nginx -t
$ sudo apache2 -t
4. 서비스 재실행
$ sudo nginx -s reload
$ sudo service apache2 restart
인증서 갱신에 대한 정보
et's encrypt 에서 발급하는 인증서는 유효기간이 3개월이기 때문에 주기적으로 갱신을 해 주어야 한다.
certbot 의 경우에도 갱신을 위한 명령어가 존재한다.
위 과정엔 자동 갱신이 포함된 상태로 발급이 되어 자동으로 만료되기 20 일 전 쯤 갱신을 해준다.
해당 예약 명령은 systemd.timer 에 등록되어 있다.
$ systemctl list-timers
NEXT LEFT LAST PASSED UNIT
n/a n/a 금 2023-04-28 15:43:28 KST 1 months 25 days ago ureadahead-stop.timer
금 2023-06-23 13:26:08 KST 1h 50min left 금 2023-06-23 06:10:49 KST 5h 25min ago certbot.timer
금 2023-06-23 15:07:43 KST 3h 31min left 금 2023-06-23 01:54:49 KST 9h ago apt-daily.timer
토 2023-06-24 06:11:49 KST 18h left 금 2023-06-23 06:13:47 KST 5h 22min ago apt-daily-upgrade.timer
인증서 갱신 주기 변경
$ sudo vi /etc/letsencrypt/renewal/[도메인].conf
# renew_before_expiry = 30 days
# -> 아래와 같이 변경
renew_before_expiry = 90 days
SSL 인증서 상태 확인
아래 명령어 실행 시 발급되어 있는 인증서들의 상태를 출력해준다.
$ sudo certbot certificates
인증서 갱신
갱신 테스트
--dry-run 옵션을 주면 실제 갱신 진행이 아닌 오류 발생여부 체크가 가능하다.
$ sudo certbot renew --dry-run
수동 갱신
서버의 다운 등의 이유로 자동 갱신이 되지 않은 경우 수동으로 갱신이 가능하다.
$ sudo certbot renew
// 만료일 무시하고 인증서 갱신
$ sudo certbot renew --force-renew --cert-name example.com
--cert-name : 인증서를 지정하여 갱신 가능
--force-renew : 만료일 무시
※ webroot 방식의 경우 서비스 재시작 필요
// apache
$ sudo service apache2 restart
// nginx
$ sudo service nginx restart
💡 발생할 수 있는 ERROR!
1. Another Instance of Certbot is Already Running
인증서를 만드는 도중 이름을 잘 못 설정해서 무의식 중에 Ctrl + Z 를 눌러버렸다!
이후 다시 명령어를 실행하니 아래와 같은 오류가 발생하면서 명령어 실행이 되지 않았다.
Another Instance of Certbot is Already Running
아래 명령어로 pid 번호를 알아내 kill 을 해봐도 죽여지지 않았다!
$ ps -ef | grep certbot
찾아보니 갱신 프로세스 중에 서버가 예기치 않게 재부팅되었을 수 있는 경우 Certbot이 실행되고 있지 않지만,
일부 .certbot.lock 파일이 남아 있을 수 있다고 한다.
아래 명령어를 통해 .certbot.lock 파일이 존재하는지 확인하고 존재하는 경우 잠금 파일을 제거한다.
$ sudo find / -type f -name ".certbot.lock" -exec rm {} \;
2. Timeout during connect (likely firewall problem)
인증서 생성 시 아래와 같이 오류가 발생하였다.
방화벽 문제이며, 나의 경우 nginx 를 이용했는데 nginx의 방화벽을 HTTP로 등록해두어서 발생하는 문제였다.
우분투에서 Nginx 구축
웹서버 Nginx & Apache (이전 포스트) 1. Nginx 설치 apt 업데이트 후 Nginx 설치 Nginx 설치 시 자동으로 실행됨 $ sudo apt update $ sudo apt-get install nginx Nginx 실행 $ sudo service nginx start # or $ sudo systemctl start nginx
sweet-rain-kim.tistory.com
위의 포스트를 보면 2. 방화벽 설정 하는 부분이 있다.
아래 명령어 실행 시 방화벽으로 설정 가능한 리스트들이 출력되는데 나의 경우 Full이나 HTTPS가 아닌 HTTP로 등록해둬서 포트 443이 허용되지 않은 것이였다.
$ sudo ufw app list
Nginx HTTP : 포트 80번만 허용 (암호화되지 않은 웹 트래픽)
Nginx HTTPS : 포트 443번만 허용 (SSL/TLS 암호화용)
Nginx Full : 포트 80, 443번 허용
방화벽 설정 상태는 아래 명령어를 통해 확인 가능하며,
ufw allow 명령어를 통해 설정해주면 된다.
$ sudo ufw status
$ sudo ufw allow 'Nginx Full'
참고사이트
certbot 으로 let's encrypt 인증서 발급받기
'🎃 기타 > 상식 ❗' 카테고리의 다른 글
Base64 인코딩이란? (0) | 2023.08.02 |
---|---|
Intellij IDEA 유용한 단축키 모음 (0) | 2023.07.24 |
Load Balancing 이란? (0) | 2023.06.16 |
https 에 취소선이 그어져 있는 경우 (0) | 2023.06.15 |
버전과 빌드 버전의 차이 (0) | 2023.06.09 |