HTTPS 已经成为 Web 服务的标配。

以前申请 SSL 证书通常需要购买商业证书,不仅需要费用,还需要每年续费。

现在,借助 Let's Encrypt 提供的免费证书和 acme.sh 自动化工具,我们可以在几分钟内完成证书申请,并实现自动续期。

本文以 Docker 部署的 Confluence + Nginx 反向代理为例,介绍 acme.sh 的安装、证书申请、Nginx 配置以及自动续期。

一、什么是 Let's Encrypt

Let's Encrypt 是一个免费的证书颁发机构(CA,Certificate Authority)。

它具有以下特点:

  • 免费

  • 自动签发

  • 自动续期

  • 全球浏览器信任

  • 支持 ACME 协议

官方网站:

https://letsencrypt.org/

证书有效期:

90 天

虽然只有 90 天,但可以自动续期,因此几乎不需要人工维护。

二、什么是 acme.sh

acme.sh 是一个使用 Shell 编写的 ACME 客户端。

GitHub:

https://github.com/acmesh-official/acme.sh

特点:

  • 不依赖 Python

  • 不依赖 OpenSSL 新版本

  • 支持 Linux、BSD、macOS

  • 支持几十种 DNS API

  • 支持 Nginx、Apache、Standalone、DNS 等多种验证方式

三、安装 acme.sh

执行:

git clone https://gitee.com/neilpang/acme.sh.git

安装完成后重新加载环境变量:

source ~/.bashrc

查看版本:

~/.acme.sh/acme.sh --version

创建邮箱:

./acme.sh --install -m xingzhibang@pexetech.com

四、证书申请方式

acme.sh 支持多种验证方式。

1、Nginx 模式

适用于:

  • Nginx 已部署

  • 80 端口可以访问

  • 域名已经解析

申请:

~/.acme.sh/acme.sh --issue -d confluence.example.com --nginx /usr/local/nginx/conf/nginx.conf

参数说明:

-d:需要申请的域名,我这里是 confluence.example.com

--nginx: nginx 的主配置文件目录位置

acme.sh 会自动修改 Nginx 配置完成验证。

2、DNS 模式(推荐)

企业环境推荐。

例如阿里云 DNS:

export Ali_Key="AccessKeyID"
export Ali_Secret="AccessKeySecret"

申请:

~/.acme.sh/acme.sh --issue \
-d confluence.example.com \
--dns dns_ali

五、安装证书

不要直接引用 ~/.acme.sh 目录中的证书。

推荐安装到固定目录:

mkdir -p /usr/local/nginx/ssl

执行:

~/.acme.sh/acme.sh --install-cert \
-d confluence.example.com \
--key-file       /usr/local/nginx/ssl/confluence.key \
--fullchain-file /usr/local/nginx/ssl/confluence.pem \
--reloadcmd "/usr/local/nginx/sbin/nginx -s reload"

安装完成后:

/usr/local/nginx/ssl/

confluence.key
confluence.pem

六、Nginx 配置 HTTPS

HTTP 自动跳转 HTTPS:

server {
    listen 80;
    server_name confluence.example.com;

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

HTTPS:

server {
    listen 443 ssl;

    server_name confluence.example.com;

    ssl_certificate     /usr/local/nginx/ssl/confluence.pem;
    ssl_certificate_key /usr/local/nginx/ssl/confluence.key;

    ssl_protocols TLSv1.2 TLSv1.3;

    location / {
        ## 这里是反向代理的配置,可以自己修改
        proxy_pass http://127.0.0.1:38090; 

        proxy_http_version 1.1;
        ## 非常重要
        proxy_set_header Host $host;
        proxy_set_header X-Forwarded-Proto https;
        proxy_set_header X-Forwarded-Port 443;
        proxy_set_header X-Real-IP $remote_addr;
        proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
    }
}

测试:

nginx -t

重新加载:

nginx -s reload

七、自动续期

安装 acme.sh 后,会自动创建 Cron 任务。

查看:

crontab -l

acme.sh 每天都会检查证书。

如果证书距离过期还有约 30 天,就会自动申请新证书。

随后:

  • 更新证书文件

  • 执行 reloadcmd

  • 自动重载 Nginx

整个过程无需人工干预。

八、查看已申请证书

~/.acme.sh/acme.sh --list

查看详情:

~/.acme.sh/acme.sh --info -d confluence.example.com

九、常见问题

1. Cannot find nginx config

原因:

acme.sh 找不到 Nginx 配置文件。

解决:

~/.acme.sh/acme.sh \
--issue \
-d confluence.example.com \
--nginx /usr/local/nginx/conf/nginx.conf

2. PEM_read_bio start line

原因:

证书文件错误。

通常是:

  • 使用了错误的证书文件

  • key 与 pem 配置反了

正确配置:

ssl_certificate     confluence.pem;
ssl_certificate_key confluence.key;