内网服务访问外部第三方 API 的统一网关
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 

226 lines
6.7 KiB

#!/bin/bash
#部署的服务器上要安装supervisor进程管理工具
TARGET="third-party-gateway-prod.srv" # 编译后的文件名
REMOTE="root@jg-serv1" # 远程服务器
REMOTE_DIR="/usr/local/third-party-gateway-prod" # 部署目录
SERVICE_NAME="third-party-gateway-prod" # Supervisor 配置里的服务名
WAIT_TIME=2 # 等待服务启动时间(秒)
BACKUP_DIR="$REMOTE_DIR/backup" # 旧版本备份目录
# Supervisor 配置目录
#cat /etc/os-release 查看操作系统版本信息
#Debian 安装supervisor
#sudo apt update
#sudo apt install supervisor -y
#systemctl status supervisor
SUPERVISOR_CONF_DIR="/etc/supervisor/conf.d" #Ubuntu/Debian 默认路径
#SUPERVISOR_CONF_DIR="/etc/supervisord.d/" #CentOS 7(EPEL)默认路径
trap 'ssh -O exit $REMOTE 2>/dev/null || true' EXIT
function remote_cmd() {
ssh "$REMOTE" "$@" </dev/null
}
# 1️⃣ 本地编译
function build_local() {
echo "🛠️ 本地交叉编译 (GOOS=linux GOARCH=amd64)..."
GOOS=linux GOARCH=amd64 go build -ldflags="-s -w" -o "$TARGET"
if [ $? -ne 0 ]; then
echo "❌ 编译失败"
exit 1
fi
}
# 2️⃣ 确保远程目录存在
function ensure_remote_dir() {
echo "📂 确保远程部署目录存在..."
remote_cmd "mkdir -p '$REMOTE_DIR'"
remote_cmd "mkdir -p '$REMOTE_DIR/config'"
remote_cmd "mkdir -p '$REMOTE_DIR/log'"
remote_cmd "mkdir -p '$BACKUP_DIR'"
}
# 3️⃣ 备份旧版本
function backup_old() {
echo "📦 备份旧版本..."
remote_cmd "
if [ -f '$REMOTE_DIR/$TARGET' ]; then
TIMESTAMP=\$(date +'%Y%m%d%H%M%S'); \
BACKUP_FILE='$BACKUP_DIR/$TARGET.'\$TIMESTAMP; \
cp '$REMOTE_DIR/$TARGET' \"\$BACKUP_FILE\"; \
echo \"✅ 旧版本已备份到 \$BACKUP_FILE\"; \
else
echo 'ℹ️ 没有旧版本需要备份'
fi
"
}
# 4️⃣ 上传二进制
function upload_binary() {
echo "📤 上传新版本到服务器..."
# 1️⃣ 上传临时文件(避免直接覆盖正在运行的程序)
TMP_TARGET="$TARGET.new"
scp "$TARGET" "$REMOTE:$REMOTE_DIR/$TMP_TARGET"
# 2️⃣ 替换旧文件并设置可执行权限
remote_cmd "mv -f '$REMOTE_DIR/$TMP_TARGET' '$REMOTE_DIR/$TARGET' && chmod +x '$REMOTE_DIR/$TARGET'"
echo "✅ 上传并替换完成: $REMOTE_DIR/$TARGET"
}
function upload_consul_conf() {
LOCAL_CONF_FILE="../config/$SERVICE_NAME.consul.yaml"
REMOTE_CONF_FILE="$REMOTE_DIR/config/$SERVICE_NAME.consul.yaml"
if [ -f "$LOCAL_CONF_FILE" ]; then
# 检查远程文件是否存在并计算差异
remote_cmd "touch $REMOTE_CONF_FILE" # 确保远程文件存在
DIFF=$(diff "$LOCAL_CONF_FILE" <(ssh "$REMOTE" "cat $REMOTE_CONF_FILE") || true)
if [ -n "$DIFF" ]; then
echo "📄 Consul 配置有变动,上传并刷新..."
scp "$LOCAL_CONF_FILE" "$REMOTE:$REMOTE_CONF_FILE"
else
echo "ℹ️ Consul 配置未变化,跳过上传"
fi
else
echo "ℹ️ 本地未找到 $LOCAL_CONF_FILE,跳过 Consul 配置"
fi
}
function upload_locale_conf() {
CONF_FILE="locale.zh.yaml"
LOCAL_PATH="../$CONF_FILE"
if [ -f "$LOCAL_PATH" ]; then
echo "找到文件:$LOCAL_PATH"
else
echo "❌ 文件不存在:$LOCAL_PATH"
return
fi
REMOTE_CONF="$REMOTE_DIR/$CONF_FILE"
remote_cmd "touch $REMOTE_CONF" # 确保远程文件存在
DIFF=$(diff "$LOCAL_PATH" <(ssh "$REMOTE" "cat $REMOTE_CONF") || true)
if [ -n "$DIFF" ]; then
echo "📄 Locale 配置有变动,上传并刷新..."
scp "$LOCAL_PATH" "$REMOTE:$REMOTE_DIR/"
else
echo "ℹ️ Locale 配置未变化,跳过上传"
fi
}
function upload_supervisor_conf() {
CONF_FILE="$SERVICE_NAME.conf"
LOCAL_PATH="../config/$CONF_FILE"
# 检查本地文件是否存在
if [ -f "$LOCAL_PATH" ]; then
echo "✅ 找到文件:$LOCAL_PATH"
else
echo "❌ 文件不存在:$LOCAL_PATH"
return
fi
# 定义远程路径
REMOTE_CONF="$SUPERVISOR_CONF_DIR/$CONF_FILE"
# 确保远程文件存在(防止 cat 报错)
remote_cmd "touch $REMOTE_CONF"
# 比较本地和远程差异
DIFF=$(diff "$LOCAL_PATH" <(ssh "$REMOTE" "cat $REMOTE_CONF") || true)
if [ -n "$DIFF" ]; then
echo "📄 Supervisor 配置有变动,上传并刷新..."
scp "$LOCAL_PATH" "$REMOTE:$SUPERVISOR_CONF_DIR/"
# 重新加载 supervisor 配置
remote_cmd "supervisorctl reread && supervisorctl update"
echo "🔄 已刷新 Supervisor 配置"
else
echo "ℹ️ Supervisor 配置未变化,跳过上传"
fi
}
# 6️⃣ 重启服务并检查状态
function restart_service() {
echo "🔄 检查服务状态并重启 (Supervisor)..."
STATUS=$(remote_cmd "supervisorctl status '$SERVICE_NAME' | awk '{print \$2}'")
echo "ℹ️ 当前服务状态: $STATUS"
if [ "$STATUS" = "RUNNING" ]; then
echo "🔁 服务正在运行,执行 restart..."
remote_cmd "supervisorctl restart '$SERVICE_NAME'"
else
echo "⚡ 服务未运行 ($STATUS),执行 start..."
remote_cmd "supervisorctl start '$SERVICE_NAME'"
fi
echo "⏳ 等待服务启动 ($WAIT_TIME 秒)..."
sleep $WAIT_TIME
FINAL_STATUS=$(remote_cmd "supervisorctl status '$SERVICE_NAME'")
echo "$FINAL_STATUS"
if echo "$FINAL_STATUS" | grep -q "RUNNING"; then
echo "✅ 服务已启动"
echo "📋 最新日志:"
remote_cmd "tail -n 10 $REMOTE_DIR/log/info.log" || true
else
echo "❌ 服务启动失败,尝试回滚旧版本..."
rollback
exit 1
fi
}
# 7️⃣ 自动回滚
function rollback() {
LATEST_BACKUP=$(remote_cmd "ls -t $BACKUP_DIR/$TARGET.* 2>/dev/null | head -n1")
if [ -z "$LATEST_BACKUP" ]; then
echo "⚠️ 没有找到备份,无法回滚!"
return
fi
echo "♻️ 回滚到 $LATEST_BACKUP ..."
remote_cmd "cp '$LATEST_BACKUP' '$REMOTE_DIR/$TARGET' && chmod +x '$REMOTE_DIR/$TARGET'"
echo "🔄 重启服务..."
remote_cmd "supervisorctl restart '$SERVICE_NAME'"
STATUS=$(remote_cmd "supervisorctl status '$SERVICE_NAME'")
echo "$STATUS"
if echo "$STATUS" | grep -q "RUNNING"; then
echo "✅ 回滚成功,服务已恢复"
else
echo "❌ 回滚失败,请手动处理"
fi
}
# 8️⃣ 清理本地产物
function clear() {
echo "🧹 清理本地编译产物..."
rm -f "$TARGET"
}
# 🔹 主流程
build_local
ensure_remote_dir
backup_old
upload_binary
upload_consul_conf
#upload_locale_conf
upload_supervisor_conf
restart_service
clear
echo "✅ 部署完成!"