#!/bin/bash
# ==============================================================================
# MeshDash Installer Script (Debian/Ubuntu/Raspberry Pi OS Focused Version)
#
# MeshDash is Free and Open Source software, licensed under the GPLv3.
# For full license details, please see: https://www.gnu.org/licenses/gpl-3.0.html
#
# This script automates the setup of MeshDash natively.
# ==============================================================================

set -o errexit
set -o pipefail

RED='\033[0;31m'
GREEN='\033[0;32m'
YELLOW='\033[0;33m'
BLUE='\033[0;34m'
CYAN='\033[0;36m'
BOLD='\033[1m'
NC='\033[0m'

# ------------------------- Dynamic URLs (Set by Setup Wizard) -------------------------
MESHDASH_VERSION="{VERSION}"                 # Version of MeshDash to install
API_KEY="{API_KEY}"                           # Your unique API key for config access
BASE_URL="{BASE_URL}"                          # MeshDash server URL

# --- [CRITICAL SAFEGUARD] PREVENT RAW TEMPLATE EXECUTION ---
if [[ "$BASE_URL" == \{* ]] || [[ "$API_KEY" == \{* ]]; then
    printf "\n${RED}${BOLD}[ERROR]${NC} This is a raw template script.\n"
    printf "You must generate your specific installation command using the Setup Wizard at:\n"
    printf "${CYAN}https://meshdash.co.uk/c2_setup.php${NC}\n\n"
    printf "If you are trying to run this inside Docker, please use the official image instead:\n"
    printf "${CYAN}rusjpmd/meshdash-runner:latest${NC}\n\n"
    exit 1
fi
# --------------------------------------------------------------------------------------

ZIP_URL="$BASE_URL/versions/$MESHDASH_VERSION/mesh-dash.zip"
CONFIG_URL="$BASE_URL/user_setup_core.php?action=download_config&key=$API_KEY"

# ------------------------- Service Auto-Install -------------------------
# Set AUTO_SERVICE to "yes" to automatically install and start systemd service without prompting,
# "no" to skip entirely, or leave as is (or empty) for interactive prompt.
AUTO_SERVICE="{AUTO_SERVICE}"
# ------------------------------------------------------------------------

INSTALL_SUBDIR="mesh-dash"
PYTHON_CMD="python3"
MIN_PYTHON_VERSION="3.9"
VENV_DIR="mesh-dash_venv"
ZIP_FILE="mesh-dash.zip"
REQUIREMENTS_FILE="requirements.txt"
MAIN_SCRIPT="meshtastic_dashboard.py"
TOOLS_SCRIPT="mesh_dash_tools.sh"
CONFIG_FILE=".mesh-dash_config"
SERVICE_NAME="mesh-dash"
SERVICE_FILE="/etc/systemd/system/${SERVICE_NAME}.service"
RUN_SCRIPT_NAME="run_meshdash.sh"
SUMMARY_FILE="Installation_details.txt"
GET_PIP_URL="https://bootstrap.pypa.io/get-pip.py"

SUDO_AVAILABLE=false
PYTHON_VERSION_DETECTED=""
OS_ID=""
OS_VERSION_ID=""
SCRIPT_RUN_DIR=""
INSTALLER_SCRIPT_PATH=""
BOX_WIDTH=70

# -------------------------------------------------------------------
# Utility functions
# -------------------------------------------------------------------
show_ascii_art() {
    printf "\n${CYAN}${BOLD}"
cat << "EOF"
 _  _  ____  ____  _  _  ____   __   ____  _  _
( \/ )(  __)/ ___)/ )( \(    \ / _\ / ___)/ )( \
/ \/ \ ) _) \___ \) __ ( ) D (/    \\___ \) __ (
\_)(_/(____)(____/\_)(_/(____/\_/\_/(____/\_)(_/

EOF
    printf "${NC}\n"
    sleep 2
}
echoinfo() {
  printf "${BLUE}[INFO]${NC} %s\n" "$1"
}

echoerror() {
  printf "${RED}${BOLD}[ERROR]${NC} %s\n" "$@" >&2
}

echowarn() {
  printf "${YELLOW}[WARN]${NC} %s\n" "$1"
}

echostep() {
  printf "\n\n${GREEN}${BOLD}=== %s ===${NC}\n" "$1"
}

echosubstep() {
    printf "\n${CYAN}--- %s ---${NC}\n" "$1"
}

center_text() {
    local text="$1"
    local text_len_ansi
    text_len_ansi=$(echo -n "$text" | sed 's/\x1b\[[0-9;]*[mK]//g' | wc -c)
    local pad_len=$(( (BOX_WIDTH - 2 - text_len_ansi) / 2 ))
    [ $pad_len -lt 0 ] && pad_len=0
    local space_pad=$(printf '%*s' $pad_len '')
    local remaining_pad=$(( BOX_WIDTH - 2 - pad_len - text_len_ansi ))
    [ $remaining_pad -lt 0 ] && remaining_pad=0
    printf "#%s%s%*s#\n" "$space_pad" "$text" $remaining_pad ""
}

compare_versions() {
    local ver1=$1
    local ver2=$2
    if command -v dpkg &>/dev/null; then
        if dpkg --compare-versions "$ver1" "ge" "$ver2"; then
            return 0
        else
            return 1
        fi
    elif command -v sort &>/dev/null && sort --version | grep -q 'GNU coreutils'; then
        echowarn "dpkg not available, falling back to sort -V for version comparison."
        if [ "$(printf '%s\n%s\n' "$ver1" "$ver2" | sort -V | head -n 1)" = "$ver2" ]; then
            return 0
        else
            return 1
        fi
    else
        echowarn "dpkg and sort -V not available, using simpler (less robust) version comparison."
        local ver1_major ver1_minor ver2_major ver2_minor
        ver1_major=$(echo "$ver1" | cut -d. -f1)
        ver1_minor=$(echo "$ver1" | cut -d. -f2)
        ver2_major=$(echo "$ver2" | cut -d. -f1)
        ver2_minor=$(echo "$ver2" | cut -d. -f2)

        if [ "$ver1_major" -gt "$ver2_major" ]; then
            return 0
        elif [ "$ver1_major" -lt "$ver2_major" ]; then
            return 1
        elif [ "$ver1_minor" -ge "$ver2_minor" ]; then
            return 0
        else
            return 1
        fi
    fi
}

download_get_pip() {
    local target_dir="$1"
    local get_pip_path="${target_dir}/get-pip.py"

    echoinfo "Attempting to download get-pip.py from $GET_PIP_URL..."
    if ! wget --progress=dot:giga -q "$GET_PIP_URL" -O "$get_pip_path"; then
        echoerror "Failed to download get-pip.py from $GET_PIP_URL."
        rm -f "$get_pip_path"
        return 1
    fi
    echoinfo "get-pip.py downloaded to $get_pip_path"
    return 0
}

# -------------------------------------------------------------------
# Prerequisite checks
# -------------------------------------------------------------------
check_command() {
  local cmd="$1"
  local package_name="$2"
  local optional="${3:-false}"

  echoinfo "Checking for command: '$cmd'..."
  if command -v "$cmd" &> /dev/null; then
    echoinfo "'$cmd' found."
    if [ "$cmd" == "sudo" ]; then SUDO_AVAILABLE=true; fi
    if [[ "$cmd" == python* ]]; then
        local version_string
        version_string=$("$cmd" --version 2>&1)
        if [[ "$version_string" =~ Python[[:space:]]+([0-9]+\.[0-9]+(\.[0-9]+)?) ]]; then
            if [ "$cmd" == "$PYTHON_CMD" ]; then
                PYTHON_VERSION_DETECTED="${BASH_REMATCH[1]}"
                echoinfo "Detected Python version for $PYTHON_CMD: $PYTHON_VERSION_DETECTED"
            else
                echoinfo "Detected version for $cmd: ${BASH_REMATCH[1]}"
            fi
        else
            echowarn "Could not reliably determine Python version from '$version_string' for $cmd."
            if [ "$cmd" == "$PYTHON_CMD" ]; then PYTHON_VERSION_DETECTED=""; fi
        fi
    fi
    return 0
  fi

  if [ "$optional" = true ]; then
    echowarn "'$cmd' command not found. Some features might require it. Optional package: '$package_name'"
    if [ "$cmd" == "systemctl" ]; then echowarn "Systemd service setup will be skipped."; fi
    return 1
  fi

  echoerror "'$cmd' command not found. This is required."
  if [ "$cmd" == "sudo" ]; then
      echoerror "Cannot automatically install 'sudo'. Please install it manually. Exiting."
      exit 1
  fi

  if ! command -v sudo &> /dev/null; then
      SUDO_AVAILABLE=false
      echoerror "Automatic installation requires 'sudo', but it's not available. Please install '$package_name' manually."
      exit 1
  else
      SUDO_AVAILABLE=true
  fi

  echoinfo "Attempting to automatically install '$package_name' using sudo apt..."
  echoinfo "Running 'sudo apt update' (quietly)..."
  if ! sudo apt update -qq > /dev/null; then
      echowarn "'sudo apt update' failed. Attempting install anyway..."
  fi
  echoinfo "Running 'sudo apt install -y $package_name' (quietly)..."
  if ! sudo apt install -y -qq "$package_name" > /dev/null; then
    echoerror "Failed to automatically install '$package_name'. Please install it manually."
    exit 1
  fi
  echoinfo "'$package_name' installed successfully via sudo apt."
  if ! command -v "$cmd" &> /dev/null; then
      echoerror "Installation of '$package_name' reported success, but command '$cmd' still not found. This is unexpected."
      exit 1
  fi
    if [[ "$cmd" == python* ]]; then
        local version_string_after_install
        version_string_after_install=$("$cmd" --version 2>&1)
        if [[ "$version_string_after_install" =~ Python[[:space:]]+([0-9]+\.[0-9]+(\.[0-9]+)?) ]]; then
            if [ "$cmd" == "$PYTHON_CMD" ]; then
                PYTHON_VERSION_DETECTED="${BASH_REMATCH[1]}"
                echoinfo "Detected Python version after install for $PYTHON_CMD: $PYTHON_VERSION_DETECTED"
            fi
        fi
    fi
  echoinfo "'$cmd' is now available."
  return 0
}

check_python_version() {
    echoinfo "Checking if Python version '$PYTHON_VERSION_DETECTED' (from $PYTHON_CMD) meets minimum requirement ($MIN_PYTHON_VERSION)..."
    if [ -z "$PYTHON_VERSION_DETECTED" ]; then
        if ! command -v "$PYTHON_CMD" &> /dev/null; then
            echoerror "Python command '$PYTHON_CMD' not found. Please install Python $MIN_PYTHON_VERSION or newer."
            if ! command -v sudo &> /dev/null; then SUDO_AVAILABLE=false; else SUDO_AVAILABLE=true; fi

            if [ "$SUDO_AVAILABLE" = true ]; then
                echoinfo "Attempting to install generic 'python3' package..."
                check_command "$PYTHON_CMD" "python3" false
                check_python_version
                return $?
            else
                echoerror "Sudo not available, cannot attempt automatic python3 install."
                exit 1
            fi
        else
             echowarn "Could not determine Python version via '$PYTHON_CMD --version'."
             echowarn "Proceeding, but installation might fail if Python version is too old (< $MIN_PYTHON_VERSION)."
             return 0
        fi
    fi

    if compare_versions "$PYTHON_VERSION_DETECTED" "$MIN_PYTHON_VERSION"; then
        echoinfo "Python version $PYTHON_VERSION_DETECTED is sufficient (>= $MIN_PYTHON_VERSION)."
        return 0
    else
        printf "\n" >&2
        echoerror "-----------------------------------------------------"
        echoerror "${BOLD}Python Version Check Failed!${NC}"
        echoerror "-----------------------------------------------------"
        echoerror "This application requires Python $MIN_PYTHON_VERSION or newer."
        echoerror "Your system's default '$PYTHON_CMD' version is $PYTHON_VERSION_DETECTED."
        printf "\n" >&2

        if [[ "$OS_ID" == "raspios" || "$OS_ID" == "debian" ]] && [[ "$OS_VERSION_ID" == "10" ]]; then
            echowarn "Detected OS version ${OS_VERSION_ID} (Buster based). This version typically requires a Python upgrade."
        else
            local os_major_version
            os_major_version=$(echo "$OS_VERSION_ID" | cut -d. -f1)
            if [[ ("$OS_ID" == "raspios" || "$OS_ID" == "debian") && "$os_major_version" =~ ^[0-9]+$ && "$os_major_version" -lt 10 ]]; then
                echowarn "Detected OS version ${OS_VERSION_ID} (Older than Buster). Automatic Python upgrade might be difficult."
            fi
        fi

        echowarn "This script can attempt to install Python $MIN_PYTHON_VERSION using 'apt' and 'sudo'."
        echowarn "On older systems, this usually involves adding the 'deadsnakes' PPA."
        echowarn "${BOLD}WARNING:${NC} Modifying system Python or adding PPAs can have unintended consequences."
        printf "\n" >&2

        if ! command -v sudo &> /dev/null; then SUDO_AVAILABLE=false; else SUDO_AVAILABLE=true; fi

        local confirmation
        read -p "Attempt automatic installation/upgrade of Python $MIN_PYTHON_VERSION? (y/N): " confirmation
        confirmation_lower=$(echo "$confirmation" | tr '[:upper:]' '[:lower:]')
        printf "\n"

        if [[ "$confirmation_lower" == "y" || "$confirmation_lower" == "yes" ]]; then
            echoinfo "Proceeding with Python $MIN_PYTHON_VERSION installation attempt..."
            if [ "$SUDO_AVAILABLE" != true ]; then
                echoerror "sudo is required but not available. Please install Python $MIN_PYTHON_VERSION manually."
                exit 1
            fi

            local ppa_added=false
            echoinfo "Checking available packages..."
            sudo apt update -qq > /dev/null

            if ! apt-cache show "python${MIN_PYTHON_VERSION}" &> /dev/null; then
                echowarn "Python ${MIN_PYTHON_VERSION} package not found in standard repositories or after update."
                echoinfo "The 'deadsnakes' PPA provides newer Python versions for Debian/Ubuntu based systems."
                local ppa_confirmation
                read -p "Add 'ppa:deadsnakes/ppa' to your system's software sources? (y/N): " ppa_confirmation
                ppa_confirmation_lower=$(echo "$ppa_confirmation" | tr '[:upper:]' '[:lower:]')
                printf "\n"
                if [[ "$ppa_confirmation_lower" == "y" || "$ppa_confirmation_lower" == "yes" ]]; then
                    echoinfo "Adding ppa:deadsnakes/ppa..."
                    if ! command -v add-apt-repository &> /dev/null; then
                        echoinfo "Installing 'software-properties-common'..."
                        if ! sudo apt-get install -y -qq software-properties-common >/dev/null; then
                            echoerror "Failed to install 'software-properties-common'. Cannot add PPA."
                            exit 1
                        fi
                       fi
                    if ! sudo add-apt-repository -y ppa:deadsnakes/ppa; then
                        echoerror "Failed to add PPA 'ppa:deadsnakes/ppa'. Please try manually."
                        exit 1
                    fi
                    ppa_added=true
                    echoinfo "PPA added. Updating package lists (this may take a moment)..."
                    if ! sudo apt update; then
                        echoerror "Failed to update package lists after adding PPA. Run 'sudo apt update' manually."
                        exit 1
                    fi
                    echoinfo "Package lists updated."
                else
                    echoerror "PPA not added. Cannot proceed with automatic Python installation."
                    exit 1
                fi
            else
                echoinfo "Python ${MIN_PYTHON_VERSION} package seems available (or PPA already added)."
            fi

            local py_pkg="python${MIN_PYTHON_VERSION}"
            local venv_pkg="python${MIN_PYTHON_VERSION}-venv"
            echoinfo "Attempting to install packages: $py_pkg $venv_pkg..."
            if ! sudo apt install -y "$py_pkg" "$venv_pkg"; then
                echoerror "Failed to install Python $MIN_PYTHON_VERSION packages ($py_pkg, $venv_pkg)."
                echoerror "Check errors above. You may need to resolve dependencies or install manually."
                exit 1
            fi
            echoinfo "Core Python $MIN_PYTHON_VERSION packages installed."

            local new_python_cmd="/usr/bin/python${MIN_PYTHON_VERSION}"
            if ! command -v "$new_python_cmd" &> /dev/null; then
                echoerror "Installation reported success, but '$new_python_cmd' not found! Cannot proceed."
                exit 1
            fi
            echoinfo "Verifying new Python version at $new_python_cmd..."
            local new_version_string
            new_version_string=$("$new_python_cmd" --version 2>&1)
            echoinfo " -> $new_version_string"

            echoinfo "Verifying pip for $new_python_cmd..."
            if ! "$new_python_cmd" -m pip --version &> /dev/null; then
                echowarn "pip module for $new_python_cmd not found after package installation. Attempting to bootstrap..."
                if ! sudo "$new_python_cmd" -m ensurepip --upgrade; then
                    echowarn "ensurepip failed for $new_python_cmd. Attempting get-pip.py..."
                    local temp_get_pip_dir
                    temp_get_pip_dir=$(mktemp -d) || { echoerror "Failed to create temp dir for get-pip.py"; exit 1; }
                    if download_get_pip "$temp_get_pip_dir"; then
                        echoinfo "Running get-pip.py with $new_python_cmd..."
                        if ! sudo "$new_python_cmd" "${temp_get_pip_dir}/get-pip.py" --no-warn-script-location; then
                            rm -rf "$temp_get_pip_dir"
                            echoerror "get-pip.py failed for $new_python_cmd."
                            echoerror "Critical: pip could not be installed for $new_python_cmd. Please resolve manually."
                            exit 1
                        fi
                        echoinfo "pip installed via get-pip.py for $new_python_cmd."
                    else
                        rm -rf "$temp_get_pip_dir"
                        echoerror "Failed to download get-pip.py. pip not installed for $new_python_cmd."
                        exit 1
                    fi
                    rm -rf "$temp_get_pip_dir"
                else
                    echoinfo "pip bootstrapped successfully using ensurepip for $new_python_cmd."
                fi
                if ! "$new_python_cmd" -m pip --version &> /dev/null; then
                    echoerror "CRITICAL: pip module for $new_python_cmd is still not working after all attempts."
                    exit 1
                fi
            fi
            "$new_python_cmd" -m pip --version

            echoinfo "Updating installer to use $new_python_cmd for subsequent steps."
            PYTHON_CMD="$new_python_cmd"
            if [[ "$new_version_string" =~ Python[[:space:]]+([0-9]+\.[0-9]+(\.[0-9]+)?) ]]; then
                PYTHON_VERSION_DETECTED="${BASH_REMATCH[1]}"
                echoinfo "Updated PYTHON_VERSION_DETECTED to $PYTHON_VERSION_DETECTED"
            else
                 PYTHON_VERSION_DETECTED=$(echo "$MIN_PYTHON_VERSION" | cut -d. -f1,2)
                 echowarn "Could not parse new version string, assuming $PYTHON_VERSION_DETECTED"
            fi

            echowarn "--------------------------------------------------------------------"
            echowarn "${BOLD}IMPORTANT:${NC} The installer will now use '$PYTHON_CMD'."
            echowarn "Your system's default 'python3' might still point to the old version."
            echowarn "To change the default 'python3', consider 'sudo update-alternatives --config python3' AFTER this script."
            echowarn "--------------------------------------------------------------------"
            sleep 3
            return 0
        else
            echoerror "Automatic Python upgrade declined. Please upgrade Python to $MIN_PYTHON_VERSION+ manually."
            exit 1
        fi
    fi
}

check_python_module() {
    local module_name="$1"
    local package_hint_template="$2"
    local is_pip_check=false
    local is_venv_check=false
    if [ "$module_name" == "pip" ]; then is_pip_check=true; fi
    if [ "$module_name" == "venv" ]; then is_venv_check=true; fi

    local python_major_minor=""
    if [[ "$PYTHON_VERSION_DETECTED" =~ ^([0-9]+\.[0-9]+) ]]; then
        python_major_minor="${BASH_REMATCH[1]}"
    else
        local current_py_ver
        current_py_ver=$($PYTHON_CMD --version 2>&1)
        if [[ "$current_py_ver" =~ Python[[:space:]]+([0-9]+\.[0-9]+) ]]; then
             python_major_minor="${BASH_REMATCH[1]}"
        else
            python_major_minor="3"
            echowarn "Could not determine specific Python X.Y version for module check, using generic fallback."
        fi
    fi

    echoinfo "Checking for system Python module: '$module_name' using '$PYTHON_CMD'..."
    if ! $PYTHON_CMD -m "$module_name" --version &> /dev/null && \
       ! ( [ "$module_name" == "venv" ] && $PYTHON_CMD -m "$module_name" -h &> /dev/null ); then
        echowarn "System Python module '$module_name' not found or not working correctly with '$PYTHON_CMD'."

        if ! command -v sudo &> /dev/null; then SUDO_AVAILABLE=false; else SUDO_AVAILABLE=true; fi

        if [ "$SUDO_AVAILABLE" = false ]; then
            echoerror "Required Python module '$module_name' is missing and sudo is not available for automatic installation."
            echoerror "Please install the necessary package for '$module_name' for '$PYTHON_CMD' manually."
            exit 1
        fi

        local installed_successfully=false
        if [ "$is_pip_check" = true ]; then
            echowarn "Attempting to install/bootstrap 'pip' for $PYTHON_CMD..."
            echoinfo "Step 1: Trying 'sudo apt install python3-pip'..."
            if ! sudo apt update -qq > /dev/null; then echowarn "apt update failed, continuing install attempt..."; fi
            if sudo apt install -y -qq python3-pip > /dev/null; then
                echoinfo "'python3-pip' package installed/updated."
                if $PYTHON_CMD -m pip --version &> /dev/null; then
                    echoinfo "'pip' module is now working with $PYTHON_CMD after python3-pip install."
                    installed_successfully=true
                else
                    echowarn "'pip' module still not working with $PYTHON_CMD after python3-pip install."
                fi
            else
                echowarn "'sudo apt install python3-pip' failed or did not resolve the issue."
            fi

            if [ "$installed_successfully" = false ]; then
                echoinfo "Step 2: Trying '$PYTHON_CMD -m ensurepip --upgrade'..."
                local ensurepip_cmd
                if [[ "$PYTHON_CMD" == /usr/bin/* || "$PYTHON_CMD" == /usr/local/bin/* ]]; then
                    ensurepip_cmd="sudo $PYTHON_CMD -m ensurepip --upgrade"
                    echoinfo "(Running ensurepip with sudo for system Python)"
                else
                    ensurepip_cmd="$PYTHON_CMD -m ensurepip --upgrade"
                fi
                if eval "$ensurepip_cmd" > /tmp/ensurepip_log 2>&1; then
                    echoinfo "'ensurepip' executed for $PYTHON_CMD."
                    rm -f /tmp/ensurepip_log
                    if $PYTHON_CMD -m pip --version &> /dev/null; then
                        echoinfo "'pip' module now working after ensurepip."
                        installed_successfully=true
                    else echowarn "'pip' still not working after ensurepip."; fi
                else
                    echowarn "'$PYTHON_CMD -m ensurepip --upgrade' failed. Log:"
                    head -n 10 /tmp/ensurepip_log; rm -f /tmp/ensurepip_log
                fi
            fi

            if [ "$installed_successfully" = false ]; then
                echoinfo "Step 3: Trying 'get-pip.py' for $PYTHON_CMD..."
                local temp_get_pip_dir
                temp_get_pip_dir=$(mktemp -d) || { echoerror "Failed to create temp dir"; exit 1; }
                if download_get_pip "$temp_get_pip_dir"; then
                    echoinfo "Running get-pip.py with $PYTHON_CMD..."
                    local get_pip_run_cmd
                    if [[ "$PYTHON_CMD" == /usr/bin/* || "$PYTHON_CMD" == /usr/local/bin/* ]]; then
                        get_pip_run_cmd="sudo $PYTHON_CMD ${temp_get_pip_dir}/get-pip.py --no-warn-script-location"
                        echoinfo "(Running get-pip.py with sudo)"
                    else
                        get_pip_run_cmd="$PYTHON_CMD ${temp_get_pip_dir}/get-pip.py --no-warn-script-location"
                    fi
                    if eval "$get_pip_run_cmd" > /tmp/getpip_log 2>&1; then
                        echoinfo "get-pip.py executed."
                        rm -f /tmp/getpip_log
                        if $PYTHON_CMD -m pip --version &> /dev/null; then
                            echoinfo "'pip' now working after get-pip.py."
                            installed_successfully=true
                        else echowarn "'pip' still not working after get-pip.py."; fi
                    else
                        echowarn "get-pip.py failed. Log:"
                        head -n 10 /tmp/getpip_log; rm -f /tmp/getpip_log
                    fi
                else echowarn "Failed to download get-pip.py."; fi
                rm -rf "$temp_get_pip_dir"
            fi

            if [ "$installed_successfully" = false ]; then
                echoerror "All attempts to install/bootstrap 'pip' for $PYTHON_CMD failed."
                exit 1
            fi
        elif [ "$is_venv_check" = true ]; then
            local specific_venv_pkg_name="python${python_major_minor}-venv"
            local generic_venv_pkg_name="python3-venv"
            echowarn "Attempting automatic installation of venv package for $PYTHON_CMD..."
            if ! sudo apt update -qq > /dev/null; then echowarn "apt update failed."; fi
            echoinfo "Trying to install '$specific_venv_pkg_name'..."
            if sudo apt install -y -qq "$specific_venv_pkg_name" > /dev/null; then
                echoinfo "'$specific_venv_pkg_name' installed."
                installed_successfully=true
            else
                echowarn "Failed to install '$specific_venv_pkg_name'. Trying '$generic_venv_pkg_name'..."
                if sudo apt install -y -qq "$generic_venv_pkg_name" > /dev/null; then
                    echoinfo "'$generic_venv_pkg_name' installed."
                    installed_successfully=true
                else echowarn "Failed to install '$generic_venv_pkg_name'."; fi
            fi
            if [ "$installed_successfully" = false ]; then
                echoerror "Failed to install venv package for $PYTHON_CMD."
                exit 1
            fi
        else
            echoerror "Module '$module_name' missing for $PYTHON_CMD. No auto-install rule."
            exit 1
        fi

        if ! $PYTHON_CMD -m "$module_name" --version &> /dev/null && \
           ! ( [ "$module_name" == "venv" ] && $PYTHON_CMD -m "$module_name" -h &> /dev/null ); then
            echoerror "Module '$module_name' still not functional after install attempt."
            exit 1
        fi
        echoinfo "Module '$module_name' now functional with $PYTHON_CMD."
    fi

    echoinfo "System Python module '$module_name' confirmed functional with $PYTHON_CMD."

    if [ "$is_venv_check" = true ]; then
        local specific_venv_pkg_for_dpkg="python${python_major_minor}-venv"
        local generic_venv_pkg_for_dpkg="python3-venv"
        echoinfo "Performing dpkg check for venv: '$specific_venv_pkg_for_dpkg' / '$generic_venv_pkg_for_dpkg'..."
        if ! dpkg-query -W -f='${Status}' "$specific_venv_pkg_for_dpkg" 2>/dev/null | grep -q "install ok installed" && \
           ! dpkg-query -W -f='${Status}' "$generic_venv_pkg_for_dpkg" 2>/dev/null | grep -q "install ok installed"; then
            echowarn "System venv packages ('$specific_venv_pkg_for_dpkg', '$generic_venv_pkg_for_dpkg') appear missing/incomplete via dpkg."
            if [ "$SUDO_AVAILABLE" = false ]; then echoerror "Cannot reinstall venv package: sudo missing."; exit 1; fi
            echoinfo "Attempting to reinstall venv packages..."
            if ! sudo apt update -qq > /dev/null; then echowarn "apt update failed."; fi
            local reinstall_success=false
            if [[ "$python_major_minor" != "3" ]]; then
                echoinfo "Trying reinstall of '$specific_venv_pkg_for_dpkg'..."
                if sudo apt install -y -qq --reinstall "$specific_venv_pkg_for_dpkg" > /dev/null; then reinstall_success=true; fi
            fi
            if [ "$reinstall_success" = false ]; then
                echoinfo "Trying reinstall of '$generic_venv_pkg_for_dpkg'..."
                if sudo apt install -y -qq --reinstall "$generic_venv_pkg_for_dpkg" > /dev/null; then reinstall_success=true; fi
            fi
            if [ "$reinstall_success" = false ]; then echowarn "Failed to reinstall venv packages. Venv creation might fail.";
            else
                echoinfo "Venv packages reinstalled."
                if ! $PYTHON_CMD -m "$module_name" -h &> /dev/null && ! $PYTHON_CMD -m "$module_name" --version &> /dev/null; then
                    echoerror "Venv module still not functional after reinstall."; exit 1;
                fi
                echoinfo "Venv module functional after reinstall check."
            fi
        else echoinfo "System venv package appears correctly installed via dpkg."; fi
    fi
}

# -------------------------------------------------------------------
# OS detection
# -------------------------------------------------------------------
detect_os() {
    if [ -f /etc/os-release ]; then
        . /etc/os-release
        OS_ID="${ID:-unknown}"
        OS_VERSION_ID="${VERSION_ID:-unknown}"
        echoinfo "Detected OS: ${PRETTY_NAME:-$OS_ID $OS_VERSION_ID}"

        if [[ "$OS_ID" == "debian" || "$OS_ID" == "raspios" || "$OS_ID" == "ubuntu" ]]; then
            local os_major_version
            os_major_version=$(echo "$OS_VERSION_ID" | cut -d. -f1)

            if [[ "$os_major_version" == "10" ]]; then
                 echoinfo "Detected Debian 10 / Raspberry Pi OS Buster based system. Python upgrade might be needed."
            elif [[ "$os_major_version" =~ ^[0-9]+$ && "$os_major_version" -lt 10 ]]; then
                echowarn "Detected OS version $OS_VERSION_ID (Older than Buster/10). Automatic Python upgrade might be difficult or unsupported."
            fi
        else
            echowarn "Detected OS '$OS_ID' is not explicitly Debian, Ubuntu, or Raspberry Pi OS. Compatibility not guaranteed."
        fi
    else
        echowarn "Could not find /etc/os-release. Assuming a Debian-based system, but compatibility not guaranteed."
        OS_ID="unknown"; OS_VERSION_ID="unknown"
    fi
}

# -------------------------------------------------------------------
# Trap for exit
# -------------------------------------------------------------------
handle_exit() {
  local exit_code=$?
  if [ $exit_code -ne 0 ] && [[ $- == *e* ]]; then
    echoerror "Installation failed with exit code $exit_code."
  fi
}

trap handle_exit ERR

# -------------------------------------------------------------------
# Determine original user (for ownership correction)
# -------------------------------------------------------------------
ORIGINAL_USER=""
ORIGINAL_USER_PRIMARY_GROUP_ID=""
INSTALL_RUN_AS_ROOT=false
if [ -n "$SUDO_USER" ] && [ "$EUID" -eq 0 ]; then
    echoinfo "Installer is being run via sudo by user: ${BOLD}$SUDO_USER${NC}"
    ORIGINAL_USER="$SUDO_USER"
    INSTALL_RUN_AS_ROOT=true
    ORIGINAL_USER_PRIMARY_GROUP_ID=$(id -g "$SUDO_USER" 2>/dev/null)
    if [ -z "$ORIGINAL_USER_PRIMARY_GROUP_ID" ]; then
        echowarn "Could not reliably determine primary group ID for user '$SUDO_USER'."
    else
         echoinfo "Determined original user's primary GID: $ORIGINAL_USER_PRIMARY_GROUP_ID"
    fi
else
    ORIGINAL_USER=$(whoami)
    echoinfo "Installer is being run directly by user: ${BOLD}$ORIGINAL_USER${NC}"
    ORIGINAL_USER_PRIMARY_GROUP_ID=$(id -g)
fi

# -------------------------------------------------------------------
# Main installation flow
# -------------------------------------------------------------------
show_ascii_art
printf "\n${YELLOW}${BOLD}MeshDash is Free and Open Source software, licensed under the GPLv3.${NC}\n"
printf "${YELLOW}For full license details, please see: https://www.gnu.org/licenses/gpl-3.0.html${NC}\n\n"
sleep 3

printf "${GREEN}${BOLD}##############################################################\n"
printf "#       Welcome to the MeshDash Installer                #\n"
printf "# (Debian / Ubuntu / Raspberry Pi OS Focused)            #\n"
printf "#       Version to Install: %-30s #\n" "$MESHDASH_VERSION"
printf "##############################################################${NC}\n"
sleep 1

echoinfo "Starting MeshDash Installation..."
detect_os

if [ -n "${BASH_SOURCE[0]}" ] && [ -f "${BASH_SOURCE[0]}" ]; then
    INSTALLER_SCRIPT_PATH_ABS="$(readlink -f "${BASH_SOURCE[0]}")"
    SCRIPT_RUN_DIR="$(dirname "$INSTALLER_SCRIPT_PATH_ABS")"
    INSTALLER_SCRIPT_PATH="$INSTALLER_SCRIPT_PATH_ABS"
    echoinfo "Installer script path detected: $INSTALLER_SCRIPT_PATH"
else
    SCRIPT_RUN_DIR="$(pwd)"
    guessed_script_name=$(basename "$0" 2>/dev/null || echo "install.sh")
    INSTALLER_SCRIPT_PATH="$SCRIPT_RUN_DIR/$guessed_script_name"
    echowarn "Could not reliably determine absolute script path (e.g., if run via 'curl | bash')."
    echowarn "Using current directory as script base: '$SCRIPT_RUN_DIR'."
    echowarn "Using assumed script name: '$guessed_script_name'. Self-removal might fail if incorrect."
fi

INSTALL_DIR="$SCRIPT_RUN_DIR/$INSTALL_SUBDIR"
echoinfo "Installation target directory will be: ${BOLD}$INSTALL_DIR${NC}"
mkdir -p "$INSTALL_DIR" || { echoerror "Failed to create installation directory: $INSTALL_DIR."; exit 1; }
echoinfo "Installation directory created or already exists."
SUMMARY_FILE_PATH="$INSTALL_DIR/$SUMMARY_FILE"

# -------------------------------------------------------------------
# Prerequisite checks
# -------------------------------------------------------------------
echostep "Checking Prerequisites (Attempting auto-install via sudo apt if needed)"
if ! command -v apt &> /dev/null; then echoerror "'apt' not found. Debian-based system required."; exit 1; fi
check_command "sudo" "sudo" true
if ! command -v sudo &> /dev/null; then SUDO_AVAILABLE=false; else SUDO_AVAILABLE=true; fi

if [ "$SUDO_AVAILABLE" = true ]; then
    echoinfo "Attempting initial 'sudo apt update' (quietly)..."
    if ! sudo apt update -qq > /dev/null; then echowarn "Initial 'sudo apt update' failed."; else echoinfo "Initial package list update successful."; fi
else
    echowarn "sudo not available/usable. Auto prerequisite install unavailable."
    echowarn "Ensure wget, unzip, python3, python3-pip, python3-venv are manually installed."
fi

check_command "wget" "wget" false
check_command "unzip" "unzip" false
check_command "$PYTHON_CMD" "python3" false
check_python_version

# --- ARM/Raspberry Pi Compilation Safeguards ---
if [ "$SUDO_AVAILABLE" = true ]; then
    echoinfo "Ensuring build-essential and python headers are present (vital for compiling packages on Raspberry Pi)..."
    sudo apt install -y -qq build-essential "python${PYTHON_VERSION_DETECTED}-dev" libxml2-dev libxslt-dev > /dev/null 2>&1 || \
    sudo apt install -y -qq build-essential python3-dev libxml2-dev libxslt-dev > /dev/null 2>&1 || \
    echowarn "Failed to install some compilation headers. Pip install might still succeed using pre-built wheels."
fi
# -----------------------------------------------

echosubstep "Final check for 'pip' module using $PYTHON_CMD"
check_python_module "pip" "python3-pip"
echosubstep "Final check for 'venv' module using $PYTHON_CMD"
check_python_module "venv" "python<version>-venv"
SYSTEMCTL_AVAILABLE=false
if check_command "systemctl" "systemd" true; then SYSTEMCTL_AVAILABLE=true; fi
echoinfo "Prerequisite checks complete. Python: ${BOLD}$PYTHON_CMD${NC} (Version: ${BOLD}${PYTHON_VERSION_DETECTED:-N/A}${NC})"

# -------------------------------------------------------------------
# Download application archive
# -------------------------------------------------------------------
echostep "Downloading Application Archive (Version: $MESHDASH_VERSION)"
ZIP_FILE_PATH="$INSTALL_DIR/$ZIP_FILE"
echoinfo "Downloading '$ZIP_FILE' from '$ZIP_URL' to '$INSTALL_DIR'..."
if [[ "$ZIP_URL" == http://* ]]; then
    echowarn "Download URL uses HTTP. Checking for HTTPS redirect..."
    EFFECTIVE_URL=$(curl -sL --max-time 15 -w %{url_effective} -o /dev/null "$ZIP_URL")
    curl_exit_code=$?
    if [ $curl_exit_code -eq 0 ] && [[ "$EFFECTIVE_URL" == https://* ]]; then echoinfo "Redirected to HTTPS: $EFFECTIVE_URL"; ZIP_URL="$EFFECTIVE_URL";
    elif [ $curl_exit_code -ne 0 ]; then echowarn "Could not check HTTPS redirect (curl code: $curl_exit_code). Using original HTTP URL: $ZIP_URL";
    else echowarn "No HTTPS redirect or not to HTTPS. Using original HTTP URL: $ZIP_URL. Effective: $EFFECTIVE_URL"; fi
fi
if ! wget --timeout=120 --progress=bar:force -c "$ZIP_URL" -O "$ZIP_FILE_PATH"; then
    echoerror "Download failed from '$ZIP_URL'. Check URL and network."
    rm -f "$ZIP_FILE_PATH"; exit 1
fi
echoinfo "Download complete: $ZIP_FILE_PATH"

# -------------------------------------------------------------------
# Extract application files
# -------------------------------------------------------------------
echostep "Extracting Application Files"
if [ ! -f "$ZIP_FILE_PATH" ]; then
    echoerror "Downloaded archive '$ZIP_FILE_PATH' not found. This should not happen if download was successful."
    exit 1
fi
echoinfo "Extracting '$ZIP_FILE' into '$INSTALL_DIR'..."
if ! unzip -o -q "$ZIP_FILE_PATH" -d "$INSTALL_DIR"; then
    echoerror "Failed to extract '$ZIP_FILE'. The archive might be corrupted or 'unzip' command failed."
    exit 1
fi

MAIN_SCRIPT_PATH="$INSTALL_DIR/$MAIN_SCRIPT"
REQUIREMENTS_FILE_PATH="$INSTALL_DIR/$REQUIREMENTS_FILE"
if [ ! -f "$MAIN_SCRIPT_PATH" ]; then
    echoerror "Main application script '$MAIN_SCRIPT_PATH' not found after unzipping. Check archive contents."
    exit 1
fi
if [ ! -f "$REQUIREMENTS_FILE_PATH" ]; then
    echoerror "Python requirements file '$REQUIREMENTS_FILE_PATH' not found after unzipping. Check archive contents."
    exit 1
fi
echoinfo "Application files extracted successfully."

# Create .new file in static directory (optional, used by app to detect first run)
STATIC_DIR_PATH="$INSTALL_DIR/static"
NEW_FILE_PATH="$STATIC_DIR_PATH/.new"
if [ -d "$STATIC_DIR_PATH" ]; then
    echoinfo "Creating '.new' file in '$STATIC_DIR_PATH'..."
    if touch "$NEW_FILE_PATH"; then
        echoinfo "'.new' file created successfully at '$NEW_FILE_PATH'."
        if [ "$INSTALL_RUN_AS_ROOT" = true ] && [ -n "$ORIGINAL_USER" ]; then
            OWNERSHIP_SPEC_FILE="$ORIGINAL_USER"
            if [ -n "$ORIGINAL_USER_PRIMARY_GROUP_ID" ]; then
                OWNERSHIP_SPEC_FILE="$ORIGINAL_USER:$ORIGINAL_USER_PRIMARY_GROUP_ID"
            fi
            echoinfo "Ensuring ownership of '$NEW_FILE_PATH' is set to '$OWNERSHIP_SPEC_FILE'..."
            chown "$OWNERSHIP_SPEC_FILE" "$NEW_FILE_PATH" 2>/dev/null || echowarn "Failed to set ownership directly on '$NEW_FILE_PATH'."
        fi
    else
        echowarn "Failed to create '.new' file at '$NEW_FILE_PATH'. This might not be critical."
    fi
else
    echowarn "Directory '$STATIC_DIR_PATH' not found. Cannot create '.new' file. Check archive contents."
fi

# Set permissions for management tools script
TOOLS_SCRIPT_PATH="$INSTALL_DIR/$TOOLS_SCRIPT"
if [ -f "$TOOLS_SCRIPT_PATH" ]; then
    echoinfo "Setting execute permissions for '$TOOLS_SCRIPT_PATH'..."
    chmod +x "$TOOLS_SCRIPT_PATH" && echoinfo "Execute permissions set for tools script." || echowarn "Failed to set execute permissions."
else
    echowarn "Management tools script '$TOOLS_SCRIPT' not found in the archive."
fi

# -------------------------------------------------------------------
# Download configuration file
# -------------------------------------------------------------------
echostep "Downloading Configuration File"
CONFIG_FILE_PATH="$INSTALL_DIR/$CONFIG_FILE"
echoinfo "Downloading config from '$CONFIG_URL' to '$CONFIG_FILE_PATH'..."
if ! wget --timeout=30 -q "$CONFIG_URL" -O "$CONFIG_FILE_PATH"; then
    echoerror "Failed to download configuration file from '$CONFIG_URL'."
    exit 1
fi
echoinfo "Configuration file downloaded successfully."

# -------------------------------------------------------------------
# Set up Python virtual environment
# -------------------------------------------------------------------
echostep "Setting up Python Environment"

if [ -n "$VIRTUAL_ENV" ]; then
    # --- CASE 1: Active Virtual Environment Detected ---
    echoinfo "Detected active virtual environment: $VIRTUAL_ENV"
    echoinfo "Skipping creation of new venv. Installing into active environment."
    
    # Use the active environment path
    VENV_PATH="$VIRTUAL_ENV"
    PYTHON_EXEC="$VENV_PATH/bin/python"

    if [ ! -x "$PYTHON_EXEC" ]; then
        echoerror "Python executable not found in active venv at: $PYTHON_EXEC"
        exit 1
    fi
else
    # --- CASE 2: No Active Venv - Create New One ---
    echoinfo "No active virtual environment detected. Creating standard MeshDash venv..."
    
    VENV_PATH="$INSTALL_DIR/$VENV_DIR"
    echoinfo "Checking for existing virtual environment: '$VENV_PATH'..."
    if [ -d "$VENV_PATH" ]; then
        echowarn "Virtual environment directory '$VENV_DIR' already exists. Removing it to ensure a clean setup..."
        rm -rf "$VENV_PATH" || { echoerror "Failed to remove existing venv directory."; exit 1; }
        echoinfo "Existing venv removed."
    fi

    echoinfo "Creating Python virtual environment in '$VENV_PATH' using '$PYTHON_CMD -m venv'..."
    if ! "$PYTHON_CMD" -m venv "$VENV_PATH"; then
        echoerror "Failed to create Python virtual environment using '$PYTHON_CMD -m venv'."
        exit 1
    fi
    echoinfo "Virtual environment created successfully at '$VENV_PATH'."

    PYTHON_EXEC="$VENV_PATH/bin/python"
fi

# Ensure pip works in the selected environment
if ! "$PYTHON_EXEC" -m pip --version &> /dev/null; then
    echowarn "'pip' not found or not working in the environment. Attempting to bootstrap using 'ensurepip'..."
    if ! "$PYTHON_EXEC" -m ensurepip --upgrade --default-pip; then
        echoerror "Failed to bootstrap pip into the virtual environment using ensurepip."
        exit 1
    fi
    if ! "$PYTHON_EXEC" -m pip --version &> /dev/null; then
        echoerror "'pip' still not runnable in the virtual environment after ensurepip."
        exit 1
    fi
    echoinfo "'pip' bootstrapped successfully."
else
    echoinfo "'pip' found and working in the virtual environment."
fi
"$PYTHON_EXEC" -m pip --version

# -------------------------------------------------------------------
# Install Python dependencies
# -------------------------------------------------------------------
echostep "Installing Python Dependencies into Virtual Environment"
echoinfo "This may take several minutes, especially on less powerful devices..."

echosubstep "Upgrading pip within the virtual environment (quietly)"
"$PYTHON_EXEC" -m pip install --upgrade pip -q || echowarn "Failed to upgrade pip."

echosubstep "Installing dependencies from '$REQUIREMENTS_FILE_PATH'"
set +e # Temporarily disable exit-on-error

# Use --no-cache-dir to prevent RAM exhaustion on 512MB/1GB Raspberry Pis
# Use --default-timeout=120 for slow SD card compilation times
if ! "$PYTHON_EXEC" -m pip install --no-cache-dir --default-timeout=120 -r "$REQUIREMENTS_FILE_PATH"; then
    echowarn "Standard requirements install encountered an error."
    echoinfo "Attempting core fallback installation (bypassing optional system packages)..."
    
    # Fallback to explicit core packages, matching the Docker entrypoint list
    if ! "$PYTHON_EXEC" -m pip install --no-cache-dir --default-timeout=120 \
        uvicorn fastapi meshtastic sse-starlette mesh-rpc attrs Automat Babel \
        passlib[bcrypt] "bcrypt<4.0.0" python-multipart aiosqlite cryptography \
        python-jose[cryptography] sqlalchemy psutil beautifulsoup4 lxml \
        requests-toolbelt httpx jinja2 python-dotenv croniter tzlocal; then
        
        echoerror "Critical failure: Core fallback installation also failed."
        exit 1
    fi
fi

set -e # Re-enable exit-on-error
echoinfo "Python dependencies installed successfully."

# -------------------------------------------------------------------
# Generate manual run script
# -------------------------------------------------------------------
echostep "Generating Manual Run Script"
RUN_SCRIPT_PATH="$INSTALL_DIR/$RUN_SCRIPT_NAME"
echoinfo "Creating manual run script at: $RUN_SCRIPT_PATH"
cat > "$RUN_SCRIPT_PATH" <<- EOF
#!/bin/bash
# Run script for MeshDash - Generated by install.sh on $(date)

SCRIPT_DIR="\$( cd "\$( dirname "\${BASH_SOURCE[0]}" )" &> /dev/null && pwd )"

CONFIG_FILE="\$SCRIPT_DIR/$CONFIG_FILE"
# VENV_PATH is injected by the installer to ensure we support external/active environments
VENV_PATH="$VENV_PATH"
PYTHON_EXEC="\$VENV_PATH/bin/python"
MAIN_APP_SCRIPT="\$SCRIPT_DIR/$MAIN_SCRIPT"

RUN_BLUE='\\033[0;34m'; RUN_YELLOW='\\033[0;33m'; RUN_RED='\\033[0;31m'; RUN_BOLD='\\033[1m'; RUN_NC='\\033[0m'

run_echoinfo() { printf "\${RUN_BLUE}[INFO]\${RUN_NC} %s\\n" "\$1"; }
run_echoerror() { printf "\${RUN_RED}\${RUN_BOLD}[ERROR]\${RUN_NC} %s\\n" "\$1" >&2; }

if [ ! -d "\$VENV_PATH" ]; then
    run_echoerror "Virtual environment not found at: \$VENV_PATH"
    exit 1
fi
if [ ! -x "\$PYTHON_EXEC" ]; then
    run_echoerror "Python executable in virtual environment not found or not executable: \$PYTHON_EXEC"
    exit 1
fi
if [ ! -f "\$MAIN_APP_SCRIPT" ]; then
    run_echoerror "Main application script not found: \$MAIN_APP_SCRIPT"
    exit 1
fi

run_echoinfo "Starting MeshDash..."
run_echoinfo "Using Python: \$PYTHON_EXEC"
run_echoinfo "Application working directory: \$SCRIPT_DIR"
run_echoinfo "Press Ctrl+C to stop the application if running in foreground."

cd "\$SCRIPT_DIR" || { run_echoerror "Failed to change directory to \$SCRIPT_DIR"; exit 1; }

"\$PYTHON_EXEC" "\$MAIN_APP_SCRIPT"

RUN_EXIT_CODE=\$?
run_echoinfo "MeshDash finished with exit code \$RUN_EXIT_CODE."
exit \$RUN_EXIT_CODE
EOF

if [ $? -eq 0 ]; then
    chmod +x "$RUN_SCRIPT_PATH" && echoinfo "Manual run script '$RUN_SCRIPT_NAME' created and made executable." || echowarn "Failed to set execute permission."
else
    echoerror "Failed to write manual run script."
fi

# -------------------------------------------------------------------
# Correct ownership of installation directory (if run with sudo)
# -------------------------------------------------------------------
echostep "Correcting Installation Directory Ownership"
if [ "$INSTALL_RUN_AS_ROOT" = true ] && [ -n "$ORIGINAL_USER" ] && [ -d "$INSTALL_DIR" ]; then
    echoinfo "Script was run via sudo. Correcting ownership of '$INSTALL_DIR' for user '$ORIGINAL_USER'..."
    OWNERSHIP_SPEC="$ORIGINAL_USER"
    if [ -n "$ORIGINAL_USER_PRIMARY_GROUP_ID" ]; then
        OWNERSHIP_SPEC="$ORIGINAL_USER:$ORIGINAL_USER_PRIMARY_GROUP_ID"
    fi
    echoinfo "Applying ownership spec: ${BOLD}$OWNERSHIP_SPEC${NC} recursively to '$INSTALL_DIR'..."
    if chown -R "$OWNERSHIP_SPEC" "$INSTALL_DIR"; then
        echoinfo "Ownership successfully corrected."
    else
        echoerror "Failed to set ownership. Manual fix required: sudo chown -R $OWNERSHIP_SPEC \"$INSTALL_DIR\""
    fi
else
    echoinfo "Skipping ownership correction (script not run via sudo or original user unknown)."
fi

# -------------------------------------------------------------------
# Optional systemd service setup
# -------------------------------------------------------------------
echostep "Setup as Systemd Service (Optional)"
SERVICE_SETUP_SUCCESSFUL="no"

if [ -f /.dockerenv ]; then
    echoinfo "Docker environment detected. Skipping systemd service setup."
    AUTO_SERVICE="no"
    SYSTEMCTL_AVAILABLE=false
fi

# ----- Determine auto‑service behavior -----
auto_service_lower=$(echo "$AUTO_SERVICE" | tr '[:upper:]' '[:lower:]' | xargs)
# If the placeholder is still present (wizard didn't replace it), treat as empty
if [[ "$auto_service_lower" == "{auto_service}" ]]; then
    auto_service_lower=""
fi

if [ "$SYSTEMCTL_AVAILABLE" = true ] && [ "$SUDO_AVAILABLE" = true ]; then
    SERVICE_USER_GROUP_NAME=$(id -gn "$ORIGINAL_USER" 2>/dev/null) || SERVICE_USER_GROUP_NAME=""
    if [ -n "$SERVICE_USER_GROUP_NAME" ]; then
        echoinfo "Determined user group for service file: $SERVICE_USER_GROUP_NAME (for user $ORIGINAL_USER)"
    else
        echowarn "Could not determine primary group name for user '$ORIGINAL_USER'. Service file will not include 'Group='."
    fi

    # Decide whether to install service automatically, skip, or prompt
    do_service_setup=false
    if [[ "$auto_service_lower" == "yes" || "$auto_service_lower" == "true" || "$auto_service_lower" == "1" ]]; then
        echoinfo "AUTO_SERVICE is set to '$AUTO_SERVICE'. Will automatically install systemd service."
        do_service_setup=true
    elif [[ "$auto_service_lower" == "no" || "$auto_service_lower" == "false" || "$auto_service_lower" == "0" ]]; then
        echoinfo "AUTO_SERVICE is set to '$AUTO_SERVICE'. Skipping systemd service setup as per configuration."
        do_service_setup=false
    else
        # Interactive prompt (default when variable not set or unrecognised)
        read -p "Do you want to set up MeshDash to run automatically on boot as a systemd service? (y/N): " setup_service_prompt_response
        setup_service_lower=$(echo "$setup_service_prompt_response" | tr '[:upper:]' '[:lower:]')
        if [[ "$setup_service_lower" == "y" || "$setup_service_lower" == "yes" ]]; then
            do_service_setup=true
        else
            echoinfo "Skipping systemd service setup as per user request."
        fi
    fi

    if [ "$do_service_setup" = true ]; then
        echoinfo "Proceeding with systemd service setup for service: $SERVICE_NAME..."
        if [ ! -f "$CONFIG_FILE_PATH" ]; then echoerror "Config file '$CONFIG_FILE_PATH' missing. Cannot create service."; exit 1; fi
        if [ ! -x "$PYTHON_EXEC" ]; then echoerror "Python venv executable '$PYTHON_EXEC' missing. Cannot create service."; exit 1; fi
        if [ ! -f "$MAIN_SCRIPT_PATH" ]; then echoerror "Main application script '$MAIN_SCRIPT_PATH' missing. Cannot create service."; exit 1; fi

        echosubstep "Creating systemd service file: $SERVICE_FILE"
        SERVICE_CONTENT=$(cat <<- EOF
[Unit]
Description=MeshDash Service (Meshtastic Web Dashboard - v$MESHDASH_VERSION)
Documentation=https://meshdash.co.uk
After=network.target network-online.target
Wants=network-online.target

[Service]
Type=simple
User=$ORIGINAL_USER
$( [ -n "$SERVICE_USER_GROUP_NAME" ] && printf "Group=%s\n" "$SERVICE_USER_GROUP_NAME" )
WorkingDirectory=$INSTALL_DIR
EnvironmentFile=$CONFIG_FILE_PATH
ExecStart=$PYTHON_EXEC $MAIN_SCRIPT_PATH
Restart=on-failure
RestartSec=10
TimeoutStopSec=30
StandardOutput=journal
StandardError=journal

[Install]
WantedBy=multi-user.target
EOF
)
        echoinfo "Writing service file content to $SERVICE_FILE (using sudo)..."
        if ! echo "$SERVICE_CONTENT" | sudo tee "$SERVICE_FILE" > /dev/null; then
            echoerror "Failed to create systemd service file."
            sudo rm -f "$SERVICE_FILE"
        else
            echoinfo "Systemd service file created: $SERVICE_FILE"
            sudo chmod 644 "$SERVICE_FILE"

            sudo systemctl daemon-reload
            echoinfo "Systemd daemon reloaded."

            if sudo systemctl enable "$SERVICE_NAME.service"; then
                echoinfo "Service '$SERVICE_NAME' enabled successfully."
            else
                echoerror "Failed to enable service '$SERVICE_NAME'."
            fi

            # Diagnostic: Show permissions before starting
            if [ -d "$STATIC_DIR_PATH" ]; then
                echoinfo "${YELLOW}Diagnostic: Listing contents and permissions of '$STATIC_DIR_PATH' before service start:${NC}"
                ls -la "$STATIC_DIR_PATH/" || echowarn "Could not list static directory."
            fi

            if ! sudo systemctl start "$SERVICE_NAME.service"; then
                echoerror "Failed to start service '$SERVICE_NAME'. Check logs."
            else
                sleep 2
                if sudo systemctl is-active --quiet "$SERVICE_NAME.service"; then
                    echoinfo "Service '$SERVICE_NAME' started successfully and is currently active."
                    SERVICE_SETUP_SUCCESSFUL="yes"
                else
                    echoerror "Service '$SERVICE_NAME' started but became inactive shortly after. Check logs."
                fi
            fi
        fi
    fi
else
    echoinfo "Skipping systemd service setup because 'systemctl' or 'sudo' is not available."
fi

# -------------------------------------------------------------------
# Write installation summary
# -------------------------------------------------------------------
if [ -d "$INSTALL_DIR" ]; then
    {
        BORDER_CHAR="="
        TOP_BORDER=$(printf "%${BOX_WIDTH}s" | tr ' ' "$BORDER_CHAR")

        printf "\n\n${GREEN}${BOLD}%s\n" "$TOP_BORDER"
        center_text "MeshDash Installation Complete!"
        center_text "(Installed Version: ${MESHDASH_VERSION})"
        printf "%s${NC}\n" "$TOP_BORDER"

        printf "\n${BLUE}[INFO]${NC} ${BOLD}Installation Details:${NC}\n"
        printf "  Installation Location:    ${BOLD}%s${NC}\n" "$INSTALL_DIR"
        printf "  Installation Owner:       ${BOLD}%s${NC} (User running app/service)\n" "$ORIGINAL_USER"
        printf "  Virtual Environment:      ${BOLD}%s${NC}\n" "$VENV_PATH"
        printf "    (Python: ${BOLD}%s${NC} - Version: ${BOLD}%s${NC})\n" "$PYTHON_CMD" "$PYTHON_VERSION_DETECTED"
        printf "  Main App Script:          ${BOLD}%s${NC}\n" "$MAIN_SCRIPT_PATH"
        printf "  Config File:              ${BOLD}%s${NC} (downloaded from URL)\n" "$CONFIG_FILE_PATH"
        printf "  Manual Run Script:        ${BOLD}%s${NC}\n" "$RUN_SCRIPT_PATH"
        if [ -f "$TOOLS_SCRIPT_PATH" ]; then printf "  Management Tools:         ${BOLD}%s${NC}\n" "$TOOLS_SCRIPT_PATH"; else printf "  Management Tools:         ${YELLOW}Not Found${NC}\n"; fi

        printf "\n${BLUE}[INFO]${NC} ${BOLD}Running the Dashboard:${NC}\n"
        if [ "$SERVICE_SETUP_SUCCESSFUL" = "yes" ] && [ "$SERVICE_SETUP_SUCCESSFUL" = "yes" ]; then
            printf "  The service is running and enabled. Access via http://<your-ip>:<port> (as defined in config).\n"
            printf "  Manage with: ${CYAN}sudo systemctl status/start/stop/restart %s${NC}\n" "$SERVICE_NAME"
        else
            printf "  To start manually:\n"
            printf "    ${CYAN}cd \"%s\"${NC}\n" "$INSTALL_DIR"
            printf "    ${CYAN}./%s${NC}\n" "$RUN_SCRIPT_NAME"
        fi

        printf "\n${BLUE}[INFO]${NC} ${BOLD}Managing Installation:${NC}\n"
        if [ -f "$TOOLS_SCRIPT_PATH" ]; then
            printf "  Use Management Tools: ${CYAN}cd \"%s\" && sudo ./%s help${NC}\n" "$INSTALL_DIR" "$TOOLS_SCRIPT"
        fi
        printf "\n"

    } | tee "$SUMMARY_FILE_PATH" || echowarn "Warning: Failed to write summary to '$SUMMARY_FILE_PATH'."
    echoinfo "Installation summary saved to: ${BOLD}$SUMMARY_FILE_PATH${NC}"
else
    echoerror "Installation directory '$INSTALL_DIR' missing. Cannot write summary."
fi

# -------------------------------------------------------------------
# Cleanup
# -------------------------------------------------------------------
echostep "Cleaning Up Downloaded Archive"
if [ -f "$ZIP_FILE_PATH" ]; then
    echoinfo "Removing downloaded archive: '$ZIP_FILE_PATH'..."
    rm -f "$ZIP_FILE_PATH" && echoinfo "Archive removed." || echowarn "Could not remove archive."
else
    echoinfo "Downloaded archive not found (already removed)."
fi

echostep "Performing Self-Cleanup of Installer Script"
if [ -n "$INSTALLER_SCRIPT_PATH" ] && [ -f "$INSTALLER_SCRIPT_PATH" ]; then
    script_basename=$(basename "$INSTALLER_SCRIPT_PATH")
    expected_basename=$(basename "$0" 2>/dev/null || echo "install.sh")
    if [[ "$script_basename" == "install.sh" || "$script_basename" == "$expected_basename" || "$script_basename" == "bash" ]]; then
        echoinfo "Attempting to remove this installer script: '$INSTALLER_SCRIPT_PATH'..."
        set +o errexit
        rm -f "$INSTALLER_SCRIPT_PATH"
        rm_rc=$?
        set -o errexit
        if [ $rm_rc -eq 0 ]; then echoinfo "Installer script removed."; else echoinfo "Could not remove installer (Code: $rm_rc). Manual removal may be needed."; fi
    else
        echowarn "Installer script name '$script_basename' doesn't match expected. Skipping self-removal."
    fi
else
    echoinfo "Self-removal skipped (path unknown or file not found)."
fi

FINAL_BORDER=$(printf "%${BOX_WIDTH}s" | tr ' ' '=')
printf "\n${GREEN}${BOLD}%s\n" "$FINAL_BORDER"
center_text "INSTALLATION FINISHED"
center_text "(MeshDash Version: ${MESHDASH_VERSION})"
printf "%s${NC}\n\n" "$FINAL_BORDER"

exit 0