#!/usr/bin/env bash
set -Eeuo pipefail

# -------------------------------------------------------------
# MacroBase: Actualizar proyecto a origin/main (solo opción 1)
# - Realiza backup de logo antes de actualizar
# - Hace fetch/reset a origin/main
# - Limpia cache y archivos temporales
# - Restaura logo si existe el backup canónico
# - Escribe salida a consola y a un log de despliegue
#
# Ubicación: raíz del proyecto (este script)
# Ejecución: bash git_update_main.sh [-y] [-w <worktree>]
# Requiere: permisos suficientes (puede usar sudo internamente)
# -------------------------------------------------------------

usage() {
  cat << EOF
Uso: $(basename "$0") [-y] [-w <worktree>] [-s]

Opciones:
  -y                  Modo no interactivo (asume confirmaciones)
  -w <worktree>       Directorio del proyecto a actualizar (por defecto: repo raíz)
  -s                  Forzar uso de sudo en comandos (por defecto no)
EOF
}

NON_INTERACTIVE="0"
WORKTREE=""
USE_SUDO="0"
while getopts ":yw:sh" opt; do
  case $opt in
    y) NON_INTERACTIVE="1" ;;
    w) WORKTREE="$OPTARG" ;;
    s) USE_SUDO="1" ;;
    h) usage; exit 0 ;;
    *) usage; exit 1 ;;
  esac
done

# Evitar ruido en entornos sin TTY
clear >/dev/null 2>&1 || true
echo -e "\n\n"
echo "#############################################################"
echo "#                  ACTUALIZANDO SISTEMAS                    #"
echo "#############################################################"
echo -e "\n"

# Carpetas relevantes respecto a este script
SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
ROOT_DEFAULT="${SCRIPT_DIR}"
ROOT_DIR="${WORKTREE:-$ROOT_DEFAULT}"     # Directorio del proyecto a actualizar
WEB_DIR="${ROOT_DIR}/web"
APP_DIR="${ROOT_DIR}/app"
LOG_BACK_DIR="/var/www/html/back"
DEPLOY_LOG_DIR="${SCRIPT_DIR}/logs"
mkdir -p "${DEPLOY_LOG_DIR}"
DEPLOY_LOG_FILE="${DEPLOY_LOG_DIR}/update_$(date +%Y%m%d_%H%M%S).log"

