之前陆续写过 Linux 下的 Let’s Encrypt 证书的获取及更新 , 这里更新一篇 Docker 下的操作方式 , 更加通用且

方便维护、升级,同时也避免破坏本地的环境

Docker 安装

这里请参考 过往文章

首次申请证书

这里是通过部署 nginx 运行静态网站来进行申请 , 这里简单展示下 nginx 的部署文件

docker-compose.yml

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
# 使用说明 V3.2.0
version: '3.0'
services:
nginx:
hostname: nginx
restart: always
logging:
driver: "json-file"
options:
max-size: "500m"
container_name: nginx
image: nginx:latest
ports:
- 80:80
- 443:443
volumes:
- ./conf/nginx.conf:/etc/nginx/nginx.conf
- ./conf/custom/:/etc/nginx/conf/
- ./www/:/etc/nginx/html/
- ./logs/:/var/log/nginx/
- ./site:/usr/share/nginx/html # nginx 保存challenges目录
- /data/apps/letsencrypt/etc/live:/letsencrypt/live # 当前证书目录
- /data/apps/letsencrypt/etc/archive:/letsencrypt/archive # 历史证书目录
- /data/apps/letsencrypt/dhparam-2048.pem:/letsencrypt/dhparam-2048.pem # 使用2048位DH(Diffie-Hellman)参数

这里将我们的静态网页放在 ./www 目录下, 然后解析对应域名到该服务器 , 添加域名nginx文件到配置目录并且启动容器和 reload nginx. 配置文件示例如下

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
server {
listen 80;
server_name 域名A,域名B;
charset utf-8;


# 高优先级,仅用于更新证书
location ~ /.well-known/acme-challenge {
allow all;
root /usr/share/nginx/html;
}

error_page 500 502 503 504 /50x.html;
location = /50x.html {
root html;
}

root /usr/share/nginx/html;
index index.html index.htm;

}

然后申请证书

1
2
3
4
5
6
7
8
9
docker run --rm -it \
-v /data/apps/letsencrypt/etc:/etc/letsencrypt \
-v /data/apps/letsencrypt/log:/var/log/letsencrypt \
-v /data/apps/letsencrypt/lib:/var/lib/letsencrypt \
-v /data/apps/nginx/site:/data/letsencrypt \
certbot/certbot:latest certonly --webroot \
--email 邮箱 --agree-tos --no-eff-email \
--webroot-path=/data/letsencrypt \
-d 域名A -d 域名B

运行结束会在 /data/apps/letsencrypt/live 目录下出生证书文件和私钥文件

生成 2048位DH

1
openssl dhparam -out ./dhparam-2048.pem 2048

拷贝到自定义目录 , 然后修改nginx文件

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
server {
listen 80;
server_name 域名;
charset utf-8;

location / {
root /etc/nginx/html/ycc;
index index.html index.htm;
}

# 高优先级,仅用于更新证书
location ~ /.well-known/acme-challenge {
allow all;
root /data/letsencrypt;
}



error_page 500 502 503 504 /50x.html;
location = /50x.html {
root html;
}

}

# 处理https请求
server {
listen 443 ssl;
server_name 域名;

server_tokens off;

ssl_certificate /letsencrypt/live/web.evdances.com/fullchain.pem;
ssl_certificate_key /letsencrypt/live/web.evdances.com/privkey.pem;

ssl_buffer_size 8k;

ssl_dhparam /letsencrypt/dhparam-2048.pem; # 使用2048位DH参数,加强安全

ssl_protocols TLSv1.2 TLSv1.1 TLSv1;
ssl_prefer_server_ciphers on;
ssl_ciphers ECDH+AESGCM:ECDH+AES256:ECDH+AES128:DH+3DES:!ADH:!AECDH:!MD5;

ssl_ecdh_curve secp384r1;
ssl_session_tickets off;

# OCSP stapling
ssl_stapling on;
ssl_stapling_verify on;
resolver 8.8.8.8;

location / {
root /etc/nginx/html/ycc;
index index.html index.htm;
}
}


重启容器, reload nginx

更新证书

1
2
3
4
5
6
7
8
9
#!/bin/bash
# 更新ssl证书
docker run -it --rm \
-v /data/apps/letsencrypt/etc:/etc/letsencrypt \
-v /data/apps/letsencrypt/lib:/var/lib/letsencrypt \
-v /data/apps/letsencrypt/log:/var/log/letsencrypt \
-v /data/apps/nginx/site:/data/letsencrypt \
certbot/certbot renew --webroot \
-w /data/letsencrypt --quiet && docker kill --signal=HUP nginx

新增定时任务 , 每月15号尝试更新证书

crontab -e

1
0 0 15 * * root sh /data/deploy/renew.sh

参考链接