acme.sh 自动化配置证书,永久免费 SSL

acme.sh 实现了 ACME 协议,可从 Let’s Encrypt 免费申请 SSL 证书,并通过 cron 自动续期。

本文只讲两件事:安装 acme.sh,以及用阿里云 DNS API 完成域名验证、申请证书、部署到 Nginx。示例域名以 tiaobug.comwww.tiaobug.com 为例,root 或非 root 用户均可操作。

安装 acme.sh

1
curl https://get.acme.sh | sh -s email=i@tiaobug.com   # 改成自己的邮箱

如果访问 GitHub 有困难,可用 Gitee 镜像:

1
2
3
git clone https://gitee.com/neilpang/acme.sh.git
cd acme.sh
./acme.sh --install -m i@tiaobug.com

安装完成后重新打开终端,或执行:

1
source ~/.bashrc

验证安装:

1
acme.sh --version

安装脚本会自动添加 cron 定时任务,用于证书自动续期:

1
2
3
crontab -l
# 示例输出:
# 24 21 * * * "/root/.acme.sh"/acme.sh --cron --home "/root/.acme.sh" > /dev/null

所有文件都在 ~/.acme.sh/ 目录下,不修改系统其他文件。


第一次使用:阿里云 DNS 申请证书

DNS 验证的好处是不需要服务器开放 80 端口,只要域名在阿里云解析即可。配合阿里云 DNS API,验证记录会自动添加和删除,续期也全自动。

1. 创建阿里云 AccessKey

  1. 登录 阿里云 RAM 控制台
  2. 身份管理 → 用户 → 创建用户
  3. 登录方式勾选 OpenAPI 调用访问
  4. 创建完成后,立即保存 AccessKey ID 和 AccessKey Secret(Secret 只显示一次)
  5. 给用户授权:搜索并添加 **AliyunDNSFullAccess**(云解析 DNS 完全控制权限)

建议单独建一个 RAM 子用户,不要用主账号 AccessKey。

2. 配置 API 凭证(仅第一次需要)

在服务器上执行,把下面的值换成自己的:

1
2
export Ali_Key="你的AccessKeyId"
export Ali_Secret="你的AccessKeySecret"

执行一次带 --dns dns_ali 的签发命令后,acme.sh 会把这两个变量自动写入 ~/.acme.sh/account.conf,以后不需要再 export。

也可以手动写入(可选):

1
2
3
echo "export Ali_Key='你的AccessKeyId'" >> ~/.bashrc
echo "export Ali_Secret='你的AccessKeySecret'" >> ~/.bashrc
source ~/.bashrc

3. 申请证书

1
2
3
acme.sh --issue --dns dns_ali \
-d tiaobug.com \
-d www.tiaobug.com

命令执行过程:

  1. acme.sh 通过阿里云 API 自动添加 _acme-challenge TXT 记录
  2. Let’s Encrypt 验证域名所有权
  3. 验证通过后签发证书,并自动删除临时 TXT 记录

成功后证书保存在:

1
2
3
4
5
~/.acme.sh/tiaobug.com_ecc/
├── tiaobug.com.cer # 域名证书
├── tiaobug.com.key # 私钥
├── ca.cer # 中间证书
└── fullchain.cer # 完整证书链(Nginx 用这个)

如果失败,常见原因:

  • Ali_Key / Ali_Secret 未配置或写错
  • RAM 用户没有 DNS 权限
  • 域名不在当前阿里云账号下

4. 安装证书到指定目录

不要把 Nginx 直接指向 ~/.acme.sh/ 里的文件。用 --install-cert 把证书复制到固定路径,并设置续期后自动 reload Nginx:

1
2
3
4
5
6
mkdir -p /home/tiaobug/ssl/tiaobug.com/

acme.sh --install-cert -d tiaobug.com -d www.tiaobug.com \
--key-file /home/tiaobug/ssl/tiaobug.com/key.pem \
--fullchain-file /home/tiaobug/ssl/tiaobug.com/cert.pem \
--reloadcmd "service nginx force-reload"

