Você não pode selecionar mais de 25 tópicos Os tópicos devem começar com uma letra ou um número, podem incluir traços ('-') e podem ter até 35 caracteres.
 
 
 

167 linhas
3.9 KiB

  1. #!/bin/bash
  2. # scripts/deploy.sh - 构建镜像并部署到国内/国外服务器
  3. #
  4. # 用法 (在 Windows 中通过 WSL 调用):
  5. # wsl -- bash -c "bash /mnt/d/code/new-api/scripts/deploy.sh [选项]"
  6. #
  7. # 选项:
  8. # (无参数) 构建镜像 + 推送 + 部署到两台服务器
  9. # cn 只部署到国内服务器
  10. # ov 只部署到国外服务器
  11. # --no-build 跳过构建推送,使用本地最新镜像部署
  12. # --no-build cn 可组合
  13. #
  14. # 前提: WSL 中已配置 SSH 免密登录到两台服务器
  15. set -euo pipefail
  16. # ==================== 配置 ====================
  17. DOCKER_REGISTRY="registry.cn-hangzhou.aliyuncs.com/fengsilin/new-api"
  18. PROJECT_DIR="/mnt/d/code/new-api"
  19. # 服务器: SSH_HOST COMPOSE_DIR
  20. CN_HOST="root@123.57.74.135"
  21. CN_DIR="/root/new-api"
  22. OV_HOST="root@139.180.189.205"
  23. OV_DIR="/root/new-api/new-api"
  24. # ==================== 颜色 ====================
  25. RED='\033[0;31m'
  26. GREEN='\033[0;32m'
  27. YELLOW='\033[1;33m'
  28. CYAN='\033[0;36m'
  29. BOLD='\033[1m'
  30. NC='\033[0m'
  31. info() { echo -e " ${CYAN}[INFO]${NC} $*"; }
  32. ok() { echo -e " ${GREEN}[OK]${NC} $*"; }
  33. warn() { echo -e " ${YELLOW}[WARN]${NC} $*"; }
  34. error() { echo -e " ${RED}[ERROR]${NC} $*"; }
  35. section() {
  36. echo ""
  37. echo -e " ${BOLD}=========================================${NC}"
  38. echo -e " ${BOLD} $*${NC}"
  39. echo -e " ${BOLD}=========================================${NC}"
  40. }
  41. # ==================== 参数解析 ====================
  42. TARGET="all"
  43. NO_BUILD=false
  44. for arg in "$@"; do
  45. case "$arg" in
  46. cn) TARGET="cn" ;;
  47. ov) TARGET="ov" ;;
  48. --no-build) NO_BUILD=true ;;
  49. -h|--help)
  50. echo "用法: $0 [cn|ov] [--no-build]"
  51. exit 0
  52. ;;
  53. *)
  54. error "未知参数: $arg"
  55. exit 1
  56. ;;
  57. esac
  58. done
  59. # ==================== Step 1: 构建并推送 ====================
  60. if [ "$NO_BUILD" = false ]; then
  61. section "Step 1/2: 构建并推送镜像"
  62. cd "$PROJECT_DIR"
  63. BRANCH=$(git rev-parse --abbrev-ref HEAD | sed 's/\//-/g')
  64. TAG="$(date +%Y%m%d%H%M)-${BRANCH}"
  65. IMAGE="${DOCKER_REGISTRY}:${TAG}"
  66. info "分支: ${BRANCH}"
  67. info "Tag: ${TAG}"
  68. info "镜像: ${IMAGE}"
  69. echo ""
  70. docker build -t "${IMAGE}" .
  71. echo ""
  72. info "推送镜像..."
  73. docker push "${IMAGE}"
  74. ok "构建并推送完成: ${TAG}"
  75. else
  76. section "跳过构建,查找本地最新镜像..."
  77. IMAGE=$(docker images --format "{{.Repository}}:{{.Tag}}" "${DOCKER_REGISTRY}" | head -1)
  78. if [ -z "$IMAGE" ]; then
  79. error "本地未找到 ${DOCKER_REGISTRY} 的镜像"
  80. error "请先不带 --no-build 运行一次"
  81. exit 1
  82. fi
  83. TAG="${IMAGE##*:}"
  84. ok "使用镜像: ${IMAGE}"
  85. fi
  86. # ==================== Step 2: 部署 ====================
  87. section "Step 2/2: 部署到服务器"
  88. FAILED=()
  89. deploy_server() {
  90. local NAME="$1"
  91. local HOST="$2"
  92. local DIR="$3"
  93. echo ""
  94. info "部署到 ${NAME} (${HOST})..."
  95. info " 目录: ${DIR} Tag: ${TAG}"
  96. echo ""
  97. if ssh -o ConnectTimeout=15 "$HOST" bash -s "$DIR" "$DOCKER_REGISTRY" "$TAG" <<'REMOTE'; then
  98. set -e
  99. DIR="$1"
  100. REGISTRY="$2"
  101. TAG="$3"
  102. cd "$DIR"
  103. echo " [1/4] 更新 image tag..."
  104. sed -i "s|${REGISTRY}:.*|${REGISTRY}:${TAG}|" docker-compose.yml
  105. echo " [2/4] 拉取新镜像..."
  106. docker compose pull new-api
  107. echo " [3/4] 重启服务..."
  108. docker compose up -d new-api
  109. echo " [4/4] 等待启动..."
  110. sleep 8
  111. docker compose ps new-api
  112. docker image prune -f >/dev/null 2>&1
  113. REMOTE
  114. ok "${NAME} 部署成功"
  115. else
  116. error "${NAME} 部署失败"
  117. FAILED+=("$NAME")
  118. fi
  119. }
  120. case "$TARGET" in
  121. cn) deploy_server "国内(CN)" "$CN_HOST" "$CN_DIR" ;;
  122. ov) deploy_server "国外(OV)" "$OV_HOST" "$OV_DIR" ;;
  123. all)
  124. deploy_server "国内(CN)" "$CN_HOST" "$CN_DIR"
  125. deploy_server "国外(OV)" "$OV_HOST" "$OV_DIR"
  126. ;;
  127. esac
  128. # ==================== 总结 ====================
  129. echo ""
  130. section "部署总结"
  131. echo -e " 镜像: ${GREEN}${IMAGE}${NC}"
  132. if [ ${#FAILED[@]} -gt 0 ]; then
  133. error "失败节点: ${FAILED[*]}"
  134. exit 1
  135. else
  136. ok "全部节点部署成功"
  137. fi