#!/usr/bin/env bash
# =============================================================================
# Script: term_tools_install.sh
# Description: 终端核心工具链自动化部署向导 (带 APT 自动自愈)
# Version: 2.2.0
# Compatibility: Bash 5.0+ (Debian 12/13, Ubuntu 22.04/24.04 兼容)
# =============================================================================

set -euo pipefail
IFS=$'\n\t'

# ==================== 全局常量 ====================
readonly SCRIPT_VERSION="2.2.0"
readonly LOG_FILE="/tmp/term_tools_install_$(date +%Y%m%d_%H%M%S).log"

readonly C_RESET='\033[0m'
readonly C_RED='\033[1;31m'
readonly C_GREEN='\033[1;32m'
readonly C_YELLOW='\033[1;33m'
readonly C_BLUE='\033[1;34m'
readonly C_CYAN='\033[1;36m'
readonly C_BOLD='\033[1m'

# ==================== 日志命名空间 ====================
log::info()    { echo -e "${C_BLUE}[INFO]${C_RESET} $1" | tee -a "${LOG_FILE}"; }
log::success() { echo -e "${C_GREEN}[ OK ]${C_RESET} $1" | tee -a "${LOG_FILE}"; }
log::warn()    { echo -e "${C_YELLOW}[WARN]${C_RESET} $1" | tee -a "${LOG_FILE}"; }
log::error()   { echo -e "${C_RED}[FAIL]${C_RESET} $1" >&2 | tee -a "${LOG_FILE}"; }
log::step()    { echo -e "\n${C_CYAN}${C_BOLD}>>> $1${C_RESET}" | tee -a "${LOG_FILE}"; }

# ==================== 工具命名空间 ====================

# -------------------------------------------------------------------------
# 函数名: utils::run_logged
# 描述: 带日志且失败可见的通用执行器 (已修复竖向排版问题)
# -------------------------------------------------------------------------
utils::run_logged() {
  local cmd_str
  cmd_str=$(echo "$@") # 消除 IFS 换行符影响
  
  log::info "执行: ${cmd_str}"
  if "$@" >> "${LOG_FILE}" 2>&1; then
    log::success "完成: ${cmd_str}"
  else
    local ret=$?
    log::error "命令失败 (退出码 ${ret}): ${cmd_str}"
    echo ">>> 最后 20 行日志:" >&2
    tail -n 20 "${LOG_FILE}" >&2
    exit "${ret}"
  fi
}

# -------------------------------------------------------------------------
# 函数名: utils::apt_run_with_heal
# 描述: 专用于 apt 的执行器，内置 dpkg/apt 异常自动修复机制
# -------------------------------------------------------------------------
utils::apt_run_with_heal() {
  local cmd_str
  cmd_str=$(echo "$@")
  
  log::info "执行: ${cmd_str}"
  if "$@" >> "${LOG_FILE}" 2>&1; then
    log::success "完成: ${cmd_str}"
  else
    log::warn "APT 命令执行失败！系统包管理器可能处于异常状态。"
    log::warn "正在启动 [自动自愈] 流程..."
    
    # 提取是否需要 sudo
    local run_sudo=""
    [[ "$1" == "sudo" ]] && run_sudo="sudo"

    # 自愈预案 1: 修复被中断的配置 (解决 dpkg was interrupted 错误)
    log::info "[自愈] 尝试修复 dpkg 锁死状态..."
    ${run_sudo} dpkg --configure -a >> "${LOG_FILE}" 2>&1 || true
    
    # 自愈预案 2: 修复破损的依赖树
    log::info "[自愈] 尝试修复损坏的依赖树..."
    ${run_sudo} apt-get install --fix-broken -y -qq >> "${LOG_FILE}" 2>&1 || true

    log::info "[自愈] 环境急救指令下发完毕，正在进行最终重试..."
    if "$@" >> "${LOG_FILE}" 2>&1; then
      log::success "🎉 触发自愈成功！重试完成: ${cmd_str}"
    else
      local ret=$?
      log::error "❌ 自动修复后重试仍失败 (退出码 ${ret}): ${cmd_str}"
      echo ">>> 最后 20 行日志:" >&2
      tail -n 20 "${LOG_FILE}" >&2
      exit "${ret}"
    fi
  fi
}

# -------------------------------------------------------------------------
# 函数名: utils::is_installed
# 描述: 多路径检测可执行文件是否存在
# -------------------------------------------------------------------------
utils::is_installed() {
  local target="$1"
  command -v "${target}" >/dev/null 2>&1 || [[ -x "${HOME}/.local/bin/${target}" ]] || [[ -x "${HOME}/.atuin/bin/${target}" ]]
}

