#!/bin/bash
# ============================================================
# i-KVM 模块管理脚本 (ikvm_module)
# 支持: easytier-core | gostc | ttyd
# 用法: ./ikvm_module.sh                       # 交互菜单
#       ./ikvm_module.sh all                   # 一键安装全部
#       ./ikvm_module.sh ttyd                  # 单独安装
#       ./ikvm_module.sh ttyd gostc            # 安装多个
#       ./ikvm_module.sh uninstall             # 交互卸载菜单
#       ./ikvm_module.sh uninstall all         # 一键卸载全部
#       ./ikvm_module.sh uninstall ttyd        # 单独卸载
# ============================================================

set -euo pipefail

# ============================================================
# 颜色 & 常量
# ============================================================
readonly RED='\033[0;31m'
readonly GREEN='\033[0;32m'
readonly YELLOW='\033[1;33m'
readonly BLUE='\033[0;34m'
readonly CYAN='\033[0;36m'
readonly NC='\033[0m'

readonly BASE_URL="http://s.6p7p.com/my/i-kvm"

# ============================================================
# 组件注册表 —— 新增组件只需在此数组中加一行
# 格式: "名称|目标路径|子目录|aarch64文件|armhf文件|amd64文件"
# ============================================================
COMPONENTS=(
    "easytier-core|/usr/bin/easytier-core|et|easytier-core.arm64|easytier-core.armhf|easytier-core.amd64"
    "gostc|/usr/bin/gostc|gs|go.arm64|go.armhf|go.amd64"
    "ttyd|/usr/bin/ttyd|ttyd|ttyd.aarch64|ttyd.armhf|ttyd.i686"
)

# ============================================================
# 全局状态
# ============================================================
SUDO=""
DOWNLOADER=""

# ============================================================
# 工具函数
# ============================================================

say()  { echo -e "$1$2${NC}"; }
ok()   { say "${GREEN}"  "[✓] $1"; }
err()  { say "${RED}"    "[✗] $1"; }
info() { say "${BLUE}"   "[i] $1"; }
warn() { say "${YELLOW}" "[!] $1"; }

banner() {
    echo -e "${CYAN}"
    echo "============================================"
    echo "       i-KVM 模块管理工具 (ikvm_module)"
    echo "============================================"
    echo -e "${NC}"
}

separator() {
    echo -e "${CYAN}━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━${NC}"
}

# 检测 CPU 架构 → 归一化为 aarch64 | armhf | amd64
detect_arch() {
    local arch
    arch=$(uname -m)
    case "$arch" in
        aarch64)              echo "aarch64" ;;
        armv7l|armv6l|arm*)   echo "armhf"   ;;
        *)                    echo "amd64"   ;;
    esac
}

# 检查 root / sudo
check_root() {
    if [ "$(id -u)" -ne 0 ]; then
        if command -v sudo &>/dev/null; then
            SUDO="sudo"
        else
            err "需要 root 权限，且系统中未找到 sudo。请以 root 用户运行。"
            exit 1
        fi
    fi
}

# 检查下载工具（curl 优先）
check_downloader() {
    if command -v curl &>/dev/null; then
        DOWNLOADER="curl"
    elif command -v wget &>/dev/null; then
        DOWNLOADER="wget"
    else
        err "系统中未找到 curl 或 wget，请先安装其中一个。"
        exit 1
    fi
}

# 统一下载方法
download() {
    local url="$1" target="$2"
    case "$DOWNLOADER" in
        curl) $SUDO curl -fsSL -o "$target" "$url" ;;
        wget) $SUDO wget  -q  -O "$target" "$url" ;;
    esac
}

# 重启 i-kvm 服务
restart_service() {
    if command -v systemctl &>/dev/null; then
        info "正在重启 i-kvm 服务 …"
        if $SUDO systemctl restart i-kvm 2>/dev/null; then
            ok "i-kvm 服务已重启"
        else
            warn "i-kvm 服务重启失败（服务可能未安装或未运行）"
        fi
    fi
}

# ============================================================
# 组件查找
# ============================================================

# 按名称查找组件配置，返回完整配置行
find_component() {
    local search="$1"
    for comp in "${COMPONENTS[@]}"; do
        local name
        name="${comp%%|*}"
        if [ "$name" = "$search" ]; then
            echo "$comp"
            return 0
        fi
    done
    return 1
}

