<!--
=============================================================================
IT智能服务台 — 管理员登录页 (v1.2, 2026-07-06)
=============================================================================
说明：智能检测企微登录状态，提供三种登录方式
  - PRD v1.5 §4.5: 企微免密登录/企微扫码登录/账号密码+OTP
  - 复用坐席端登录 API（POST /api/agents/login）
  - 企微免密登录：检测到企微登录账号且有管理员角色，免密直接进入
-->
<template>
  <div class="login-page">
    <!-- 背景装饰 -->
    <div class="login-bg">
      <div class="login-bg-gradient"></div>
    </div>

    <!-- 登录卡片 -->
    <div class="login-card">
      <!-- Logo -->
      <div class="login-logo">
        <div class="login-logo-icon">
          <el-icon :size="28"><Headset /></el-icon>
        </div>
        <h1 class="login-title">IT智能服务台</h1>
        <p class="login-subtitle">管理后台</p>
      </div>

      <!-- 企微免密登录（仅企微内管理员可见） -->
      <div v-if="wecomUserId" style="text-align: center; margin-bottom: 12px;">
        <el-button
          type="primary"
          size="large"
          :loading="wecomQuickLoading"
          @click="handleWecomQuickLogin"
          class="option-btn"
          style="width: 100%;"
        >
          <el-icon><Key /></el-icon>
          企微免密登录（{{ wecomUserId }}）
        </el-button>
      </div>

      <!-- 企微扫码登录面板（始终可见，与坐席端一致） -->
      <div class="qr-login">
        <div class="qr-container">
          <div v-if="qrLoading" class="qr-loading">
            <el-icon class="is-loading"><Loading /></el-icon>
            <p>加载中...</p>
          </div>
          <div v-else-if="qrCode" class="qr-code">
            <img :src="qrCode" alt="企微扫码登录" />
          </div>
          <div v-else class="qr-error">
            <p>获取二维码失败</p>
            <el-button size="small" @click="fetchQrCode">重试</el-button>
          </div>
        </div>
        <p class="qr-hint">请使用企业微信扫码登录</p>

        <!-- 分隔线 -->
        <div class="divider">
          <span>其他登录方式</span>
        </div>

        <el-button
          size="large"
          class="password-login-btn"
          @click="showPasswordPanel = true"
        >
          <span>🔐</span>
          账号密码登录
        </el-button>
      </div>

      <!-- 账号密码登录表单（与二维码同时展示，无需返回按钮） -->
      <div v-if="showPasswordPanel" class="password-login">
        <el-form
          ref="formRef"
          :model="loginForm"
          :rules="rules"
          label-position="top"
          @submit.prevent="handleLogin"
        >
        <el-form-item label="账号" prop="userId">
          <el-input
            v-model="loginForm.userId"
            placeholder="请输入账号（如 sxn）"
            size="large"
            :prefix-icon="User"
            @keydown.enter="handleLogin"
          />
        </el-form-item>

        <el-form-item label="密码" prop="password">
          <el-input
            v-model="loginForm.password"
            type="password"
            placeholder="请输入密码"
            size="large"
            :prefix-icon="Lock"
            show-password
            @keydown.enter="handleLogin"
          />
        </el-form-item>

        <!-- OTP 输入区: 仅在 requireOtp 时显示 -->
        <el-form-item v-if="requireOtp" label="OTP 验证码" prop="otpCode">
          <el-input
            v-model="loginForm.otpCode"
            placeholder="请输入 Google Authenticator 验证码"
            size="large"
            :prefix-icon="Key"
            maxlength="6"
            @keydown.enter="handleLogin"
          />
        </el-form-item>

        <el-form-item>
          <el-button
            type="primary"
            size="large"
            :loading="adminStore.logging"
            :disabled="adminStore.logging"
            @click="handleLogin"
            class="login-btn"
          >
            {{ adminStore.logging ? '登录中...' : (requireOtp ? '验证 OTP' : '登录管理后台') }}
          </el-button>
        </el-form-item>
        </el-form>
      </div>

      <!-- 错误提示 -->
      <el-alert
        v-if="errorMsg"
        :title="errorMsg"
        type="error"
        show-icon
        :closable="true"
        @close="errorMsg = ''"
        style="margin-top: 16px"
      />

      <!-- 提示信息 -->
      <div class="login-tips">
        <el-icon :size="14"><InfoFilled /></el-icon>
        <span>仅限组长（admin角色）登录管理后台</span>
      </div>
    </div>
  </div>
