#!/usr/bin/env bash
#
# Set up Supervisor to keep the Afaq SIP2 socket server (sip2:serve) alive
# on Linux. Supported OS: Ubuntu and AlmaLinux.
#
# What it does:
#   1. Detects the OS (Ubuntu / AlmaLinux).
#   2. Installs Supervisor if it is not already present.
#   3. Enables Supervisor so it starts automatically on boot.
#   4. Writes a program config for the SIP2 server and starts it.
#
# Usage (as root):
#   sudo bash deployment_scripts/afaq_sip2_as_service.sh
#
# Optional overrides (environment variables):
#   PHP_BIN   path to the php binary       (default: autodetected)
#   RUN_USER  user the server runs as       (default: www-data on Ubuntu, apache on AlmaLinux)
#   PROJECT_DIR  project root               (default: parent of this script)

set -euo pipefail

PROGRAM_NAME="afaq-sip2"

if [ "$(id -u)" -ne 0 ]; then
    echo "ERROR: run this script as root (sudo bash deployment_scripts/afaq_sip2_as_service.sh)." >&2
    exit 1
fi

# ---------------------------------------------------------------------------
# Resolve paths
# ---------------------------------------------------------------------------
SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
PROJECT_DIR="${PROJECT_DIR:-$(cd "$SCRIPT_DIR/.." && pwd)}"

if [ ! -f "$PROJECT_DIR/artisan" ]; then
    echo "ERROR: could not find artisan at $PROJECT_DIR/artisan. Set PROJECT_DIR explicitly." >&2
    exit 1
fi

PHP_BIN="${PHP_BIN:-$(command -v php || true)}"
if [ -z "$PHP_BIN" ]; then
    echo "ERROR: php not found on PATH. Set PHP_BIN to the php binary path." >&2
    exit 1
fi

LOG_FILE="$PROJECT_DIR/app/storage/logs/supervisor-sip2.log"

# ---------------------------------------------------------------------------
# Detect OS
# ---------------------------------------------------------------------------
if [ ! -r /etc/os-release ]; then
    echo "ERROR: /etc/os-release not found; cannot detect the OS." >&2
    exit 1
fi

# shellcheck disable=SC1091
. /etc/os-release
OS_ID="${ID:-}"
OS_LIKE="${ID_LIKE:-}"

case "$OS_ID" in
    ubuntu)
        FAMILY="debian"
        ;;
    almalinux)
        FAMILY="rhel"
        ;;
    *)
        # Fall back to the family hint for close relatives.
        if echo "$OS_LIKE" | grep -qi "debian"; then
            FAMILY="debian"
        elif echo "$OS_LIKE" | grep -qiE "rhel|fedora"; then
            FAMILY="rhel"
        else
            echo "ERROR: unsupported OS '$OS_ID'. This script supports Ubuntu and AlmaLinux." >&2
            exit 1
        fi
        ;;
esac

echo ">> Detected OS: ${PRETTY_NAME:-$OS_ID} (family: $FAMILY)"

# ---------------------------------------------------------------------------
# Per-family settings
# ---------------------------------------------------------------------------
if [ "$FAMILY" = "debian" ]; then
    SERVICE_NAME="supervisor"
    CONF_DIR="/etc/supervisor/conf.d"
    CONF_FILE="$CONF_DIR/$PROGRAM_NAME.conf"
    DEFAULT_USER="www-data"
else
    SERVICE_NAME="supervisord"
    CONF_DIR="/etc/supervisord.d"
    CONF_FILE="$CONF_DIR/$PROGRAM_NAME.ini"
    DEFAULT_USER="apache"
fi

RUN_USER="${RUN_USER:-$DEFAULT_USER}"

# ---------------------------------------------------------------------------
# Install Supervisor if missing
# ---------------------------------------------------------------------------
if command -v supervisorctl >/dev/null 2>&1; then
    echo ">> Supervisor already installed."
else
    echo ">> Supervisor not found. Installing..."
    if [ "$FAMILY" = "debian" ]; then
        apt-get update
        apt-get install -y supervisor
    else
        # Supervisor ships in EPEL on AlmaLinux.
        dnf install -y epel-release
        dnf install -y supervisor
    fi
fi

# ---------------------------------------------------------------------------
# Enable on boot + ensure running
# ---------------------------------------------------------------------------
echo ">> Enabling $SERVICE_NAME to start on boot..."
systemctl enable "$SERVICE_NAME"
systemctl start "$SERVICE_NAME"

mkdir -p "$CONF_DIR"

# ---------------------------------------------------------------------------
# Write the program config
# ---------------------------------------------------------------------------
echo ">> Writing $CONF_FILE"
cat > "$CONF_FILE" <<EOF
[program:$PROGRAM_NAME]
command=$PHP_BIN artisan sip2:serve
directory=$PROJECT_DIR
user=$RUN_USER
autostart=true
autorestart=true
numprocs=1
startsecs=5
startretries=3
stopsignal=TERM
stopwaitsecs=30
redirect_stderr=true
stdout_logfile=$LOG_FILE
EOF

# Make sure the log file is writable by the run user.
touch "$LOG_FILE" 2>/dev/null || true
chown "$RUN_USER" "$LOG_FILE" 2>/dev/null || true

# ---------------------------------------------------------------------------
# Load + (re)start the program
# ---------------------------------------------------------------------------
echo ">> Reloading Supervisor and starting $PROGRAM_NAME..."
supervisorctl reread
supervisorctl update
supervisorctl restart "$PROGRAM_NAME" 2>/dev/null || supervisorctl start "$PROGRAM_NAME"

echo
echo ">> Done. Status:"
supervisorctl status "$PROGRAM_NAME" || true

echo
echo "Reminder: SIP2 must be enabled (sip2_services_enabled) and the port/IP in"
echo "app/config/sip2.php must be free. Only one sip2:serve instance per host."