{
  # Helper sudo opcional
  if [[ "$USE_SUDO" == "1" ]]; then SUDO="sudo"; else SUDO=""; fi

  # Alias Git con safe.directory para evitar "dubious ownership"
  GIT_CMD=(git -c safe.directory="$ROOT_DIR")
  if [[ -n "$SUDO" ]]; then GIT_CMD=(sudo git -c safe.directory="$ROOT_DIR"); fi

  echo "Seleccione una opción:"
  echo "============================================================="
  echo "  1) Actualizar solo rama 'main' (Producción/REALS)"
  echo "============================================================="
  if [[ "${NON_INTERACTIVE}" == "1" ]]; then
    OPCION=1
  else
    read -rp "Ingrese su opción [1]: " OPCION || true
    OPCION=${OPCION:-1}
  fi

  echo -e "\n\n"
  echo "#############################################################"
  echo "#              INICIANDO PROCESO DE ACTUALIZACIÓN           #"
  echo "#############################################################"
  echo -e "\n"

  # Identificador (no tokens)
  echo -e "\n>>> Identificador <<<"
  echo "macrobase-update"
  echo "============================================================="

  backup_logo() {
      local SRC="${WEB_DIR}/logo.jpg"
      local DEST_DIR="${LOG_BACK_DIR}"
      local TS
      TS="$(date +%Y%m%d_%H%M%S)"
      local DEST_TS="${DEST_DIR}/logo_${TS}.jpg"
      local DEST_CANON="${DEST_DIR}/logo.jpg"

      echo -e "\n📦 Haciendo backup del logo antes de actualizar..."
      local BKP_DIR="${DEST_DIR}"
      ${SUDO} mkdir -p "${BKP_DIR}" >/dev/null 2>&1 || true
      if [[ ! -w "${BKP_DIR}" ]]; then
          BKP_DIR="${WEB_DIR}/backups"
          ${SUDO} mkdir -p "${BKP_DIR}" >/dev/null 2>&1 || true
          echo "ℹ️  Usando carpeta de respaldo local: ${BKP_DIR}"
      fi

      if [[ -f "${SRC}" ]]; then
          if [[ -n "$SUDO" ]]; then
              ${SUDO} cp -p "${SRC}" "${BKP_DIR}/logo_${TS}.jpg" || true
              ${SUDO} cp -p "${SRC}" "${BKP_DIR}/logo.jpg" || true
          else
              cp "${SRC}" "${BKP_DIR}/logo_${TS}.jpg" || true
              cp "${SRC}" "${BKP_DIR}/logo.jpg" || true
          fi
          echo "✅ Backup creado en: ${BKP_DIR}/logo_${TS}.jpg"
      else
          echo "⚠️ No se encontró ${SRC}. Se continúa sin backup."
      fi
  }

  # Confirmación si hay cambios locales
  echo -e "\n🔎 Verificando cambios locales (por si acaso)..."
  if [[ ! -d "${ROOT_DIR}/.git" ]]; then
      echo "❌ El directorio de trabajo no parece un repositorio Git: ${ROOT_DIR}" >&2
      exit 1
  fi
  pushd "${ROOT_DIR}" >/dev/null
  if [[ -n "$("${GIT_CMD[@]}" status --porcelain || true)" ]]; then
      echo "⚠️ Se detectaron cambios locales sin commitear."
      if [[ "${NON_INTERACTIVE}" == "1" ]]; then
          echo "↪ Ejecutando reset --hard automáticamente (modo -y)."
      else
          read -rp "¿Continuar y DESCARTAR los cambios con reset --hard? [y/N]: " CONFIRM || true
          CONFIRM=${CONFIRM:-N}
          if [[ "${CONFIRM}" != "y" && "${CONFIRM}" != "Y" ]]; then
              echo "❌ Operación cancelada por el usuario."
              exit 1
          fi
      fi
  fi

  # Backup de logo
  backup_logo

  if [[ "${OPCION}" == "1" ]]; then
      echo "🛠️  Actualizando solo rama 'main'..."
      echo -e "\n⏱ Guardando HEAD actual por si se requiere rollback..."
      CURRENT_HEAD="$("${GIT_CMD[@]}" rev-parse HEAD || true)"
      echo "HEAD actual: ${CURRENT_HEAD}" > "${DEPLOY_LOG_FILE}.head"

      # Respaldar cambios locales (tracked modificados y untracked), ignorando carpeta web/
      TS_CLEAN="$(date +%Y%m%d_%H%M%S)"
      BACK_ROOT="${LOG_BACK_DIR}"
      ${SUDO} mkdir -p "$BACK_ROOT" >/dev/null 2>&1 || true
      if [[ ! -w "$BACK_ROOT" ]]; then BACK_ROOT="${WEB_DIR}/backups"; ${SUDO} mkdir -p "$BACK_ROOT" >/dev/null 2>&1 || true; fi
      DEST_CHG="$BACK_ROOT/changes_${TS_CLEAN}"
      ${SUDO} mkdir -p "$DEST_CHG" >/dev/null 2>&1 || true

      CHANGED_LIST=$("${GIT_CMD[@]}" status --porcelain | awk '{print $2}' || true)
      UNTRACKED_LIST=$("${GIT_CMD[@]}" ls-files --others --exclude-standard || true)
      BACKED_UP=0
      if [[ -n "$CHANGED_LIST$UNTRACKED_LIST" ]]; then
          echo "🧾 Respaldando cambios locales (ignorando 'web/')..."
          {
            echo "$CHANGED_LIST"
            echo "$UNTRACKED_LIST"
          } | while read -r f; do
              [[ -z "$f" ]] && continue
              # Ignorar entradas dentro de web/
              if [[ "$f" == web/* ]]; then continue; fi
              # Solo archivos regulares
              if [[ -f "$f" ]]; then
                  dname="$(dirname "$f")"
                  ${SUDO} mkdir -p "$DEST_CHG/$dname" >/dev/null 2>&1 || true
                  ${SUDO} cp -a "$f" "$DEST_CHG/$f" >/dev/null 2>&1 || true
                  echo "   • $f"
                  BACKED_UP=1
              fi
          done
      fi
      if [[ "$BACKED_UP" -eq 1 ]]; then
          echo "✅ Cambios respaldados en: $DEST_CHG"
      else
          echo "ℹ️  No se encontraron cambios locales a respaldar (fuera de 'web/')."
      fi
      echo "🧽 Limpiando no rastreados (git clean -fd)..."
      "${GIT_CMD[@]}" clean -fd || true

      "${GIT_CMD[@]}" fetch --all --prune
      "${GIT_CMD[@]}" checkout -f main
      "${GIT_CMD[@]}" reset --hard origin/main
      # Si require pull ff-only (por si HEAD no apunta a origin/main ya):
      "${GIT_CMD[@]}" pull --ff-only || true

  else
      echo "❌ Opción inválida. Saliendo del script."
      exit 1
  fi

  # Limpieza de cache/temporales
  echo -e "\n🧹 Limpiando caché y archivos temporales..."
  if [[ -d "${APP_DIR}/cache" ]]; then
      ${SUDO} rm -rf "${APP_DIR}/cache"/* || true
      ${SUDO} chmod -R 777 "${APP_DIR}/cache" || true
  fi
  if [[ -d "${APP_DIR}/logs" ]]; then
      ${SUDO} chmod -R 777 "${APP_DIR}/logs" || true
  fi
  if [[ -d "${WEB_DIR}" ]]; then
      ${SUDO} chmod -R 777 "${WEB_DIR}" || true
      ${SUDO} rm -f "${WEB_DIR}"/*.pdf "${WEB_DIR}"/*.xls "${WEB_DIR}"/*.xlsx || true
  fi

  echo -e "\n🔁 Restaurando logo en la web..."
  if [[ -f "${LOG_BACK_DIR}/logo.jpg" ]]; then
      ${SUDO} cp -p "${LOG_BACK_DIR}/logo.jpg" "${WEB_DIR}/" || true
      echo "✅ Logo restaurado."
  else
      echo "⚠️ No se encontró ${LOG_BACK_DIR}/logo.jpg para restaurar."
  fi

  # Mostrar commit final
  FINAL_SHA="$("${GIT_CMD[@]}" rev-parse HEAD || true)"
  echo -e "\n📌 Commit aplicado: ${FINAL_SHA}"
  echo "Mensaje: $("${GIT_CMD[@]}" log -1 --pretty=%s || true)"
  echo "Autor:   $("${GIT_CMD[@]}" log -1 --pretty=%an || true)"
  echo "Fecha:   $("${GIT_CMD[@]}" log -1 --pretty=%ad || true)"
  popd >/dev/null

  echo -e "\n\n#############################################################"
  echo "#                         ✅ ¡FIN!                           #"
  echo "#############################################################"
  sleep 1
  echo "📢 La rama actual es 'main'. Por favor, avisar en el grupo."

} | tee -a "${DEPLOY_LOG_FILE}"

exit 0