</template>

<script setup lang="ts">
// ==========================================================================
// 依赖导入
// ==========================================================================
import { ref, reactive, onMounted, onUnmounted } from 'vue'
import { useRouter } from 'vue-router'
import { ElMessage } from 'element-plus'
import { useAdminStore } from '@/stores/admin'
import type { FormInstance, FormRules } from 'element-plus'
import { Loading, User, Lock, Key, InfoFilled, Headset } from '@element-plus/icons-vue'

// ==========================================================================
// Store
// ==========================================================================
const router = useRouter()
const adminStore = useAdminStore()

// ==========================================================================
// 表单状态
// ==========================================================================

/** 表单引用 */
const formRef = ref<FormInstance>()

/** 登录表单数据 */
const loginForm = reactive({
  userId: '',
  password: '',
  otpCode: '',
})

/** 是否需要 OTP 验证 */
const requireOtp = ref(false)

/** 错误信息 */
const errorMsg = ref<string>('')

// ==========================================================================
// 企微智能检测相关状态（PRD v1.5 §4.5）
// ==========================================================================

/** 是否显示账号密码登录 */
const showPasswordPanel = ref(false)

/** 企微用户ID（用于免密登录） */
const wecomUserId = ref('')

/** 企微快捷登录loading */
const wecomQuickLoading = ref(false)

/** 企微二维码 */
const qrCode = ref('')

/** 二维码加载中 */
const qrLoading = ref(false)

/** 轮询定时器 */
let pollTimer: ReturnType<typeof setInterval> | null = null
/** 当前二维码票据 */
let currentTicket = ''

/** 企微检测中 */
const wecomChecking = ref(false)

/** 表单校验规则 */
const rules: FormRules = {
  userId: [
    { required: true, message: '请输入账号', trigger: 'blur' },
  ],
  password: [
    { required: true, message: '请输入密码', trigger: 'blur' },
  ],
  otpCode: [
    { required: true, message: '请输入 OTP 验证码', trigger: 'blur' },
    { len: 6, message: '验证码为 6 位数字', trigger: 'blur' },
  ],
}

// ==========================================================================
// 方法
// ==========================================================================

/**
 * 检测企微客户端登录状态（PRD v1.5 §4.5）
 * 页面加载时自动检测
 */
async function checkWecomClient(): Promise<void> {
  wecomChecking.value = true

  try {
    // 首先尝试使用 UA 检测
    const isWxWork = /wxwork/i.test(navigator.userAgent)

    // 不在企微环境
    if (!isWxWork) {
      wecomChecking.value = false
      return
    }

    // 在企微客户端中，尝试使用企微 JS-SDK
    if (typeof (window as any).wx !== 'undefined') {
      try {
        // 获取当前页面 URL
        const currentUrl = window.location.href.split('#')[0]

        // 调用后端接口获取 JS-SDK 签名配置
        const apiClient = (await import('@/api')).default
        const configResponse = await apiClient.get('/wecom/jsapi-config', {
          params: { url: currentUrl }
        })

        const jsConfig: any = configResponse
        console.log('[Admin Login] 获取到企微 JS-SDK 配置:', jsConfig)

        // 使用 wx.config 配置企微 JS-SDK
        await new Promise<void>((resolve) => {
          (window as any).wx.config({
            beta: true,
            debug: false,
            appId: jsConfig.corp_id,
            timestamp: jsConfig.timestamp,
            nonceStr: jsConfig.nonce_str,
            signature: jsConfig.signature,
            jsApiList: ['agentConfig']
          })
          resolve()
        })

        // 使用 wx.agentConfig 获取当前用户信息
        const userInfo = await new Promise<any>((resolve, reject) => {
          (window as any).wx.agentConfig({
            corpid: jsConfig.corp_id,
            agentid: jsConfig.agent_id,
            timestamp: jsConfig.timestamp,
            nonceStr: jsConfig.nonce_str,
            signature: jsConfig.signature,
            success: (res: any) => resolve(res),
            fail: (res: any) => reject(new Error(res.errMsg || 'agentConfig 失败'))
          })
        })

        // 获取用户ID
        const userId = userInfo.userId
        if (userId) {
          console.log('[Admin Login] 获取到企微用户 ID:', userId)
          wecomUserId.value = userId

          // 检测角色
          const roleResponse = await apiClient.get('/wecom/check-role', {
            params: { userid: userId }
          })
          const roleData: any = roleResponse
          console.log('[Admin Login] 用户角色:', roleData)

          // 如果是管理员，显示免密登录选项
          if (roleData.role === 'admin') {
            // 企微内管理员可免密登录（按钮将显示在顶部）
          } else {
            // 非管理员，使用二维码和密码登录
          }
        }
      } catch (e) {
        // 检测失败，显示普通登录
        console.warn('[Admin Login] 企微 JS-SDK 检测失败:', e)
      }
    } else {
      // 没有企微 JS-SDK
      console.log('[Admin Login] 无企微 JS-SDK，使用默认登录')
    }
  } catch (error) {
    console.error('企微客户端检测失败:', error)
  } finally {
    wecomChecking.value = false
  }
}