# 列出所有可用组件名
list_names() {
    for comp in "${COMPONENTS[@]}"; do
        echo "  - ${comp%%|*}"
    done
}

# ============================================================
# 安装单个组件
# ============================================================
install_one() {
    local name="$1" target="$2" subdir="$3"
    local fa="$4" fh="$5" famd="$6"
    local arch filename url

    separator
    info "正在安装: ${name}"

    arch=$(detect_arch)

    case "$arch" in
        aarch64) filename="$fa"   ;;
        armhf)   filename="$fh"   ;;
        amd64)   filename="$famd" ;;
    esac

    url="${BASE_URL}/${subdir}/${filename}"
    info "架构: ${arch}"
    info "下载: ${url}"

    download "$url" "$target"

    if [ ! -f "$target" ]; then
        err "${name} 下载失败"
        return 1
    fi

    $SUDO chmod +x "$target"
    ok "${name} 安装完成 → ${target}"
}

# ============================================================
# 安装流程
# ============================================================

# 一键安装全部
install_all() {
    info "开始一键安装全部组件 …"
    local total=${#COMPONENTS[@]} ok_count=0 fail_count=0

    for comp in "${COMPONENTS[@]}"; do
        local name target subdir fa fh famd
        IFS='|' read -r name target subdir fa fh famd <<< "$comp"
        if install_one "$name" "$target" "$subdir" "$fa" "$fh" "$famd"; then
            (( ++ok_count ))
        else
            (( ++fail_count ))
        fi
    done

    echo ""
    separator
    info "安装结果: 成功 ${ok_count}/${total}, 失败 ${fail_count}/${total}"
    separator
    restart_service
}

# 安装指定名称的组件（对外接口）
install_by_name() {
    local comp
    comp=$(find_component "$1") || {
        err "未知组件: $1"
        echo "可用组件:"
        list_names
        return 1
    }
    local name target subdir fa fh famd
    IFS='|' read -r name target subdir fa fh famd <<< "$comp"
    install_one "$name" "$target" "$subdir" "$fa" "$fh" "$famd"
    restart_service
}

# ============================================================
# 卸载功能
# ============================================================

# 卸载单个组件（强制删除目标文件）
uninstall_one() {
    local name="$1" target="$2"

    separator
    info "正在卸载: ${name}"

    if [ ! -f "$target" ]; then
        warn "${name} 未安装（${target} 不存在），跳过。"
        return 0
    fi

    $SUDO rm -f "$target"

    if [ -f "$target" ]; then
        err "${name} 卸载失败，文件仍存在: ${target}"
        return 1
    fi

    ok "${name} 已卸载（已删除 ${target}）"
}

# 一键卸载全部
uninstall_all() {
    info "开始一键卸载全部组件 …"
    local total=${#COMPONENTS[@]} ok_count=0 fail_count=0

    for comp in "${COMPONENTS[@]}"; do
        local name target
        IFS='|' read -r name target _ <<< "$comp"
        if uninstall_one "$name" "$target"; then
            (( ++ok_count ))
        else
            (( ++fail_count ))
        fi
    done

    echo ""
    separator
    info "卸载结果: 成功 ${ok_count}/${total}, 失败 ${fail_count}/${total}"
    separator
    restart_service
}

# 按名称卸载（对外接口）
uninstall_by_name() {
    local comp
    comp=$(find_component "$1") || {
        err "未知组件: $1"
        echo "可用组件:"
        list_names
        return 1
    }
    local name target
    IFS='|' read -r name target _ <<< "$comp"
    uninstall_one "$name" "$target"
    restart_service
}

# 卸载子菜单
uninstall_menu() {
    while true; do
        echo ""
        echo -e "${CYAN}────────── 卸载管理 ──────────${NC}"
        echo ""
        local i=1
        for comp in "${COMPONENTS[@]}"; do
            local name target
            IFS='|' read -r name target _ <<< "$comp"
            local status
            if [ -f "$target" ]; then
                status="${GREEN}已安装${NC}"
            else
                status="${YELLOW}未安装${NC}"
            fi
            printf "  ${GREEN}%s)${NC} %-20s → %-30s %b\n" "$i" "$name" "$target" "$status"
            ((i++))
        done
        echo -e "  ${GREEN}a)${NC} 一键卸载全部组件"
        echo -e "  ${GREEN}q)${NC} 返回主菜单"
        echo ""

        read -r -p "请选择 [1-${#COMPONENTS[@]}/a/q]: " choice

        case "$choice" in
            q|Q)
                return 0
                ;;
            a|A)
                uninstall_all
                ;;
            *)
                if [[ "$choice" =~ ^[0-9]+$ ]] && \
                   [ "$choice" -ge 1 ] && \
                   [ "$choice" -le ${#COMPONENTS[@]} ]; then
                    local idx=$((choice - 1))
                    local comp="${COMPONENTS[$idx]}"
                    local name target
                    IFS='|' read -r name target _ <<< "$comp"
                    uninstall_one "$name" "$target"
                    restart_service
                else
                    err "无效选择: $choice"
                fi
                ;;
        esac

        echo ""
        read -r -p "按 Enter 继续 ..."
    done
}

# ============================================================
# 交互菜单
# ============================================================
interactive_menu() {
    while true; do
        banner

        echo "可用组件:"
        local i=1
        for comp in "${COMPONENTS[@]}"; do
            local name target
            IFS='|' read -r name target _ <<< "$comp"
            printf "  ${GREEN}%s)${NC} %-20s → %s\n" "$i" "$name" "$target"
            ((i++))
        done
        echo -e "  ${GREEN}a)${NC} 一键安装全部组件"
        echo -e "  ${GREEN}u)${NC} 进入卸载管理"
        echo -e "  ${GREEN}q)${NC} 退出"
        echo ""

        read -r -p "请选择 [1-${#COMPONENTS[@]}/a/u/q]: " choice

        case "$choice" in
            q|Q)
                echo "已退出。"
                exit 0
                ;;
            a|A)
                install_all
                ;;
            u|U)
                uninstall_menu
                ;;
            *)
                if [[ "$choice" =~ ^[0-9]+$ ]] && \
                   [ "$choice" -ge 1 ] && \
                   [ "$choice" -le ${#COMPONENTS[@]} ]; then
                    local idx=$((choice - 1))
                    local comp="${COMPONENTS[$idx]}"
                    local name target subdir fa fh famd
                    IFS='|' read -r name target subdir fa fh famd <<< "$comp"
                    install_one "$name" "$target" "$subdir" "$fa" "$fh" "$famd"
                    restart_service
                else
                    err "无效选择: $choice"
                fi
                ;;
        esac

        echo ""
        read -r -p "按 Enter 返回主菜单 ..."
    done
}

# ============================================================
# 帮助信息
# ============================================================
show_help() {
    echo "用法: $0 [选项|组件名...]"
    echo "      $0 uninstall [all|组件名...]"
    echo ""
    echo "安装命令:"
    echo "  无参数              进入交互式菜单"
    echo "  all                 一键安装全部组件"
    echo "  <组件名>            安装指定组件（支持多个，空格分隔）"
    echo ""
    echo "卸载命令:"
    echo "  uninstall           进入交互卸载菜单"
    echo "  uninstall all       一键卸载全部组件"
    echo "  uninstall <组件名>  卸载指定组件（支持多个，空格分隔）"
    echo ""
    echo "  -h, --help          显示此帮助"
    echo ""
    echo "可用组件:"
    list_names
    echo ""
    echo "示例:"
    echo "  $0                      # 交互菜单"
    echo "  $0 all                  # 安装全部"
    echo "  $0 ttyd                 # 仅安装 ttyd"
    echo "  $0 ttyd gostc           # 安装 ttyd 和 gostc"
    echo "  $0 uninstall all        # 卸载全部"
    echo "  $0 uninstall ttyd       # 仅卸载 ttyd"
}

# ============================================================
# 主入口
# ============================================================
main() {
    check_root
    check_downloader

    if [ $# -eq 0 ]; then
        interactive_menu
        exit 0
    fi

    # 卸载子命令处理
    if [ "$1" = "uninstall" ]; then
        shift
        if [ $# -eq 0 ]; then
            uninstall_menu
            exit 0
        fi
        local exit_code=0
        for arg in "$@"; do
            case "$arg" in
                all)
                    uninstall_all
                    exit 0
                    ;;
                *)
                    uninstall_by_name "$arg" || exit_code=1
                    ;;
            esac
        done
        exit $exit_code
    fi

    local exit_code=0

    for arg in "$@"; do
        case "$arg" in
            -h|--help)
                show_help
                exit 0
                ;;
            all)
                install_all
                exit 0
                ;;
            *)
                install_by_name "$arg" || exit_code=1
                ;;
        esac
    done

    exit $exit_code
}

main "$@"
