#!/usr/bin/env bash
# swap.sh — Carbon → ChatChat plugin swap orchestrator.
# racked.ru / 2026-05-07
#
# Operator-run only. Walks all swap-window steps with confirmation gates.
# Paper does NOT support hot-unload of plugins reliably, so this script does a
# full server stop → swap → start cycle. Estimated downtime: 60-90s.
#
# Required env / defaults:
#   SSH_TARGET=user@192.168.0.100   # nullstone
#   CONTAINER=minecraft-mc
#   COMPOSE_DIR=/opt/docker/minecraft

set -euo pipefail

SSH_TARGET="${SSH_TARGET:-user@192.168.0.100}"
CONTAINER="${CONTAINER:-minecraft-mc}"
COMPOSE_DIR="${COMPOSE_DIR:-/opt/docker/minecraft}"
STAGING_DIR="$(cd "$(dirname "$0")/.." && pwd)"
JAR_LOCAL="${STAGING_DIR}/build/ChatChat-1.0.0-SNAPSHOT-racked-1.jar"
TIMESTAMP="$(date +%Y-%m-%d-%H%M%S)"

confirm() {
  read -rp "  → press ENTER to continue, ctrl-c to abort: " _
}

step() { echo ""; echo "=== STEP $1: $2 ==="; }

step 1 "Pre-flight checks"
test -f "$JAR_LOCAL" || { echo "MISSING: $JAR_LOCAL — run build/build.sh first"; exit 1; }
test -d "${STAGING_DIR}/configs" || { echo "MISSING configs dir"; exit 1; }
ssh "$SSH_TARGET" "docker exec $CONTAINER rcon-cli list" >/dev/null
echo "  Server reachable; jar found ($(du -h "$JAR_LOCAL" | cut -f1))."

step 2 "Broadcast swap warning to players (60s lead)"
ssh "$SSH_TARGET" "docker exec $CONTAINER rcon-cli 'say [racked.ru] chat plugin swap in 60s — restart incoming, world is safe'"
echo "  Sleeping 60s..."
sleep 60
ssh "$SSH_TARGET" "docker exec $CONTAINER rcon-cli 'save-all'"
sleep 3

step 3 "Backup current Carbon plugin + configs on nullstone"
ssh "$SSH_TARGET" "docker exec $CONTAINER bash -c '
  mkdir -p /data/backups/chat-swap-${TIMESTAMP} &&
  cp /data/plugins/carbonchat-paper-3.0.0-beta.36.jar /data/backups/chat-swap-${TIMESTAMP}/ &&
  cp -r /data/plugins/CarbonChat /data/backups/chat-swap-${TIMESTAMP}/ &&
  ls -la /data/backups/chat-swap-${TIMESTAMP}/
'"
echo "  Backup OK."
confirm

step 4 "Stop the server (compose down preserves volumes)"
ssh "$SSH_TARGET" "cd $COMPOSE_DIR && docker compose stop mc"
echo "  Stopped. Verify container is down before continuing."
ssh "$SSH_TARGET" "docker ps -a --filter name=$CONTAINER --format '{{.Names}} {{.Status}}'"

step 5 "Remove Carbon JAR + dir, drop ChatChat JAR + configs"
# Carbon
ssh "$SSH_TARGET" "docker run --rm -v minecraft_mc-data:/data alpine:3 sh -c '
  rm -f /data/plugins/carbonchat-paper-3.0.0-beta.36.jar &&
  mv /data/plugins/CarbonChat /data/plugins/CarbonChat.disabled-${TIMESTAMP}
'"
# ChatChat jar
scp "$JAR_LOCAL" "$SSH_TARGET":/tmp/chatchat.jar
ssh "$SSH_TARGET" "docker run --rm -v /tmp/chatchat.jar:/in.jar:ro -v minecraft_mc-data:/data alpine:3 sh -c '
  cp /in.jar /data/plugins/ChatChat-1.0.0-SNAPSHOT-racked-1.jar &&
  mkdir -p /data/plugins/ChatChat
'"
# ChatChat configs
for f in channels.yml formats.yml settings.yml extensions.yml; do
  scp "${STAGING_DIR}/configs/${f}" "$SSH_TARGET":/tmp/${f}
  ssh "$SSH_TARGET" "docker run --rm -v /tmp/${f}:/in.yml:ro -v minecraft_mc-data:/data alpine:3 sh -c 'cp /in.yml /data/plugins/ChatChat/${f}'"
done
ssh "$SSH_TARGET" "rm -f /tmp/chatchat.jar /tmp/channels.yml /tmp/formats.yml /tmp/settings.yml /tmp/extensions.yml"
echo "  Plugins/configs swapped."
confirm

step 6 "Apply LP permission migration"
"${STAGING_DIR}/scripts/lp-migration.sh"
echo "  NOTE: LP perms above failed because server is offline — that's expected."
echo "  Will re-run after server boot."
confirm

step 7 "Start the server"
ssh "$SSH_TARGET" "cd $COMPOSE_DIR && docker compose start mc"
echo "  Waiting 30s for full boot..."
sleep 30
ssh "$SSH_TARGET" "docker exec $CONTAINER rcon-cli list"

step 8 "Re-apply LP permission migration (now that RCON is live)"
"${STAGING_DIR}/scripts/lp-migration.sh"

step 9 "Smoke test — operator-driven"
echo ""
echo "  Run these manually on the server:"
echo "    1. Log in as s8n; check chat from another client (or YOU500's perspective)."
echo "    2. /msg s8n hi  (should work for default-group player)"
echo "    3. Have YOU500 chat — confirm prefix shown is [Adventurer] (his rank), NOT [⛧] (s8n's)."
echo "    4. Check console-log: each chat line should show LP plain prefix."
echo ""
echo "  If smoke passes: leave it running."
echo "  If smoke FAILS: run scripts/rollback.sh"
