AI 写脚本,监控+提醒+certbot 自动申请
https://maifeipin.com/archives/zi-dong-bu-shu-xi-tong-jian-kong-jiao-ben只需替换你的邮箱和 tencentcloud.ini (对应的域名 API key ) 就行了
···
#!/bin/bash
THRESHOLD=7
CREDENTIALS="/etc/letsencrypt/tencentcloud.ini"
EMAIL="yourmail@qq.com"
EMAIL_ARG="--email $EMAIL"
# EMAIL_ARG="--register-unsafely-without-email"
nginx_conf_dirs=(
"/etc/nginx/nginx.conf"
"/etc/nginx/conf.d/"
"/etc/nginx/sites-enabled/"
"/etc/nginx/sites-available/"
"/usr/local/nginx/conf/"
)
nginx_cert_files=$(mktemp)
for conf_dir in "${nginx_conf_dirs[@]}"; do
if [ -d "$conf_dir" ]; then
find "$conf_dir" -type f -name "*.conf" 2>/dev/null | while read -r file; do
grep -E '^\s*ssl_certificate\s+' "$file" | awk '{print $2}' | sed "s/['\";]//g" >> "$nginx_cert_files"
done
elif [ -f "$conf_dir" ]; then
grep -E '^\s*ssl_certificate\s+' "$conf_dir" | awk '{print $2}' | sed "s/['\";]//g" >> "$nginx_cert_files"
fi
done
sort -u "$nginx_cert_files" -o "$nginx_cert_files"
while read -r cert_path; do
if [ -z "$cert_path" ]; then continue; fi
if [ ! -f "$cert_path" ]; then
echo "证书文件: $cert_path (未找到!)"
echo "-----------------------------"
continue
fi
expiry_date=$(openssl x509 -noout -enddate -in "$cert_path" 2>/dev/null | cut -d= -f2)
expiry_epoch=$(date -d "$expiry_date" +%s)
now_epoch=$(date +%s)
days_left=$(( (expiry_epoch - now_epoch) / 86400 ))
all_domains=$(openssl x509 -noout -text -in "$cert_path" 2>/dev/null | grep "DNS:" | sed 's/.*DNS://;s/, /\n/g' | tr '\n' ' ')
if [ $days_left -le $THRESHOLD ]; then
main_domain=$(echo "$all_domains" | awk '{print $1}')
echo "证书文件: $cert_path"
echo " 包含域名: $all_domains"
echo " 过期时间: $expiry_date (剩余 $days_left 天)"
echo " 证书即将过期或已过期,自动续期..."
certbot certonly \
-a dns-tencentcloud \
--dns-tencentcloud-credentials "$CREDENTIALS" \
-d $all_domains \
$EMAIL_ARG \
--non-interactive --agree-tos \
--keep-until-expiring
if [ $? -eq 0 ]; then
echo " 证书续期成功"
# 自动覆盖 Nginx 实际用的证书
src_cert="/etc/letsencrypt/live/$main_domain/fullchain.pem"
src_key="/etc/letsencrypt/live/$main_domain/privkey.pem"
if [ -f "$src_cert" ] && [ -f "$src_key" ]; then
# 只在 Nginx 用的路径和 Let’s Encrypt 路径不一致时覆盖
if [ "$cert_path" != "$src_cert" ]; then
cp -f "$src_cert" "$cert_path"
echo " 已覆盖 Nginx 用的证书: $cert_path"
fi
# 查找 key 路径
key_path=$(grep -E '^\s*ssl_certificate_key\s+' /etc/nginx/nginx.conf /etc/nginx/conf.d/*.conf /etc/nginx/sites-enabled/* /etc/nginx/sites-available/* /usr/local/nginx/conf/*.conf 2>/dev/null | grep "$main_domain" | awk '{print $2}' | sed "s/['\";]//g" | head -n1)
if [ -n "$key_path" ] && [ "$key_path" != "$src_key" ]; then
cp -f "$src_key" "$key_path"
echo " 已覆盖 Nginx 用的私钥: $key_path"
fi
fi
systemctl reload nginx
else
echo " 证书续期失败"
fi
else
echo "证书文件: $cert_path"
echo " 包含域名: $all_domains"
echo " 过期时间: $expiry_date (剩余 $days_left 天)"
fi
echo "-----------------------------"
done < "$nginx_cert_files"
rm -f "$nginx_cert_files"
···