在 CentOS 上实现 SSL 证书自动续签,最主流、最省心的方案是用 Certbot(Let’s Encrypt 官方工具) 或 acme.sh,两者都能做到到期前自动续期并重载 Web 服务。下面分别给出完整可直接执行的配置步骤。

一、方案一:Certbot(推荐,Nginx/Apache 友好)

Certbot 是 Let’s Encrypt 官方客户端,支持自动申请、自动续期、自动修改 Nginx/Apache 配置。

1. 安装 Certbot(CentOS 7/8/9)

bash

运行

# 安装 EPEL 源

sudo yum install -y epel-release

 

# 安装 Certbot + Nginx 插件(Apache 则用 python3-certbot-apache)

sudo yum install -y certbot python3-certbot-nginx

2. 申请证书(自动配置 Nginx)

bash

运行

# 替换为你的域名

sudo certbot --nginx -d example.com -d www.example.com

按提示输入邮箱、同意协议、选择是否重定向 HTTP → HTTPS。

证书默认存放在:/etc/letsencrypt/live/example.com/

3. 测试自动续期(安全模拟)

bash

运行

# 模拟续期,不实际颁发新证书

sudo certbot renew --dry-run

出现 Congratulations, all renewals succeeded 表示配置正常。

4. 配置自动续期(Cron 定时)

Certbot 通常会自动创建定时任务,也可手动添加更稳定的规则:

方式 A:添加到系统 cron(推荐)

bash

运行

# 每天 0 点、12 点检查,临近到期自动续期,静默执行

echo "0 0,12 * * * root /usr/bin/certbot renew --quiet --post-hook 'nginx -s reload'" | sudo tee -a /etc/cron.d/certbot

方式 B:添加到 root crontab

bash

运行

sudo crontab -e

# 添加一行(每天凌晨 3 点执行)

0 3 * * * /usr/bin/certbot renew --quiet --post-hook "nginx -s reload" >> /var/log/letsencrypt/renew.log 2>&1

5. 续期后自动重载 Nginx(钩子脚本,可选)

bash

运行

# 创建钩子目录

sudo mkdir -p /etc/letsencrypt/renewal-hooks/deploy

 

# 编写重载脚本

sudo tee /etc/letsencrypt/renewal-hooks/deploy/reload-nginx.sh > /dev/null << 'EOF'

#!/bin/bash

nginx -t && nginx -s reload

EOF

 

# 赋予执行权限

sudo chmod +x /etc/letsencrypt/renewal-hooks/deploy/reload-nginx.sh

后续 certbot renew 成功后会自动执行此脚本。

二、方案二:acme.sh(轻量、支持 DNS 验证、通配符)

acme.sh 纯 Shell 实现,无需依赖 Python,支持 DNS 验证(可申请通配符证书),自动续期更灵活。

1. 安装 acme.sh

bash

运行

# 一键安装(替换为你的邮箱)

curl https://get.acme.sh | sh -s email=your-email@example.com

 

# 加载环境变量

source ~/.bashrc

2. 申请证书(HTTP 验证,Nginx 示例)

bash

运行

# 替换为你的域名与网站根目录

acme.sh --issue -d example.com -d www.example.com -w /usr/share/nginx/html

3. 安装证书到 Nginx 并配置自动重载

bash

运行

acme.sh --install-cert -d example.com \

--key-file /etc/nginx/ssl/example.com.key \

--fullchain-file /etc/nginx/ssl/fullchain.cer \

--reloadcmd "nginx -s reload"

4. 自动续期(默认已配置)

acme.sh 安装时会自动创建 cron 任务,每天 0 点检查:

bash

运行

# 查看自动任务

crontab -l | grep acme.sh

默认输出类似:

plaintext

0 0 * * * /root/.acme.sh/acme.sh --cron --home /root/.acme.sh &>/var/log/acme.sh.log

无需额外配置,到期前 30 天会自动续期并执行 reloadcmd。

5. (可选)DNS 验证(申请通配符证书,如 *.example.com)

以阿里云 DNS 为例:

bash

运行

# 配置阿里云 AccessKey(推荐写入配置文件)

export Ali_Key="你的AccessKeyID"

export Ali_Secret="你的AccessKeySecret"

 

# 申请通配符证书

acme.sh --issue --dns dns_ali -d example.com -d *.example.com

三、关键验证与维护

1. 验证证书有效期

bash

运行

# Certbot

sudo certbot certificates

 

# acme.sh

acme.sh --list

2. 查看续期日志

bash

运行

# Certbot

tail -f /var/log/letsencrypt/renew.log

 

# acme.sh

tail -f /var/log/acme.sh.log

3. 防火墙放行(必须)

bash

运行

# 放行 80/443(HTTP-01 验证需要 80 端口)

sudo firewall-cmd --permanent --add-service=http

sudo firewall-cmd --permanent --add-service=https

sudo firewall-cmd --reload

四、两种方案对比

表格

特性 Certbot acme.sh

依赖 Python 纯 Shell,无额外依赖

自动配置 自动修改 Nginx/Apache 配置 需手动指定证书路径与重载命令

通配符 需 DNS 插件,略繁琐 原生支持 DNS 验证,通配符友好

自动续期 Cron/Systemd Timer 自动创建 Cron,开箱即用

适用场景 Nginx/Apache 常规站点 复杂环境、多域名、通配符

五、常见问题

续期失败:端口占用 / 防火墙拦截

确保 80/443 端口开放,无其他服务占用 80 端口。

CentOS 7 CA 证书过旧

bash

运行

sudo yum update -y ca-certificates

sudo update-ca-trust

acme.sh 默认 CA 为 ZeroSSL

切回 Let’s Encrypt:

bash

运行

acme.sh --set-default-ca --server letsencrypt