#!/usr/bin/env bash # ============================================================================= # 出交付盘:在我方构建机上执行,把 deploy/offline/ 刷新成一个可直接带走的完整交付包 # # ./scripts/export-images.sh 1.0.0 # 默认 linux/amd64 # TARGET_PLATFORM=linux/arm64 ./scripts/export-images.sh 1.0.0 # 鲲鹏/飞腾 # # 刷新后的 deploy/offline/(现场照它装,不再依赖本仓库): # ├── images/*.tar 五个镜像 + SHA256SUMS.txt # ├── sql/01-init-table.sql 建表 02-init-data.sql 初始数据 # ├── .env.iw / .env.ow 内网机 / 外网机出厂配置 # └── docker-compose.yml config/ nginx/ scripts/ VERSION.txt # 另外产出 deploy/offline/dist/sfile-offline-<版本>-<平台>.tar.gz(拷盘/刻录用) # # 前置:backend/target/s-file.jar 与 frontend/ 已构建好(见仓库根 README) # ============================================================================= set -euo pipefail VER="${1:?用法:export-images.sh <版本号>,如 1.0.0}" PLATFORM="${TARGET_PLATFORM:-linux/amd64}" PLATFORM_TAG="$(echo "$PLATFORM" | tr -d '/:')" HERE="$(cd "$(dirname "$0")/.." && pwd)" # deploy/offline ROOT="$(cd "$HERE/../.." && pwd)" # 仓库根 OUT="$HERE/dist/sfile-offline-$VER-$PLATFORM_TAG" APP_IMAGE="sfile-app:$VER" WEB_IMAGE="sfile-web:$VER" PG_IMAGE="postgres:18" # 验证过的是 18.3,同大版本即可 REDIS_IMAGE="redis:8" # 验证过的是 8.6.3 MQ_IMAGE="rabbitmq:3.13-management-alpine" # 验证过的是 3.13.7 say() { printf '\033[1;36m==> %s\033[0m\n' "$1"; } say "构建目标平台:$PLATFORM" [ "$PLATFORM" = "linux/amd64" ] || say "非 amd64 需要 buildx/QEMU 模拟器,慢属正常" # ---------- 1. 构建业务镜像 ---------- say "构建 $APP_IMAGE" docker build --platform "$PLATFORM" -f "$ROOT/deploy/docker/Dockerfile.app" -t "$APP_IMAGE" "$ROOT/backend/target" say "构建 $WEB_IMAGE(内含内网+外网两套前端,耗时较长)" docker build --platform "$PLATFORM" -f "$ROOT/deploy/docker/Dockerfile.web" -t "$WEB_IMAGE" "$ROOT/frontend" # ---------- 2. 基础镜像就位(本机没有才拉,避免交付时缺包) ---------- for img in "$PG_IMAGE" "$REDIS_IMAGE" "$MQ_IMAGE"; do docker image inspect "$img" >/dev/null 2>&1 || { say "本机没有 $img,拉取 $PLATFORM 版本" docker pull --platform "$PLATFORM" "$img" } done # ---------- 3. 镜像 tar 就地导出 ---------- say "docker save 导出镜像到 $HERE/images/(约 700M,耐心等)" mkdir -p "$HERE/images" rm -f "$HERE"/images/*.tar "$HERE/images/SHA256SUMS.txt" docker save -o "$HERE/images/sfile-app.tar" "$APP_IMAGE" docker save -o "$HERE/images/sfile-web.tar" "$WEB_IMAGE" docker save -o "$HERE/images/postgres.tar" "$PG_IMAGE" docker save -o "$HERE/images/redis.tar" "$REDIS_IMAGE" docker save -o "$HERE/images/rabbitmq.tar" "$MQ_IMAGE" ( cd "$HERE/images" && sha256sum *.tar > SHA256SUMS.txt ) # ---------- 4. SQL 与 .env 就地刷新 ---------- # 建表脚本必须先于灌数据脚本执行,靠文件名前缀定序 say "刷新 sql/(来自 backend/db/)" mkdir -p "$HERE/sql" cp "$ROOT/backend/db/init-table-postgres-full.sql" "$HERE/sql/01-init-table.sql" cp "$ROOT/backend/db/init-data.sql" "$HERE/sql/02-init-data.sql" say "刷新 .env.iw / .env.ow 的镜像 tag 为 $VER" for f in .env.iw .env.ow; do [ -f "$HERE/$f" ] || { say "缺少 $HERE/$f,跳过"; continue; } sed -i -E "s/^APP_IMAGE=.*/APP_IMAGE=sfile-app:$VER/; s/^WEB_IMAGE=.*/WEB_IMAGE=sfile-web:$VER/" "$HERE/$f" done # ---------- 5. 组交付目录并打包 ---------- say "组装 $OUT" rm -rf "$OUT" mkdir -p "$OUT/sql" cp "$HERE/docker-compose.yml" "$HERE/.env.example" "$HERE/.env.iw" "$HERE/.env.ow" "$OUT/" cp -r "$HERE/config" "$HERE/nginx" "$HERE/scripts" "$HERE/sql" "$HERE/images" "$OUT/" cp "$HERE/.gitignore" "$OUT/" 2>/dev/null || true { echo "s-file 离线交付包 $VER" echo "构建平台: $PLATFORM" echo "导出时间: $(date '+%F %T')" echo echo "镜像清单(sha256 见 images/SHA256SUMS.txt):" for t in "$OUT"/images/*.tar; do TAGS="$(tar -xOf "$t" manifest.json | tr -d '\n' | { grep -oE '"RepoTags":\[[^]]*\]' || true; } | awk 'NR==1{print}')" printf ' %-18s %-8s %s\n' "$(basename "$t")" "$(du -h "$t" | cut -f1)" "${TAGS:-?}" done echo echo "SQL: sql/01-init-table.sql sql/02-init-data.sql" echo echo "现场步骤(两台服务器各执行一次):" echo " 内网机 tar -xzf sfile-offline-$VER-$PLATFORM_TAG.tar.gz && cd sfile-offline-$VER-$PLATFORM_TAG" echo " vi .env.iw # 至少改 MESHSAFE_SECRET,按需改口令/网段/目录" echo " ./scripts/install.sh iw" echo " 外网机 同上,改成 ./scripts/install.sh ow" echo " 验证 python3 scripts/smoke_test.py" } > "$OUT/VERSION.txt" say "打包交付盘" mkdir -p "$HERE/dist" tar -czf "$OUT.tar.gz" -C "$(dirname "$OUT")" "$(basename "$OUT")" du -h "$OUT.tar.gz" | awk '{print " 交付盘: "$1" "$2}' echo " 两台服务器各自解压同一份盘,装完只差 install.sh 的参数(iw / ow)"