/**
 * 企微免密登录
 */
async function handleWecomQuickLogin(): Promise<void> {
  wecomQuickLoading.value = true

  try {
    const apiClient = (await import('@/api')).default

    // 拦截器已统一返回 inner data（CTRT-03），response 即 {token, employee_id, name, ...}
    const result: any = await apiClient.post('/auth_wecom/jsdk-login', {
      userid: wecomUserId.value,
      login_source: 'wecom_jsdk_admin'
    })

    if (result?.token) {
      const { token, employee_id, name } = result

      // 存储 token
      localStorage.setItem('admin_token', token)
      if (employee_id) {
        localStorage.setItem('admin_user_id', employee_id)
      }

      // 存储到 store
      adminStore.token = token
      adminStore.adminUserId = employee_id

      ElMessage.success('登录成功')
      router.push('/')
    } else {
      throw new Error('免密登录失败')
    }
  } catch (error) {
    console.error('企微免密登录失败:', error)
    ElMessage.error('免密登录失败，请使用其他方式')
  } finally {
    wecomQuickLoading.value = false
  }
}

/**
 * 获取扫码登录二维码
 */
async function fetchQrCode(): Promise<void> {
  qrLoading.value = true
  try {
    const apiClient = (await import('@/api')).default
    const result: any = await apiClient.post('/auth_qrcode/create')
    if (result.qrcode_png_base64) {
      qrCode.value = `data:image/png;base64,${result.qrcode_png_base64}`
    } else if (result.qrcode_url) {
      qrCode.value = result.qrcode_url
    }
    // 保存票据并启动轮询
    if (result.ticket) {
      currentTicket = result.ticket
      startPolling()
    }
  } catch (error) {
    console.error('获取二维码失败:', error)
  } finally {
    qrLoading.value = false
  }
}

/**
 * 轮询扫码状态
 */
async function pollQrCode(): Promise<void> {
  if (!currentTicket) return
  try {
    const apiClient = (await import('@/api')).default
    const result: any = await apiClient.get(`/auth_qrcode/poll/${currentTicket}`)
    if (!result) return

    const { status, token, employee_id, name } = result

    if (status === 'confirmed' && token) {
      stopPolling()
      localStorage.setItem('admin_token', token)
      if (employee_id) localStorage.setItem('admin_user_id', employee_id)
      adminStore.token = token
      adminStore.adminUserId = employee_id
      ElMessage.success('扫码登录成功')
      router.push('/')
    } else if (status === 'expired') {
      stopPolling()
      qrCode.value = ''
      ElMessage.warning('二维码已过期，请刷新')
    }
  } catch (error) {
    console.warn('轮询扫码状态失败:', error)
  }
}

/** 启动轮询（每 2 秒） */
function startPolling(): void {
  stopPolling()
  pollTimer = setInterval(pollQrCode, 2000)
}

/** 停止轮询 */
function stopPolling(): void {
  if (pollTimer) {
    clearInterval(pollTimer)
    pollTimer = null
  }
}

/**
 * 处理登录
 */
async function handleLogin(): Promise<void> {
  // 表单校验
  const valid = await formRef.value?.validate().catch(() => false)
  if (!valid) return

  errorMsg.value = ''

  try {
    await adminStore.login(
      loginForm.userId.trim(),
      loginForm.password,
      loginForm.otpCode.trim() || undefined
    )
  } catch (error: unknown) {
    // 检查是否需要 OTP 验证
    if (error instanceof Error && error.message === 'require_otp') {
      requireOtp.value = true
      loginForm.otpCode = ''
      ElMessage.info('请输入 OTP 验证码')
      return
    }

    const errMsg = error instanceof Error ? error.message : '登录失败，请重试'
    errorMsg.value = errMsg
  }
}

