nginx + ssl(letsencrypt) + auto ssl renew w
[조건]
- 표준(기본) nginx 설치
- nginx 서비스 무중단 letsencrypt 인증서 자동 갱신
- 웹접속 http -> https
- 기본 표준 설치 상태 활용
[툴설치]
# apt update
# apt install certbot
# apt install python3-certbot-nginx
- 설치된 nginx 없는 상태 -
[nginx 설치 시작]
# apt install nginx
[방화벽]
# ufw enable
# ufw app list
-------------
Nginx Full
Nginx HTTP
Nginx HTTPS
-------------
# ufw allow 'Nginx Full'
# ufw status
------------------
Nginx Full ALLOW Anywhere
Nginx Full (v6) ALLOW Anywhere (v6)
----------------------
[nginx 설치 경로정보]
/etc/nginx/ - 웹 서버 메인 경로
/etc/nginx/nginx.conf - 웹 서버 nginx.conf
/usr/sbin/nginx - nginx 실행 파일
/run/nginx.pid - nginx.pid 파일
/var/www/html - 웹html루트
/usr/lib/systemd/system/nginx.service ex) service nginx status
/etc/nginx/sites-available/ <----- sites-available (각 설정사이트들)
/etc/nginx/sites-enabled/ <----- sites-enabled (sites-available/* 각 설정사이트들 중 실제 ln 적용할 사이트 경로)
■ /etc/nginx/nginx.conf
certbot --nginx 실행 전에 아래와 같이 기초 구성 <- server { 안에.. server_name mysite.kr; 도메인 명 필수 }
server {
listen 80 default_server;
root /var/www/html;
index index.html index.htm index.nginx-debian.html;
server_name mysite.kr;
location / {
try_files $uri $uri/ =404;
}
}
[nginx 실행/중지 등]
service nginx start
service nginx stop
service nginx reload
service nginx restart
# service nginx start - nginx 서비스 시작 상태에서 진행.
[letsencrypt 설치 시작]
# certbot --nginx
[ssl 경로정보]
/etc/letsencrypt/live/mysite.kr/
cert.pem chain.pem fullchain.pem privkey.pem
/etc/letsencrypt/renewal/mysite.kr.conf
※ certbot renew 으로 갱신할 때 사용되는 옵션들이 저장되어 있음.
※ certbot --nginx 으로 설치하여 갱신방식(authenticator , installer)이 nginx 로 되어 있음.
------------------------------------------------------------------------------------------
renew_before_expiry = 30 days
version = 1.21.0
archive_dir = /etc/letsencrypt/archive/mysite.kr
cert = /etc/letsencrypt/live/mysite.kr/cert.pem
privkey = /etc/letsencrypt/live/mysite.kr/privkey.pem
chain = /etc/letsencrypt/live/mysite.kr/chain.pem
fullchain = /etc/letsencrypt/live/mysite.kr/fullchain.pem
# Options used in the renewal process
[renewalparams]
account = 1f971017c331d297c9d61f08ff579c3e
authenticator = nginx
installer = nginx
#------------- standalone 방식으로 갱신할때 사용하는 옵션 --
#authenticator = standalone
#pre_hook = service nginx stop
#post_hook = service nginx start
-------------------------------------------------------------------------------------------
[참고] 위처럼 nginx 를 이용하지 않고, standalone 방식의 재발급이 필요한 경우라면...
아래처럼 nginx stop -> ssl갱신 -> nginx start 순으로 실행되게 설정(즉, nginx 웹서버가 일시 중단됨) - 불안정 상태 -
---------------------------------
[renewalparams]
account = 1f971017c331d297c9d61f08ff579c3e
authenticator = standalone
pre_hook = service nginx stop
post_hook = service nginx start
-------------------------------
※ 위 처럼 가동 중인 nginx 를 통해 인증서를 재발급 받게 되므로, nginx 중단 없이 ssl 이 정상 재발급 됨.
# /usr/bin/certbot renew --dry-run < --- Simulating 테스트(정상 발급 되는지 미리 확인)
[/etc/nginx/nginx.conf 설정 확인]
certbot --nginx 에 의해 자동 생성된 ssl 구문 확인 -> 환경에 맞게 수정.
user nginx;
worker_processes auto;
pid /run/nginx.pid;
include /etc/nginx/modules-enabled/*.conf;
events {
worker_connections 1024;
}
http {
include mime.types;
default_type application/octet-stream;
sendfile on;
#80
server {
listen 80;
root /var/www/html;
location / {
}
}
#443
server {
listen 443 ssl; # managed by Certbot
root /var/www/html;
#ssl-----------------------------------------
ssl_certificate /etc/letsencrypt/live/mysite.kr/fullchain.pem; # managed by Certbot
ssl_certificate_key /etc/letsencrypt/live/mysite.kr/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
#--------------------------------------------
location / {
index index.html index.htm index.php;
}
#monitoring
location /nginx_status {
stub_status;
}
#*.php-fpm
location ~ \.php$ {
try_files $uri =404;
include fastcgi.conf;
include fastcgi_params;
fastcgi_index index.php;
fastcgi_pass unix:/run/php/php8.1-fpm.sock;
}
}
}
[자동 ssl 갱신]
[참고]
/etc/cron.d/ 에 certbot 스크립트 자동 생성되어 있음.
------------------------
SHELL=/bin/sh
PATH=/usr/local/sbin:/usr/local/bin:/sbin:/bin:/usr/sbin:/usr/bin
0 */12 * * * root test -x /usr/bin/certbot -a \! -d /run/systemd/system && perl -e 'sleep int(rand(43200))' && certbot -q renew
------------------------
/usr/lib/systemd/system/ 에 certbot.service , certbot.timer 자동 생성되어 있음.
[certbot.service]
---------------------
[Unit]
Description=Certbot
Documentation=file:///usr/share/doc/python-certbot-doc/html/index.html
[Service]
Type=oneshot
ExecStart=/usr/bin/certbot -q renew
PrivateTmp=true
---------------------------
[certbot.timer]
----------------------
[Unit]
Description=Run certbot twice daily
[Timer]
OnCalendar=*-*-* 00,12:00:00
RandomizedDelaySec=43200
Persistent=true
[Install]
WantedBy=timers.target
--------------------------
※ 자동 생성된 /etc/cron.d/certbot 과 /usr/lib/systemd/system/ 아래 certbot.service, certbot.timer 조합이 복잡함. -> 단순화.
■ /etc/cron.d/certbot 내용 주석처리
------------------------
SHELL=/bin/sh
PATH=/usr/local/sbin:/usr/local/bin:/sbin:/bin:/usr/sbin:/usr/bin
#0 */12 * * * root test -x /usr/bin/certbot -a \! -d /run/systemd/system && perl -e 'sleep int(rand(43200))' && certbot -q renew
------------------------
■ certbot 갱신 서비스 중지
systemctl stop certbot.timer
service certbot stop
※ certbot.timer 가 자동 시작 등록되어 있어 reboot 시 재 가동, 서비스 미 사용 설정.
systemctl stop certbot.timer
service certbot stop
systemctl disable certbot.timer
---------
Removed /etc/systemd/system/timers.target.wants/certbot.timer.
---------
■ 단순하게 crontab 에 등록
# nano /etc/crontab
---------------------------------------------------------------------------------
00 5 * * * root /usr/bin/certbot renew >> /var/log/cron_certbotrenew.log 2>&1
-----------------------------------------------------------------------------------------------------
# service cron restart
# cat /var/log/letsencrypt/letsencrypt.log 파일에서 로그기록 확인가능.
# cat /var/log/cron_certbotrenew.log 파일에서 로그기록 확인가능.
끝.
[개선된 다른 방법 ★]
/etc/cron.d/certbot 만 사용(/etc/crontab 에는 설정 안함) / certbot.timer 중지, disable 사용안함.
■ certbot.timer 서비스 상태(is-active)에 따라 대응
1) certbot.timer 중지
systemctl stop certbot.timer
systemctl disable certbot.timer
2) /etc/cron.d/certbot 스크립트 개선
-----------------------------------
SHELL=/bin/sh
PATH=/usr/local/sbin:/usr/local/bin:/sbin:/bin:/usr/sbin:/usr/bin
0 5 * * * root test -x /usr/bin/certbot && ! systemctl is-active certbot.timer && perl -e 'sleep int(rand(600))' && certbot -q renew
---------------------------------
[설명]
0 5 * * * root test -x /usr/bin/certbot && ! systemctl is-active certbot.timer && perl -e 'sleep int(rand(600))' && certbot -q renew
※ 매일 05시 /usr/bin/certbot 실행파일 존재 && certbot.timer 가 active 가 아닌상태(즉 중지상태) && 10분 이내 랜덤 대기 후 갱신 실행.