#!/usr/bin/env bash # # 申请 Let's Encrypt 证书(默认 5 个域名合成一张 SAN 证书)。 # # 完整引导流程: # 1. 创建共享卷(幂等)—— nginx 以 external 方式引用,必须先存在 # 2. 启动 nginx —— 此时 ssl.d/ 为空,只加载 80 端口配置,不依赖证书 # 3. 申请证书 —— webroot 写入挑战文件,由 nginx 直接对外提供 # 4. 启用 HTTPS —— 证书就绪后把 server 块放进 ssl.d/ 并重载 # set -euo pipefail export PATH="/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin${PATH:+:$PATH}" SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)" NGINX_DIR="$SCRIPT_DIR/../nginx" EMAIL="${EMAIL:-admin@stonelan.cn}" DOMAINS="${DOMAINS:-fastgpt.stonelan.cn gitea.stonelan.cn image.stonelan.cn registry.stonelan.cn www.stonelan.cn}" args=() for d in $DOMAINS; do args+=(-d "$d") done cd "$SCRIPT_DIR" # 1. 共享卷 for v in certbot-certs certbot-webroot certbot-logs; do docker volume create "$v" >/dev/null done # 2. nginx(无证书也能起来) docker compose -f "$NGINX_DIR/docker-compose.yml" up -d # 3. 申请证书 # --keep-until-expiring:证书离到期还远就跳过,避免撞 LE 的重复证书限流 # (原脚本的 --force-renewal 每次都强制重签,同一组域名每周只有 5 次额度) echo "==> 申请证书:$DOMAINS" docker compose run --rm certbot certonly \ --webroot \ --webroot-path /var/www/certbot \ --non-interactive \ --agree-tos \ --no-eff-email \ --email "$EMAIL" \ --keep-until-expiring \ "${args[@]}" # 4. 启用 HTTPS echo "==> 启用 HTTPS 配置" exec bash "$NGINX_DIR/enable-ssl.sh"