#!/bin/bash
# Final capture on the OLD Mac. Use a new package directory each time.
set -euo pipefail
umask 077
fail() { echo "ERROR: $*" >&2; exit 1; }
ask() { local a; printf '%s [y/N] ' "$*" >/dev/tty; IFS= read -r a </dev/tty; case "$a" in y|Y|yes|YES) return 0;; *) return 1;; esac; }
if [ "$#" -ne 1 ] || [ "${1:-}" = --help ]; then
    echo 'Usage: /bin/bash capture-migration.sh /Volumes/Temp\ Storage/NEW-package-name'
    echo 'Captures all 32 file roots plus fresh database/role exports. No services are stopped automatically.'
    exit 0
fi
[ -t 0 ] || fail 'Run interactively on the original Mac.'
[ "$(id -un)" = kinsleypetit-homme ] || fail 'Use the original account.'
[ ! -e "$1" ] || fail 'Choose a new package directory; existing backups are never overwritten.'
parent=$(cd "$(dirname "$1")" && pwd -P)
case "$parent" in /Volumes/*) ;; *) fail 'Use the selected external storage, not the nearly full internal disk.';; esac
package="$parent/$(basename "$1")"
here=$(cd "$(dirname "$0")" && pwd -P)
[ -f "$here/restore-migration-paths.txt" ] || fail 'Missing capture path list.'
if /usr/bin/pgrep -x 'httpd|php-fpm' >/dev/null 2>&1; then fail 'Finish requests and stop Apache/PHP-FPM for the final capture; leave PostgreSQL running.'; fi
for label in com.kinsley.megatron-follow-up-email com.kinsley.duckdns com.kinsley.acme-renew; do
    if launchctl print "gui/$UID/$label" >/dev/null 2>&1; then fail "Unload $label during final capture."; fi
done
ask 'Have you closed Adobe, finished edits/uploads and paused all other writers for the final capture?' || exit 1
ask "Create $package and its backup subfolders on external storage?" || exit 1
/bin/mkdir -p "$package/filesystem" "$package/databases"
exec > >(/usr/bin/tee -a "$package/capture.log") 2>&1
trap 'echo "Capture failed at line $LINENO; this package is incomplete." >&2' ERR
/usr/local/opt/php@8.3/bin/php "$here/export-migration-databases.php" "$package/databases"
while IFS= read -r source || [ -n "$source" ]; do
    case "$source" in ''|'#'*) continue;; esac
    [ -e "$source" ] && [ ! -L "$source" ] || fail "Missing or symlink source: $source"
    dest="$package/filesystem$source"
    /bin/mkdir -p "$(dirname "$dest")"
    echo "COPY: $source"
    /usr/bin/ditto --rsrc --extattr --acl "$source" "$dest"
    if [ -d "$source" ]; then
        differences=$(/usr/bin/rsync -rlcni "$source/" "$dest/")
    else
        differences=$(/usr/bin/rsync -rlcni "$source" "$(dirname "$dest")/")
    fi
    [ -z "$differences" ] || fail "Capture verification differs: $source"
done < "$here/restore-migration-paths.txt"
(cd "$package/databases" && /usr/bin/shasum -a 256 ./*.dump ./*.sql ./*.txt > SHA256SUMS)
echo 'Recording durable SHA-256 checksums for all captured regular files...'
(cd "$package" && /usr/bin/find filesystem -type f -print0 | /usr/bin/xargs -0 /usr/bin/shasum -a 256 > FILES.sha256)
/bin/cp "$here/restore-migration-paths.txt" "$package/CAPTURED-PATHS.txt"
date -u > "$package/FILES_COMPLETE"
echo "File copies/content checks and database export completed: $package"
echo 'Next run restore-migration-databases.sh PACKAGE --rehearse. Keep software installers and the toolkit alongside this package.'
echo 'No production services have been restarted. Metadata and application acceptance checks remain required.'
