优化部署脚本非交互变量支持

This commit is contained in:
2026-06-30 22:12:26 +08:00
parent d54cf2f6ce
commit 2a40ad91c8
7 changed files with 483 additions and 73 deletions
+122 -18
View File
@@ -1,3 +1,5 @@
#!/bin/bash
if command -v nginx &> /dev/null; then
echo "✅ Nginx 已安装,跳过安装步骤"
else
@@ -104,12 +106,55 @@ else
fi
# ===== 域名配置交互与文件生成 =====
sanitize_domain() {
local domain=$1
domain="${domain#http://}"
domain="${domain#https://}"
domain="${domain%%/*}"
domain="${domain%;}"
echo "$domain" | xargs
}
validate_domain_value() {
local domain=$1
[[ "$domain" =~ ^[A-Za-z0-9]([A-Za-z0-9-]{0,61}[A-Za-z0-9])?(\.[A-Za-z0-9]([A-Za-z0-9-]{0,61}[A-Za-z0-9])?)+$ ]]
}
get_env_domain() {
local domain="${HTTPS_DOMAIN:-${EASYAI_PROXY_DOMAIN:-${DEPLOY_DOMAIN:-}}}"
if [ -z "$domain" ]; then
return 0
fi
domain="$(sanitize_domain "$domain")"
if ! validate_domain_value "$domain"; then
echo "❌ 域名变量格式不正确: $domain" >&2
exit 1
fi
echo "$domain"
}
is_non_interactive() {
[ "${HTTPS_NON_INTERACTIVE:-${DEPLOY_NON_INTERACTIVE:-0}}" = "1" ] || [ "${CI:-}" = "true" ] || [ ! -t 0 ]
}
prompt_domain() {
local domain
domain="$(get_env_domain)"
if [ -n "$domain" ]; then
echo "$domain"
return 0
fi
if is_non_interactive; then
echo "❌ 当前为非交互环境,HTTPS 配置需要传入域名变量" >&2
echo " 请设置 DEPLOY_DOMAIN=<域名> 或 EASYAI_PROXY_DOMAIN=<域名>" >&2
exit 1
fi
while true; do
read -r -p "🌐 请输入域名(例如 demo.example.com: " domain
domain=$(echo "$domain" | xargs)
if [ -n "$domain" ] && [[ "$domain" =~ ^[A-Za-z0-9]([A-Za-z0-9-]{0,61}[A-Za-z0-9])?(\.[A-Za-z0-9]([A-Za-z0-9-]{0,61}[A-Za-z0-9])?)+$ ]]; then
domain="$(sanitize_domain "$domain")"
if [ -n "$domain" ] && validate_domain_value "$domain"; then
echo "$domain"
return 0
fi
@@ -211,24 +256,59 @@ server {
EOF
}
conf_contains_domain() {
local conf_file=$1
local domain=$2
grep -Eq "server_name[^;]*(^|[[:space:]])(www\\.)?${domain//./\\.}([[:space:];]|$)" "./$conf_file"
}
normalize_domain_action() {
local action=$1
action="$(printf '%s' "$action" | tr '[:upper:]' '[:lower:]')"
case "$action" in
1|replace) echo "1" ;;
2|add|"") echo "2" ;;
*)
echo "❌ EASYAI_PROXY_DOMAIN_ACTION 只能是 replace 或 add,当前为: $action" >&2
exit 1
;;
esac
}
upsert_domain_for_conf() {
local conf_file=$1
local env_domain="${2:-}"
local env_action="${3:-}"
local mode
local new_domain
echo "️ 检测到当前目录已有配置文件: $conf_file"
while true; do
echo "请选择域名处理方式:"
echo " 1) 替换当前域名"
echo " 2) 新增一个域名"
read -r -p "请输入选项 (1/2): " mode
case "$mode" in
1|2) break ;;
*) echo "❌ 无效选项,请输入 1 或 2" ;;
esac
done
if [ -n "$env_domain" ]; then
new_domain="$(sanitize_domain "$env_domain")"
if ! validate_domain_value "$new_domain"; then
echo "❌ 域名变量格式不正确: $new_domain"
exit 1
fi
if conf_contains_domain "$conf_file" "$new_domain"; then
echo "️ 配置文件已包含域名 $new_domain,无需修改。"
return 0
fi
mode="$(normalize_domain_action "$env_action")"
echo "使用变量配置域名: $new_domain, action=$([ "$mode" = "1" ] && echo replace || echo add)"
else
while true; do
echo "请选择域名处理方式:"
echo " 1) 替换当前域名"
echo " 2) 新增一个域名"
read -r -p "请输入选项 (1/2): " mode
case "$mode" in
1|2) break ;;
*) echo "❌ 无效选项,请输入 1 或 2" ;;
esac
done
new_domain=$(prompt_domain)
new_domain=$(prompt_domain)
fi
if [ "$mode" = "1" ]; then
local old_domain
@@ -268,7 +348,9 @@ upsert_domain_for_conf() {
detect_existing_proxy_conf() {
local preferred_file=$1
local domain_filter="${2:-}"
local -a candidates=()
local -a matched_candidates=()
local conf
if [ -n "$preferred_file" ] && [ -f "./$preferred_file" ]; then
@@ -286,15 +368,36 @@ detect_existing_proxy_conf() {
return 1
fi
if [ -n "$domain_filter" ]; then
for conf in "${candidates[@]}"; do
if conf_contains_domain "$conf" "$domain_filter"; then
matched_candidates+=("$conf")
fi
done
if [ "${#matched_candidates[@]}" -eq 1 ]; then
echo "${matched_candidates[0]}"
return 0
fi
if [ "${#matched_candidates[@]}" -gt 1 ] && is_non_interactive; then
echo "❌ 多个配置文件都包含 $domain_filter,请通过 EASYAI_PROXY_CONF 指定文件" >&2
exit 1
fi
fi
if [ "${#candidates[@]}" -eq 1 ]; then
echo "${candidates[0]}"
return 0
fi
echo "⚠️ 检测到多个可用配置文件,请选择一个:"
if is_non_interactive; then
echo "❌ 检测到多个可用配置文件,请通过 EASYAI_PROXY_CONF 指定文件" >&2
exit 1
fi
echo "⚠️ 检测到多个可用配置文件,请选择一个:" >&2
local i
for i in "${!candidates[@]}"; do
printf " %s) %s\n" "$((i + 1))" "${candidates[$i]}"
printf " %s) %s\n" "$((i + 1))" "${candidates[$i]}" >&2
done
while true; do
read -r -p "请输入序号: " i
@@ -310,9 +413,10 @@ echo "🚀 复制当前目录的配置文件到nginx配置文件目录"
# 支持 EASYAI_PROXY_CONF 指定配置文件(如 51easyai.com.conf
PREFERRED_CONF_FILE="${EASYAI_PROXY_CONF:-}"
DEFAULT_NEW_CONF_FILE="${EASYAI_PROXY_CONF:-easyai-proxy.conf}"
CONF_FILE=$(detect_existing_proxy_conf "$PREFERRED_CONF_FILE")
HTTPS_DOMAIN_INPUT="$(get_env_domain)"
CONF_FILE=$(detect_existing_proxy_conf "$PREFERRED_CONF_FILE" "$HTTPS_DOMAIN_INPUT")
if [ -n "$CONF_FILE" ]; then
upsert_domain_for_conf "$CONF_FILE"
upsert_domain_for_conf "$CONF_FILE" "$HTTPS_DOMAIN_INPUT" "${EASYAI_PROXY_DOMAIN_ACTION:-}"
else
CONF_FILE="$DEFAULT_NEW_CONF_FILE"
echo "ℹ️ 当前目录未找到可用 nginx 配置文件(*.conf 且包含 server_name"
@@ -363,7 +467,7 @@ if [ -n "$DOMAINS" ]; then
sudo certbot --nginx \
--non-interactive \
--agree-tos \
--email wangbo@51easyai.com \
--email "${CERTBOT_EMAIL:-wangbo@51easyai.com}" \
--rsa-key-size 2048 \
--preferred-challenges http \
--force-renewal \