// 页面加载时检测企微客户端状态 + 获取二维码
onMounted(() => {
  checkWecomClient()
  fetchQrCode()
})

// 页面卸载时停止轮询
onUnmounted(() => {
  stopPolling()
})
</script>

<style scoped>
/* 登录页面容器 */
.login-page {
  min-height: 100vh;
  display: flex;
  align-items: center;
  justify-content: center;
  position: relative;
  background: var(--bg-primary);
}

/* 背景装饰 */
.login-bg {
  position: absolute;
  inset: 0;
  overflow: hidden;
}
.login-bg-gradient {
  position: absolute;
  top: -50%;
  left: -50%;
  width: 200%;
  height: 200%;
  background: radial-gradient(ellipse at center, rgba(59, 130, 246, 0.08) 0%, transparent 60%);
  animation: rotate 30s linear infinite;
}
@keyframes rotate {
  from { transform: rotate(0deg); }
  to { transform: rotate(360deg); }
}

/* 登录卡片 */
.login-card {
  position: relative;
  z-index: 1;
  width: 400px;
  padding: 40px;
  background: var(--bg-secondary);
  border: 1px solid var(--border);
  border-radius: var(--radius-lg);
  box-shadow: 0 4px 24px rgba(0, 0, 0, 0.3);
}

/* Logo */
.login-logo {
  text-align: center;
  margin-bottom: 32px;
}
.login-logo-icon {
  width: 56px;
  height: 56px;
  background: linear-gradient(135deg, #3b82f6, #8b5cf6);
  border-radius: 14px;
  display: flex;
  align-items: center;
  justify-content: center;
  color: white;
  margin: 0 auto 16px;
}
.login-title {
  font-size: 22px;
  font-weight: 700;
  color: var(--text-primary);
  margin: 0 0 4px;
}
.login-subtitle {
  font-size: 13px;
  color: var(--text-muted);
  margin: 0;
}

/* 登录按钮 */
.login-btn {
  width: 100%;
  margin-top: 8px;
}

/* 提示信息 */
.login-tips {
  display: flex;
  align-items: center;
  justify-content: center;
  gap: 6px;
  margin-top: 20px;
  font-size: 12px;
  color: var(--text-muted);
}

/* 登录方式选择 */
.login-options {
  text-align: center;
  padding: 20px 0;
}

.login-options-title {
  font-size: 14px;
  color: var(--text-secondary);
  margin-bottom: 16px;
}

.login-options-btns {
  display: flex;
  flex-direction: column;
  gap: 12px;
}

.option-btn {
  width: 100%;
  height: 44px;
  font-size: 14px;
}

/* 扫码登录 */
.qr-login {
  text-align: center;
  padding: 20px 0;
}

.qr-title {
  font-size: 16px;
  color: var(--text-primary);
  margin-bottom: 16px;
}

.qr-code {
  width: 180px;
  height: 180px;
  margin: 0 auto 16px;
  background: var(--bg-secondary);
  border-radius: 8px;
  display: flex;
  align-items: center;
  justify-content: center;
}

.qr-code img {
  max-width: 100%;
  max-height: 100%;
}

.qr-loading {
  color: var(--text-muted);
}

.qr-hint {
  font-size: 13px;
  color: var(--text-muted);
  margin-bottom: 12px;
}

/* 二维码容器 */
.qr-container {
  margin-bottom: 12px;
}

.qr-error {
  color: var(--text-muted);
  text-align: center;
  padding: 20px 0;
}

/* 分隔线 */
.divider {
  display: flex;
  align-items: center;
  margin: 16px 0;
  color: var(--text-muted);
  font-size: 13px;
}
.divider::before,
.divider::after {
  content: '';
  flex: 1;
  border-bottom: 1px solid var(--border);
}
.divider span {
  padding: 0 12px;
}

/* 账号密码登录按钮 */
.password-login-btn {
  width: 100%;
}

/* 账号密码登录面板 */
.password-login {
  margin-top: 8px;
}
</style>
