1449f08e6c
* wip: preserve local changes before upstream merge * Improve proxy routing stability and add stable-first strategy * Sync explicit-group routing strategy to eligible source routes * Fix proxy retry and runtime health review issues * fix: make proxy channel retry attempts configurable * fix: harden proxy retry recovery and bookkeeping * fix: address pr 257 review comments --------- Co-authored-by: Cita <juricek.chen@gmail.com>
160 lines
3.5 KiB
Bash
Executable File
160 lines
3.5 KiB
Bash
Executable File
#!/usr/bin/env bash
|
|
|
|
set -euo pipefail
|
|
|
|
ROOT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
|
|
COMPOSE_FILE="$ROOT_DIR/docker/docker-compose.yml"
|
|
COMPOSE_OVERRIDE_FILE="$ROOT_DIR/docker/docker-compose.override.yml"
|
|
ENV_FILE="$ROOT_DIR/docker/.env"
|
|
DATA_DIR="$ROOT_DIR/docker/data"
|
|
|
|
DO_PULL=0
|
|
SKIP_BACKUP=0
|
|
|
|
usage() {
|
|
cat <<'EOF'
|
|
Usage: ./update-and-restart.sh [--pull] [--skip-backup]
|
|
|
|
默认行为:
|
|
1. 保留现有 docker/data 数据
|
|
2. 先备份数据目录
|
|
3. 基于当前本地代码重新构建并重启容器
|
|
|
|
可选参数:
|
|
--pull 先拉取最新 Git 代码后再构建。若工作区有未提交修改会直接退出,避免覆盖本地改动
|
|
--skip-backup 跳过启动前数据备份
|
|
-h, --help 显示帮助
|
|
EOF
|
|
}
|
|
|
|
require_cmd() {
|
|
if ! command -v "$1" >/dev/null 2>&1; then
|
|
echo "Missing required command: $1" >&2
|
|
exit 1
|
|
fi
|
|
}
|
|
|
|
require_file() {
|
|
if [ ! -f "$1" ]; then
|
|
echo "Missing required file: $1" >&2
|
|
exit 1
|
|
fi
|
|
}
|
|
|
|
while [ $# -gt 0 ]; do
|
|
case "$1" in
|
|
--pull)
|
|
DO_PULL=1
|
|
;;
|
|
--skip-backup)
|
|
SKIP_BACKUP=1
|
|
;;
|
|
-h|--help)
|
|
usage
|
|
exit 0
|
|
;;
|
|
*)
|
|
echo "Unknown argument: $1" >&2
|
|
usage >&2
|
|
exit 1
|
|
;;
|
|
esac
|
|
shift
|
|
done
|
|
|
|
require_cmd docker
|
|
require_cmd tar
|
|
require_cmd git
|
|
require_file "$COMPOSE_FILE"
|
|
require_file "$ENV_FILE"
|
|
|
|
COMPOSE_ARGS=(
|
|
-f "$COMPOSE_FILE"
|
|
--env-file "$ENV_FILE"
|
|
)
|
|
|
|
if [ -f "$COMPOSE_OVERRIDE_FILE" ]; then
|
|
COMPOSE_ARGS=(
|
|
-f "$COMPOSE_FILE"
|
|
-f "$COMPOSE_OVERRIDE_FILE"
|
|
--env-file "$ENV_FILE"
|
|
)
|
|
fi
|
|
|
|
if [ "$DO_PULL" -eq 1 ]; then
|
|
echo "[0/5] Checking git worktree..."
|
|
if [ -n "$(git -C "$ROOT_DIR" status --porcelain)" ]; then
|
|
echo "Git worktree has uncommitted changes. Commit/stash them first, or rerun without --pull to rebuild the current local code." >&2
|
|
exit 1
|
|
fi
|
|
|
|
echo "[1/5] Pulling latest git changes..."
|
|
git -C "$ROOT_DIR" pull --rebase
|
|
else
|
|
echo "[1/4] Using current local source code..."
|
|
fi
|
|
|
|
BACKUP_FILE=""
|
|
RESTORE_ON_ERROR=0
|
|
|
|
restore_if_failed() {
|
|
if [ "$RESTORE_ON_ERROR" -eq 1 ]; then
|
|
echo "Update failed after containers were stopped; attempting to restore service..." >&2
|
|
docker compose "${COMPOSE_ARGS[@]}" up -d --force-recreate || true
|
|
fi
|
|
}
|
|
|
|
trap restore_if_failed ERR
|
|
|
|
if [ "$DO_PULL" -eq 1 ]; then
|
|
echo "[2/5] Stopping current containers..."
|
|
else
|
|
echo "[2/4] Stopping current containers..."
|
|
fi
|
|
docker compose "${COMPOSE_ARGS[@]}" down --remove-orphans
|
|
RESTORE_ON_ERROR=1
|
|
|
|
if [ "$SKIP_BACKUP" -eq 0 ]; then
|
|
mkdir -p "$DATA_DIR"
|
|
BACKUP_FILE="$ROOT_DIR/docker/data-backup-$(date +%Y%m%d-%H%M%S).tar.gz"
|
|
if [ "$DO_PULL" -eq 1 ]; then
|
|
echo "[3/5] Backing up data directory..."
|
|
else
|
|
echo "[3/4] Backing up data directory..."
|
|
fi
|
|
tar -czf "$BACKUP_FILE" -C "$DATA_DIR" .
|
|
else
|
|
if [ "$DO_PULL" -eq 1 ]; then
|
|
echo "[3/5] Skipping data backup by request..."
|
|
else
|
|
echo "[3/4] Skipping data backup by request..."
|
|
fi
|
|
fi
|
|
|
|
if [ "$DO_PULL" -eq 1 ]; then
|
|
echo "[4/5] Rebuilding and starting containers..."
|
|
else
|
|
echo "[4/4] Rebuilding and starting containers..."
|
|
fi
|
|
docker compose "${COMPOSE_ARGS[@]}" up -d --build --force-recreate
|
|
RESTORE_ON_ERROR=0
|
|
trap - ERR
|
|
|
|
echo
|
|
echo "Container status:"
|
|
docker compose "${COMPOSE_ARGS[@]}" ps
|
|
|
|
echo
|
|
echo "Recent logs:"
|
|
docker compose "${COMPOSE_ARGS[@]}" logs --tail 20
|
|
|
|
if [ -n "$BACKUP_FILE" ]; then
|
|
echo
|
|
echo "Data backup saved to: $BACKUP_FILE"
|
|
fi
|
|
|
|
if PORT_MAPPING="$(docker compose "${COMPOSE_ARGS[@]}" port metapi 4000 2>/dev/null)"; then
|
|
echo
|
|
echo "Service is available at: $PORT_MAPPING"
|
|
fi
|