说明:

  • --key-file:私钥输出路径
  • --fullchain-file:完整证书链输出路径(Nginx 的 ssl_certificate 指向这个文件)
  • --reloadcmd:证书续期后自动执行的命令

这里用 service nginx force-reload,不要用 reload——普通 reload 不会重新加载已更换的证书文件。

5. 配置 Nginx

HTTP 跳转 HTTPS:

1
2
3
4
5
6
7
8
server {
listen 80;
listen [::]:80;

server_name tiaobug.com www.tiaobug.com;

return 301 https://$host$request_uri;
}

HTTPS 站点:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
server {
listen 443 ssl;
listen [::]:443 ssl;

server_name tiaobug.com www.tiaobug.com;

ssl_certificate /home/tiaobug/ssl/tiaobug.com/cert.pem;
ssl_certificate_key /home/tiaobug/ssl/tiaobug.com/key.pem;

ssl_session_cache shared:SSL:10m;
ssl_session_timeout 10m;
ssl_protocols TLSv1.2 TLSv1.3;

root /home/tiaobug/web-sites/tiaobug.com/;
index index.html;

location / {
try_files $uri $uri/ =404;
}
}

检查配置并重载:

1
2
nginx -t
nginx -s reload

注意 ssl_certificatessl_certificate_key 不要写反:前者是证书(.pem / fullchain),后者是私钥(key.pem)。


后续新增域名证书

AccessKey 已在第一次使用时保存,新增域名不需要再配置 Ali_Key / Ali_Secret,直接签发即可。

example.com 为例:

1
2
3
4
5
6
7
8
9
10
11
12
# 1. 申请证书
acme.sh --issue --dns dns_ali \
-d example.com \
-d www.example.com

# 2. 安装到指定目录
mkdir -p /home/tiaobug/ssl/example.com/

acme.sh --install-cert -d example.com -d www.example.com \
--key-file /home/tiaobug/ssl/example.com/key.pem \
--fullchain-file /home/tiaobug/ssl/example.com/cert.pem \
--reloadcmd "service nginx force-reload"

然后在 Nginx 里新增对应的 server 块:

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
server {
listen 80;
listen [::]:80;
server_name example.com www.example.com;
return 301 https://$host$request_uri;
}

server {
listen 443 ssl;
listen [::]:443 ssl;

server_name example.com www.example.com;

ssl_certificate /home/tiaobug/ssl/example.com/cert.pem;
ssl_certificate_key /home/tiaobug/ssl/example.com/key.pem;

ssl_session_cache shared:SSL:10m;
ssl_session_timeout 10m;
ssl_protocols TLSv1.2 TLSv1.3;

root /home/tiaobug/web-sites/example.com/;
index index.html;

location / {
try_files $uri $uri/ =404;
}
}

如果只加子域名(例如 api.example.com),签发时只写需要的域名即可:

1
2
3
4
5
6
7
acme.sh --issue --dns dns_ali -d api.example.com

mkdir -p /home/tiaobug/ssl/api.example.com/
acme.sh --install-cert -d api.example.com \
--key-file /home/tiaobug/ssl/api.example.com/key.pem \
--fullchain-file /home/tiaobug/ssl/api.example.com/cert.pem \
--reloadcmd "service nginx force-reload"

查看证书信息

1
acme.sh --info -d tiaobug.com

输出包含证书路径、过期时间、续期状态等。


自动续期

安装时写入的 cron 任务会在证书到期前自动续期,续期成功后执行 --reloadcmd 让 Nginx 加载新证书,无需手动操作。

Notice: 正常情况下,这里会有一个基于utteranc.es的留言系统,如果看不到,可能要想想办法才能看到。

Powered by Hexo and Hexo-theme-hiker

Copyright © 2012 - 2026 tiaobug.com All Rights Reserved.

鲁ICP备2024124237号-1