97 lines
3.5 KiB
Bash
Executable File
97 lines
3.5 KiB
Bash
Executable File
#!/usr/bin/env bash
|
|
set -Eeuo pipefail
|
|
|
|
REMOTE="${REMOTE:-root@drivers.smartsoltech.kr}"
|
|
REMOTE_DIR="${REMOTE_DIR:-/opt/drivers_bot}"
|
|
BASE_URL="${BASE_URL:-http://127.0.0.1:8000}"
|
|
COMPOSE="${COMPOSE:-docker compose}"
|
|
RUN_LOCAL_CHECKS="${RUN_LOCAL_CHECKS:-true}"
|
|
BACKUP_BEFORE_DEPLOY="${BACKUP_BEFORE_DEPLOY:-true}"
|
|
BRANCH="$(git rev-parse --abbrev-ref HEAD 2>/dev/null || echo unknown)"
|
|
REVISION="$(git rev-parse --short HEAD 2>/dev/null || echo unknown)"
|
|
|
|
EXCLUDES=(
|
|
"--exclude=.git/"
|
|
"--exclude=.env"
|
|
"--exclude=.env.*"
|
|
"--exclude=.venv/"
|
|
"--exclude=venv/"
|
|
"--exclude=__pycache__/"
|
|
"--exclude=.pytest_cache/"
|
|
"--exclude=.ruff_cache/"
|
|
"--exclude=.history/"
|
|
"--exclude=backups/"
|
|
"--exclude=*.sqlite"
|
|
"--exclude=*.sqlite3"
|
|
"--exclude=*.db"
|
|
)
|
|
|
|
send_remote_report() {
|
|
local text="$1"
|
|
ssh "$REMOTE" "cd '$REMOTE_DIR' && export CARPASS_REPORT_TEXT=\$(cat); if $COMPOSE exec -T api test -f scripts/send_telegram_report.py >/dev/null 2>&1; then $COMPOSE exec -T -e CARPASS_REPORT_TEXT api python scripts/send_telegram_report.py; else $COMPOSE run --rm --no-deps -e CARPASS_REPORT_TEXT api python scripts/send_telegram_report.py; fi" <<<"$text" || true
|
|
}
|
|
|
|
fail_report() {
|
|
local line="${1:-unknown}"
|
|
send_remote_report "❌ CarPass rsync deploy failed
|
|
Branch: $BRANCH
|
|
Revision: $REVISION
|
|
Step line: $line
|
|
Target: $REMOTE"
|
|
}
|
|
|
|
trap 'fail_report "$LINENO"' ERR
|
|
|
|
if [[ "$RUN_LOCAL_CHECKS" == "true" ]]; then
|
|
echo "Running local checks..."
|
|
.venv/bin/ruff check app bot tests
|
|
.venv/bin/pytest -q
|
|
fi
|
|
|
|
send_remote_report "🚀 CarPass rsync deploy started
|
|
Branch: $BRANCH
|
|
Revision: $REVISION
|
|
Target: $REMOTE
|
|
Checks: local=${RUN_LOCAL_CHECKS}"
|
|
|
|
echo "Checking remote..."
|
|
ssh "$REMOTE" "test -d '$REMOTE_DIR' && test -f '$REMOTE_DIR/docker-compose.yml'"
|
|
|
|
if [[ "$BACKUP_BEFORE_DEPLOY" == "true" ]]; then
|
|
echo "Creating remote code backup..."
|
|
ssh "$REMOTE" "cd '$(dirname "$REMOTE_DIR")' && mkdir -p '$REMOTE_DIR/backups' && tar --exclude='$(basename "$REMOTE_DIR")/backups' --exclude='$(basename "$REMOTE_DIR")/.git' --exclude='$(basename "$REMOTE_DIR")/.env' --exclude='$(basename "$REMOTE_DIR")/.venv' -czf '$REMOTE_DIR/backups/code_pre_rsync_$(date +%Y%m%d%H%M%S).tgz' '$(basename "$REMOTE_DIR")'"
|
|
fi
|
|
|
|
echo "Syncing code with rsync..."
|
|
rsync -az --delete "${EXCLUDES[@]}" ./ "$REMOTE:$REMOTE_DIR/"
|
|
|
|
echo "Building remote images..."
|
|
ssh "$REMOTE" "cd '$REMOTE_DIR' && $COMPOSE build"
|
|
send_remote_report "🧱 CarPass rsync deploy progress
|
|
Branch: $BRANCH
|
|
Step: docker build completed"
|
|
|
|
echo "Applying migrations..."
|
|
ssh "$REMOTE" "cd '$REMOTE_DIR' && $COMPOSE run --rm api alembic upgrade head"
|
|
send_remote_report "🗄️ CarPass rsync deploy progress
|
|
Branch: $BRANCH
|
|
Step: migrations applied"
|
|
|
|
echo "Starting services..."
|
|
ssh "$REMOTE" "cd '$REMOTE_DIR' && $COMPOSE up -d"
|
|
|
|
echo "Waiting for API readiness..."
|
|
ssh "$REMOTE" "cd '$REMOTE_DIR' && for i in \$(seq 1 30); do status=\$(docker inspect -f '{{.State.Health.Status}}' drivers_bot-api-1 2>/dev/null || echo missing); echo \"api_health=\$status\"; [ \"\$status\" = healthy ] && exit 0; sleep 2; done; $COMPOSE logs --tail=120 api; exit 1"
|
|
|
|
echo "Running remote smoke tests..."
|
|
ssh "$REMOTE" "cd '$REMOTE_DIR' && BASE_URL='$BASE_URL' ./scripts/smoke_test.sh && curl -fsSI '$BASE_URL/admin.html' | head -5 && $COMPOSE ps"
|
|
|
|
send_remote_report "✅ CarPass rsync deploy completed
|
|
Branch: $BRANCH
|
|
Revision: $REVISION
|
|
Migration: $(ssh "$REMOTE" "cd '$REMOTE_DIR' && curl -fsS '$BASE_URL/ready'" | tr '\n' ' ')
|
|
Checks: /health ok, /ready ok, /metrics ok, /admin.html 200
|
|
Services: api healthy, bot restarted"
|
|
|
|
echo "Deploy completed."
|