#!/usr/bin/env bash
# Reset testnot.work to the fabricated example catalog.
#
# Reseeds from the in-repo `--seed-examples` flow: a self-contained catalog of
# fabricated `@example.test` creators and public-domain items. testnot holds no
# prod-derived data at all. This replaced a prod-restore refresh that reloaded
# the database from a production backup, putting real user data on the staging
# box; that path was deleted on 2026-07-22.
#
# Runs on fw13 (the Sando host, which has tailnet root on testnot via Tailscale
# SSH). It stops the app, resets the schema as the postgres superuser (streamed
# over Tailscale SSH), then runs the app binary once with `--seed-examples`,
# which applies migrations to the empty schema and runs the guarded seed before
# exiting. The seed's own guards (ALLOW_EXAMPLE_SEED, testnot-host allowlist,
# no-real-users) make it refuse anywhere but a testnot/localhost box.
#
# Idempotent and safe to re-run: the seed is fixed, and every run rebuilds the
# same catalog. Unlike the refresh, there is no pause-flag — the catalog is
# stable by construction, so a soak needs no protection from a daily wipe.
#
# Media (previews/downloads) attaches in-process only when object storage is
# configured in the env file (S3_*). Until MinIO is stood up on testnot, items
# seed hidden (scan_status stays pending) and the catalog shows creators,
# projects, blog posts, and follow counts without media.
set -euo pipefail

SSH_TARGET="${TESTNOT_SSH:-root@testnot}"
DB="${TESTNOT_DB:-makenotwork}"
SERVICE="makenotwork.service"
BIN="${TESTNOT_BIN:-/opt/mnw/current/makenotwork}"
BIN_DIR="$(dirname "$BIN")"
BIN_NAME="$(basename "$BIN")"
ENV_FILE="${TESTNOT_ENV:-/etc/mnw/makenotwork.env}"
SEED_USER="${TESTNOT_SEED_USER:-deploy}"

log() { echo "[$(date -u +%H:%M:%S)] $*"; }
ts_ssh() { tailscale ssh "$SSH_TARGET" "$@"; }

log "stopping $SERVICE on testnot"
ts_ssh "systemctl stop $SERVICE"

# Drop every non-system schema (migrations create custom schemas like
# tower_sessions that survive DROP SCHEMA public CASCADE). Recreate public OWNED
# BY the app role: on PG15+ a postgres-owned public grants no CREATE to other
# roles, so boot migrations would fail with "no schema has been selected to
# create in". This is the same reset the prod-refresh used, minus the restore.
log "resetting schema"
ts_ssh "sudo -u postgres psql -v ON_ERROR_STOP=1 -d $DB" <<SQL
DO \$\$
DECLARE s text;
BEGIN
    FOR s IN
        SELECT nspname FROM pg_namespace
        WHERE nspname NOT LIKE 'pg_%' AND nspname <> 'information_schema'
    LOOP
        EXECUTE format('DROP SCHEMA IF EXISTS %I CASCADE', s);
    END LOOP;
    EXECUTE 'CREATE SCHEMA public AUTHORIZATION $DB';
END \$\$;
SQL

# Run the binary as the app user with the seed opt-in flag set.
# `--seed-examples` applies migrations to the empty schema, runs the guarded
# seed, and exits(0) before the server binds a port — so this is safe to run
# while the service is stopped. Use systemd-run with the service's own
# EnvironmentFile rather than shell-sourcing it: systemd parses `KEY=value`
# literally, so secrets containing shell metacharacters (e.g. the DB password)
# load correctly, whereas `. env` would choke on them.
log "migrating + seeding the example catalog"
ts_ssh "systemd-run --pipe --wait --collect --service-type=exec \
    -p EnvironmentFile=$ENV_FILE -p WorkingDirectory=$BIN_DIR -p User=$SEED_USER \
    -E ALLOW_EXAMPLE_SEED=1 $BIN --seed-examples"

log "starting $SERVICE"
ts_ssh "systemctl start $SERVICE"

# Boot smoke: the app must come back healthy after the reseed.
for _ in $(seq 1 20); do
    code=$(ts_ssh "curl -s -o /dev/null -w '%{http_code}' http://127.0.0.1:8080/health" || echo 000)
    [ "$code" = "200" ] && { log "health OK"; exit 0; }
    sleep 3
done
echo "testnot did not return healthy after reseed" >&2
exit 1
