#!/usr/bin/env bash
set -e

PREFIX="dev_pkg_"
STATE_FILE="/var/lib/ansipa-packages/installed.list"
mkdir -p "$(dirname "$STATE_FILE")"

# Detect distro
if [ -f /etc/os-release ]; then
    . /etc/os-release
    DISTRO=$ID
else
    DISTRO="unknown"
fi

# -----------------------------
# Package install function
# -----------------------------
install_pkg() {
    PKG="$1"
    case "$DISTRO" in
        arch)
            pacman -Sy --noconfirm "$PKG" 2>/dev/null || true
            ;;
        debian|ubuntu)
            apt update -y && apt install -y "$PKG" 2>/dev/null || true
            ;;
        rhel|centos|rocky|almalinux)
            yum install -y "$PKG" 2>/dev/null || dnf install -y "$PKG" 2>/dev/null || true
            ;;
        fedora)
            dnf install -y "$PKG" 2>/dev/null || true
            ;;
        opensuse*|sles)
            zypper install -y "$PKG" 2>/dev/null || true
            ;;
    esac
}

# -----------------------------
# Package uninstall function
# -----------------------------
remove_pkg() {
    PKG="$1"
    case "$DISTRO" in
        arch)
            pacman -Rns --noconfirm "$PKG" 2>/dev/null || true
            ;;
        debian|ubuntu)
            apt remove -y "$PKG" 2>/dev/null || true
            ;;
        rhel|centos|rocky|almalinux)
            yum remove -y "$PKG" 2>/dev/null || dnf remove -y "$PKG" 2>/dev/null || true
            ;;
        fedora)
            dnf remove -y "$PKG" 2>/dev/null || true
            ;;
        opensuse*|sles)
            zypper remove -y "$PKG" 2>/dev/null || true
            ;;
    esac
}

# -----------------------------
# Get FreeIPA install groups
# -----------------------------
IPA_GROUPS=$(ipa group-find --pkey-only | awk '/Group name:/{print $NF}' | grep "^$PREFIX" || true)

# Extract package names from groups
DESIRED_PKGS=()
for G in $IPA_GROUPS; do
    PKG="${G#$PREFIX}"
    DESIRED_PKGS+=("$PKG")
done

# -----------------------------
# Get currently installed packages
# -----------------------------
case "$DISTRO" in
    arch)
        INSTALLED_PKGS=$(pacman -Qq)
        ;;
    debian|ubuntu)
        INSTALLED_PKGS=$(dpkg -l | awk '/^ii/ {print $2}')
        ;;
    rhel|centos|rocky|almalinux|fedora)
        INSTALLED_PKGS=$(rpm -qa --qf "%{NAME}\n")
        ;;
    opensuse*|sles)
        INSTALLED_PKGS=$(rpm -qa --qf "%{NAME}\n")
        ;;
    *)
        INSTALLED_PKGS=""
        ;;
esac

# -----------------------------
# Install missing packages and record them
# -----------------------------
[[ -f "$STATE_FILE" ]] || touch "$STATE_FILE"

for PKG in "${DESIRED_PKGS[@]}"; do
    if ! echo "$INSTALLED_PKGS" | grep -qx "$PKG"; then
        echo "[INFO] Installing package: $PKG"
        install_pkg "$PKG"
    fi
    # Record that ansipa manages this package
    grep -qxF "$PKG" "$STATE_FILE" || echo "$PKG" >> "$STATE_FILE"
done

# -----------------------------
# Remove packages no longer desired
# Only remove packages previously installed by ansipa (tracked in state file).
# -----------------------------
while IFS= read -r PKG; do
    [[ -z "$PKG" ]] && continue
    # Still desired? Leave it alone.
    if printf '%s\n' "${DESIRED_PKGS[@]+"${DESIRED_PKGS[@]}"}" | grep -qxF "$PKG"; then
        continue
    fi
    echo "[INFO] Removing package no longer required by any IPA group: $PKG"
    remove_pkg "$PKG"
    # Remove from state file
    grep -vxF "$PKG" "$STATE_FILE" > "${STATE_FILE}.tmp" && mv "${STATE_FILE}.tmp" "$STATE_FILE"
done < "$STATE_FILE"

# Persist current desired list (union of what's already tracked + newly added)
if [[ ${#DESIRED_PKGS[@]} -gt 0 ]]; then
    printf '%s\n' "${DESIRED_PKGS[@]}" | sort -u > "${STATE_FILE}.tmp"
    # Merge: keep previously-managed packages that are still desired
    sort -u "$STATE_FILE" "${STATE_FILE}.tmp" > "${STATE_FILE}.merged"
    comm -12 "${STATE_FILE}.merged" "${STATE_FILE}.tmp" > "$STATE_FILE"
    rm -f "${STATE_FILE}.tmp" "${STATE_FILE}.merged"
fi