# ==================== 核心注入逻辑 ====================
config::inject_shell() {
  local target_shell="$1"

  if [[ "${target_shell}" != "zsh" ]]; then
    log::warn "Current default shell is ${target_shell}; this script only maintains zsh configuration."
    log::warn "Run ./00_Zsh_Install_Config.sh and re-login before running this script."
    return 0
  fi

  log::success "zsh environment confirmed; initialization is managed by 00_Zsh_Install_Config.sh"
}

# ==================== 主程序入口 ====================
main() {
  touch "${LOG_FILE}"
  trap 'log::error "脚本在第 ${LINENO} 行失败！请查看日志: ${LOG_FILE}"; echo ">>> 最后 30 行日志:" >&2; tail -n 30 "${LOG_FILE}" >&2' ERR
  trap 'rm -f /tmp/*.deb /tmp/*.tar.gz 2>/dev/null || true' EXIT

  mkdir -p "${HOME}/.local/bin"
  export PATH="${HOME}/.local/bin:${HOME}/.fzf/bin:${HOME}/.atuin/bin:${PATH}"

  local sudo_cmd=""
  if [[ "$(id -u)" -ne 0 ]]; then
    command -v sudo >/dev/null 2>&1 || { log::error "非 root 且无 sudo！请切换至 root 后重试。"; exit 1; }
    sudo_cmd="sudo"
  fi

  clear
  echo -e "${C_CYAN}${C_BOLD}=== 终端核心工具链自动化部署向导 v${SCRIPT_VERSION} ===${C_RESET}"
  echo -e "运行日志: ${C_BOLD}${LOG_FILE}${C_RESET}\n"

  log::info "正在侦测系统环境..."

  if ! grep -qE '^(ID|ID_LIKE)="?(debian|ubuntu)' /etc/os-release 2>/dev/null; then
    log::error "仅支持 Debian / Ubuntu 体系！"
    exit 1
  fi

  local os_pretty
  local arch_deb
  local arch_uname
  local arch_gnu
  
  os_pretty=$(grep -E '^PRETTY_NAME=' /etc/os-release | cut -d= -f2 | tr -d '"')
  arch_deb=$(dpkg --print-architecture)
  arch_uname=$(uname -m)

  if [[ "${arch_uname}" == "x86_64" ]]; then
    arch_gnu="x86_64-unknown-linux-gnu"
  elif [[ "${arch_uname}" == "aarch64" ]] || [[ "${arch_uname}" == "arm64" ]]; then
    arch_gnu="aarch64-unknown-linux-gnu"
  else
    log::error "不支持的架构: ${arch_uname}"
    exit 1
  fi

  local user_shell
  local current_shell_name
  user_shell=$(getent passwd "${USER}" | cut -d: -f7)
  current_shell_name=$(basename "${user_shell:-$SHELL}")

  echo -e "----------------------------------------"
  echo -e "  OS   : ${C_GREEN}${os_pretty}${C_RESET}"
  echo -e "  ARCH : ${C_GREEN}${arch_uname} (${arch_deb})${C_RESET}"
  echo -e "  SHELL: ${C_GREEN}${current_shell_name}${C_RESET}"
  echo -e "  USER : ${C_GREEN}$(whoami) $([[ -z "${sudo_cmd}" ]] && echo '(Root免提权)' || echo '(需Sudo提权)')${C_RESET}"
  echo -e "----------------------------------------"

  local confirm_sys
  read -r -p "是否继续执行部署？ [Y/n] " confirm_sys
  if [[ "${confirm_sys}" =~ ^[Nn]$ ]]; then
    log::warn "用户取消部署。"
    exit 0
  fi

  log::step "选择需要安装的组件模块"
  echo "请根据需要输入对应序号，多个序号用空格分隔 (例如: 1 3 5)"
  echo "若需安装推荐精简组件，请直接按 [Enter] 回车。"
  echo ""
  echo -e "  ${C_BOLD}[1] 现代核心命令${C_RESET} (eza, bat, fd, ripgrep) [推荐]"
  echo -e "  ${C_BOLD}[2] 资源可视化监控${C_RESET} (duf, dust, bottom) [可选]"
  echo -e "  ${C_BOLD}[3] 终端导航利器${C_RESET} (fzf, zoxide) [推荐]"
  echo -e "  ${C_BOLD}[4] 历史记录同步${C_RESET} (atuin) [可选]"
  echo -e "  ${C_BOLD}[5] 终端提示美化${C_RESET} (starship) [推荐]"
  echo ""
  
  local menu_choices
  read -r -p "请输入您的选择 [默认: 1 3 5]: " menu_choices
  menu_choices=${menu_choices:-"1 3 5"}

  local opt_core=0 opt_monitor=0 opt_nav=0 opt_hist=0 opt_prompt=0
  [[ " ${menu_choices} " =~ " 1 " ]] && opt_core=1
  [[ " ${menu_choices} " =~ " 2 " ]] && opt_monitor=1
  [[ " ${menu_choices} " =~ " 3 " ]] && opt_nav=1
  [[ " ${menu_choices} " =~ " 4 " ]] && opt_hist=1
  [[ " ${menu_choices} " =~ " 5 " ]] && opt_prompt=1

  log::info "由于静默安装，日志输出已重定向，请耐心等待..."

  log::step "准备基础运行环境"
  # 【注意这里换成了具备自愈能力的执行器】
  utils::apt_run_with_heal ${sudo_cmd} apt update -y -qq
  utils::apt_run_with_heal ${sudo_cmd} apt install -y -qq curl wget git unzip tar gpg ca-certificates python3

  # --- [1] 现代核心命令 ---
  if [[ "${opt_core}" -eq 1 ]]; then
    log::step "模块 1/5: 现代核心命令"

    if utils::is_installed eza; then log::success "eza 已安装，跳过"; else
      log::info "配置并安装 eza..."
      utils::run_logged ${sudo_cmd} mkdir -p /etc/apt/keyrings
      curl -fsSL https://raw.githubusercontent.com/eza-community/eza/main/deb.asc | ${sudo_cmd} gpg --dearmor --yes -o /etc/apt/keyrings/gierens.gpg 2>> "${LOG_FILE}" || true
      echo "deb [signed-by=/etc/apt/keyrings/gierens.gpg] http://deb.gierens.de stable main" | ${sudo_cmd} tee /etc/apt/sources.list.d/gierens.list >/dev/null
      utils::run_logged ${sudo_cmd} chmod 644 /etc/apt/keyrings/gierens.gpg /etc/apt/sources.list.d/gierens.list
      
      # 这里也应用了自愈机制
      utils::apt_run_with_heal ${sudo_cmd} apt update -y -qq
      utils::apt_run_with_heal ${sudo_cmd} apt install -y -qq eza
    fi

    if ! utils::is_installed bat; then
      log::info "安装最新版 bat..."
      local bat_url
      bat_url=$(curl -s https://api.github.com/repos/sharkdp/bat/releases/latest | grep -o "https://[^\"]*${arch_gnu}\.tar\.gz" | head -n1 || true)
      if [[ -z "${bat_url}" ]]; then log::error "获取 bat 下载链接失败 (可能触发 API 限流)"; exit 1; fi
      curl -fsSL "${bat_url}" -o /tmp/bat.tar.gz
      rm -rf /tmp/bat-*
      tar -xzf /tmp/bat.tar.gz -C /tmp
      mv /tmp/bat-*/bat "${HOME}/.local/bin/bat" && chmod +x "${HOME}/.local/bin/bat"
    else
      log::success "bat 已安装，跳过"
    fi

    if ! utils::is_installed fd; then
      log::info "安装最新版 fd..."
      local fd_url
      fd_url=$(curl -s https://api.github.com/repos/sharkdp/fd/releases/latest | grep -o "https://[^\"]*${arch_deb}\.deb" | head -n1 || true)
      if [[ -z "${fd_url}" ]]; then log::error "获取 fd 下载链接失败 (可能触发 API 限流)"; exit 1; fi
      curl -fsSL -o /tmp/fd.deb "${fd_url}"
      utils::apt_run_with_heal ${sudo_cmd} apt install -y -qq /tmp/fd.deb
    else
      log::success "fd 已安装，跳过"
    fi

    if ! utils::is_installed rg; then
      log::info "安装最新版 ripgrep..."
      local rg_deb
      rg_deb=$(curl -s https://api.github.com/repos/BurntSushi/ripgrep/releases/latest | grep -o "https://[^\"]*${arch_deb}\.deb" | head -n1 || true)
      if [[ -z "${rg_deb}" ]]; then log::error "获取 ripgrep 下载链接失败 (可能触发 API 限流)"; exit 1; fi
      curl -fsSL -o /tmp/rg.deb "${rg_deb}"
      utils::apt_run_with_heal ${sudo_cmd} apt install -y -qq /tmp/rg.deb
    else
      log::success "ripgrep 已安装，跳过"
    fi
  fi

  # --- [2] 资源可视化监控 ---
  if [[ "${opt_monitor}" -eq 1 ]]; then
    log::step "模块 2/5: 资源可视化监控"

    if ! utils::is_installed duf; then
      log::info "安装 duf (v0.9.1)..."
      local duf_url="https://github.com/muesli/duf/releases/download/v0.9.1/duf_0.9.1_linux_${arch_deb}.deb"
      curl -fsSL -o /tmp/duf.deb "${duf_url}"
      utils::apt_run_with_heal ${sudo_cmd} apt install -y -qq /tmp/duf.deb
    else
      log::success "duf 已安装，跳过"
    fi

    if ! utils::is_installed dust; then
      log::info "安装最新版 dust..."
      if [[ "${arch_deb}" == "amd64" ]]; then
        local dust_deb
        dust_deb=$(curl -s https://api.github.com/repos/bootandy/dust/releases/latest | grep -o "https://[^\"]*amd64\.deb" | head -n1 || true)
        if [[ -z "${dust_deb}" ]]; then log::error "获取 dust 下载链接失败"; exit 1; fi
        curl -fsSL -o /tmp/dust.deb "${dust_deb}"
        utils::apt_run_with_heal ${sudo_cmd} apt install -y -qq /tmp/dust.deb
      else
        local dust_tar
        dust_tar=$(curl -s https://api.github.com/repos/bootandy/dust/releases/latest | grep -o "https://[^\"]*${arch_gnu}\.tar\.gz" | head -n1 || true)
        if [[ -z "${dust_tar}" ]]; then log::error "获取 dust 下载链接失败"; exit 1; fi
        curl -fsSL "${dust_tar}" -o /tmp/dust.tar.gz
        rm -rf /tmp/dust-*
        tar -xzf /tmp/dust.tar.gz -C /tmp
        mv /tmp/dust-*/dust "${HOME}/.local/bin/dust" && chmod +x "${HOME}/.local/bin/dust"
      fi
    else
      log::success "dust 已安装，跳过"
    fi

    if ! utils::is_installed btm; then
      log::info "安装最新版 bottom..."
      local btm_deb
      btm_deb=$(curl -s https://api.github.com/repos/ClementTsang/bottom/releases/latest | grep -o "https://[^\"]*${arch_deb}\.deb" | head -n1 || true)
      if [[ -z "${btm_deb}" ]]; then log::error "获取 bottom 下载链接失败"; exit 1; fi
      curl -fsSL -o /tmp/btm.deb "${btm_deb}"
      utils::apt_run_with_heal ${sudo_cmd} apt install -y -qq /tmp/btm.deb
    else
      log::success "bottom 已安装，跳过"
    fi
  fi

  # --- [3] 终端导航利器 ---
  if [[ "${opt_nav}" -eq 1 ]]; then
    log::step "模块 3/5: 终端导航利器"

    if [[ ! -x "${HOME}/.fzf/bin/fzf" ]]; then
      log::info "安装 fzf..."
      rm -rf "${HOME}/.fzf"
      utils::run_logged git clone --depth 1 https://github.com/junegunn/fzf.git "${HOME}/.fzf"
      utils::run_logged "${HOME}/.fzf/install" --all --no-update-rc
    else
      log::success "fzf 已安装，跳过"
    fi

    if ! utils::is_installed zoxide; then
      log::info "安装 zoxide..."
      curl -fsSL https://raw.githubusercontent.com/ajeetdsouza/zoxide/main/install.sh | bash >> "${LOG_FILE}" 2>&1
      log::success "完成: zoxide 安装"
    else
      log::success "zoxide 已安装，跳过"
    fi
  fi

  # --- [4] 历史记录同步 ---
  if [[ "${opt_hist}" -eq 1 ]]; then
    log::step "模块 4/5: 历史记录同步"
    if ! utils::is_installed atuin; then
      log::info "安装 atuin..."
      curl --proto '=https' --tlsv1.2 -fsSL https://setup.atuin.sh | bash -s -- --non-interactive >> "${LOG_FILE}" 2>&1
      log::success "完成: atuin 安装"
    else
      log::success "atuin 已安装，跳过"
    fi
  fi

  # --- [5] 终端美化提示 ---
  if [[ "${opt_prompt}" -eq 1 ]]; then
    log::step "模块 5/5: 终端美化提示"
    if ! utils::is_installed starship; then
      log::info "安装最新版 starship（官方推荐 sh 方式）..."
      if curl -fsSL https://starship.rs/install.sh | sh -s -- --yes -b "${HOME}/.local/bin" >> "${LOG_FILE}" 2>&1; then
        log::success "完成: starship 安装"
      else
        log::warn "starship 安装脚本产生警告（官方已知行为），继续验证..."
      fi

      if utils::is_installed starship; then
        log::success "starship 安装已确认"
      else
        log::error "starship 安装失败，请查看日志"
        exit 1
      fi
    else
      log::success "starship 已安装，跳过"
    fi
  fi

  # --- [6] 触发配置注入 ---
  log::step "清理残留文件并写入 Shell 配置"
  rm -rf /tmp/dust-* /tmp/bat-* 2>/dev/null || true
  
  config::inject_shell "${current_shell_name}" "${opt_hist}" "${opt_nav}" "${opt_prompt}"
  echo ""
  echo -e "${C_GREEN}下一步请执行别名配置脚本：${C_RESET}"
  echo -e "${C_CYAN}   ./02_Modern_CLI_Aliases_Setup.sh${C_RESET}"
  echo ""
}

# 启动执行
main "$@"
