// 管理员后台组件
function AdminPage({ onBack }) {
  const [authed, setAuthed] = React.useState(false);
  const [checking, setChecking] = React.useState(true);
  const [password, setPassword] = React.useState('');
  const [error, setError] = React.useState('');
  const [records, setRecords] = React.useState([]);
  const [sortField, setSortField] = React.useState('submittedAt');
  const [sortOrder, setSortOrder] = React.useState('desc');
  const [searchText, setSearchText] = React.useState('');

  // V2：登录状态由服务器 HttpOnly Cookie 管理，不在前端保存管理员密码或 token。
  const loadRecords = function() {
    return fetch('/api/admin/records', {
      method: 'GET',
      credentials: 'same-origin',
      cache: 'no-store'
    })
      .then(function(res) {
        if (res.status === 401) {
          setAuthed(false);
          throw new Error('未登录');
        }
        if (!res.ok) throw new Error('加载成绩失败');
        return res.json();
      })
      .then(function(data) {
        setRecords(data.list || []);
        setAuthed(true);
        return data.list || [];
      });
  };

  React.useEffect(() => {
    loadRecords()
      .catch(function() {})
      .finally(function() {
        setChecking(false);
      });
  }, []);

  const handleLogin = function(e) {
    e.preventDefault();
    setError('');
    fetch('/api/admin/login', {
      method: 'POST',
      headers: { 'Content-Type': 'application/json' },
      credentials: 'same-origin',
      body: JSON.stringify({ password: password })
    })
      .then(function(res) {
        return res.json().catch(function() { return {}; }).then(function(data) {
          if (!res.ok) throw new Error(data.error || '登录失败');
          return data;
        });
      })
      .then(function() {
        setPassword('');
        return loadRecords();
      })
      .catch(function(err) {
        setAuthed(false);
        setError(err.message || '密码错误，请重试');
      });
  };

  const handleLogout = function() {
    fetch('/api/admin/logout', {
      method: 'POST',
      credentials: 'same-origin'
    }).catch(function() {}).finally(function() {
      setAuthed(false);
      setPassword('');
      setRecords([]);
    });
  };

  if (checking) {
    return (
      <div style={adminStyles.loginWrapper}>
        <div style={adminStyles.loginCard}>
          <div style={adminStyles.loginTitle}>管理员后台</div>
          <div style={adminStyles.loginSub}>正在验证登录状态…</div>
        </div>
      </div>
    );
  }

  // 排序 + 搜索
  const filteredRecords = React.useMemo(() => {
    let list = [...records];
    if (searchText.trim()) {
      const kw = searchText.trim().toLowerCase();
      list = list.filter((r) => r.name && r.name.toLowerCase().includes(kw));
    }
    list.sort((a, b) => {
      let va = a[sortField];
      let vb = b[sortField];
      if (sortField === 'submittedAt') {
        va = new Date(va).getTime();
        vb = new Date(vb).getTime();
      } else if (sortField === 'score') {
        va = Number(va);
        vb = Number(vb);
      }
      if (va < vb) return sortOrder === 'asc' ? -1 : 1;
      if (va > vb) return sortOrder === 'asc' ? 1 : -1;
      return 0;
    });
    return list;
  }, [records, sortField, sortOrder, searchText]);

  const handleSort = (field) => {
    if (sortField === field) {
      setSortOrder(sortOrder === 'asc' ? 'desc' : 'asc');
    } else {
      setSortField(field);
      setSortOrder('desc');
    }
  };

  // 导出 CSV（本地生成）
  const exportCSV = function() {
    if (filteredRecords.length === 0) {
      alert('暂无记录可导出');
      return;
    }

    var headers = [
      '序号',
      '姓名',
      '分数',
      '是否合格',
      '答题用时(分钟)',
      '提交时间',
    ];

    var rows = filteredRecords.map(function(r, i) {
      return [
        i + 1,
        r.name || '',
        r.score != null ? r.score : '',
        r.passed ? '合格' : '不合格',
        r.durationMin != null ? r.durationMin : '',
        formatDateTime(r.submittedAt),
      ];
    });

    // 添加 BOM 防乱码
    var csvContent = '\uFEFF';
    csvContent += headers.join(',') + '\n';
    rows.forEach(function(row) {
      csvContent +=
        row
          .map(function(cell) {
            var s = String(cell != null ? cell : '');
            // 含逗号/引号的字段加引号
            if (s.indexOf(',') >= 0 || s.indexOf('"') >= 0 || s.indexOf('\n') >= 0) {
              return '"' + s.replace(/"/g, '""') + '"';
            }
            return s;
          })
          .join(',') + '\n';
    });

    var blob = new Blob([csvContent], { type: 'text/csv;charset=utf-8' });
    var url = URL.createObjectURL(blob);
    var link = document.createElement('a');
    link.href = url;
    var today = new Date();
    var dateStr = today.getFullYear() + String(today.getMonth() + 1).padStart(2, '0') + String(today.getDate()).padStart(2, '0');
    link.download = 'Group_y_考试成绩_' + dateStr + '.csv';
    document.body.appendChild(link);
    link.click();
    document.body.removeChild(link);
    URL.revokeObjectURL(url);
  };

  const formatDateTime = (dateStr) => {
    if (!dateStr) return '';
    const d = new Date(dateStr);
    const pad = (n) => String(n).padStart(2, '0');
    return `${d.getFullYear()}-${pad(d.getMonth() + 1)}-${pad(d.getDate())} ${pad(d.getHours())}:${pad(d.getMinutes())}:${pad(d.getSeconds())}`;
  };

  const formatDuration = (min) => {
    if (min === undefined || min === null) return '—';
    if (min < 1) return '不足1分钟';
    if (min < 60) return `${Math.round(min)} 分钟`;
    const h = Math.floor(min / 60);
    const m = Math.round(min % 60);
    return `${h} 小时 ${m} 分`;
  };

  // 统计
  const stats = React.useMemo(() => {
    if (records.length === 0) {
      return { total: 0, passed: 0, avgScore: 0, passRate: 0 };
    }
    const passed = records.filter((r) => r.passed).length;
    const totalScore = records.reduce((sum, r) => sum + (r.score || 0), 0);
    return {
      total: records.length,
      passed,
      avgScore: Math.round((totalScore / records.length) * 10) / 10,
      passRate: Math.round((passed / records.length) * 1000) / 10,
    };
  }, [records]);

  // === 登录页 ===
  if (!authed) {
    return (
      <div style={adminStyles.loginWrapper}>
        <div style={adminStyles.loginCard}>
          <div style={adminStyles.loginLogoWrap}>
            <img
              src="assets/group_y_logo.png"
              alt="Group y"
              style={adminStyles.loginLogo}
            />
          </div>
          <div style={adminStyles.loginTitle}>管理员后台</div>
          <div style={adminStyles.loginSub}>Group y 品牌入职考核成绩管理</div>

          <form onSubmit={handleLogin} style={adminStyles.loginForm}>
            <div style={adminStyles.inputGroup}>
              <label style={adminStyles.inputLabel}>管理员密码</label>
              <input
                type="password"
                value={password}
                onChange={(e) => {
                  setPassword(e.target.value);
                  setError('');
                }}
                style={{
                  ...adminStyles.input,
                  ...(error ? adminStyles.inputError : {}),
                }}
                placeholder="请输入密码"
                autoFocus
              />
              {error && <div style={adminStyles.errorText}>{error}</div>}
            </div>

            <button type="submit" style={adminStyles.loginBtn} className="gy-login-btn">
              登录
            </button>
          </form>

          <button style={adminStyles.backLink} onClick={onBack}>
            ← 返回首页
          </button>
        </div>
      </div>
    );
  }

  // === 后台主界面 ===
  return (
    <div style={adminStyles.wrapper}>
      {/* 顶部 */}
      <div style={adminStyles.header}>
        <div style={adminStyles.headerLeft}>
          <img
            src="assets/group_y_logo.png"
            alt="Group y"
            style={adminStyles.headerLogo}
          />
          <span style={adminStyles.headerSep}>·</span>
          <span style={adminStyles.headerTitle}>管理员后台</span>
        </div>
        <div style={adminStyles.headerRight}>
          <button style={adminStyles.backBtn} onClick={onBack} className="gy-back-btn">
            ← 返回首页
          </button>
          <button style={adminStyles.logoutBtn} onClick={handleLogout} className="gy-logout-btn">
            退出登录
          </button>
        </div>
      </div>

      {/* 内容 */}
      <div style={adminStyles.content} className="gy-content-admin">
        {/* 统计卡片 */}
        <div style={adminStyles.statsRow} className="gy-stats-row-admin">
          <div style={adminStyles.statCard}>
            <div style={adminStyles.statValue}>{stats.total}</div>
            <div style={adminStyles.statLabel}>考试总人次</div>
          </div>
          <div style={adminStyles.statCard}>
            <div style={{ ...adminStyles.statValue, color: '#3a6a3a' }}>
              {stats.passed}
            </div>
            <div style={adminStyles.statLabel}>合格人数</div>
          </div>
          <div style={adminStyles.statCard}>
            <div style={{ ...adminStyles.statValue, color: '#8b6914' }}>
              {stats.passRate}%
            </div>
            <div style={adminStyles.statLabel}>合格率</div>
          </div>
          <div style={adminStyles.statCard}>
            <div style={{ ...adminStyles.statValue, color: '#9a5a70' }}>
              {stats.avgScore}
            </div>
            <div style={adminStyles.statLabel}>平均分数</div>
          </div>
        </div>

        {/* 操作栏 */}
        <div style={adminStyles.toolbar} className="gy-toolbar-admin">
          <div style={adminStyles.searchBox} className="gy-search-box-admin">
            <svg
              viewBox="0 0 24 24"
              width="16"
              height="16"
              fill="none"
              stroke="currentColor"
              strokeWidth="2"
              strokeLinecap="round"
              strokeLinejoin="round"
              style={adminStyles.searchIcon}
            >
              <circle cx="11" cy="11" r="8" />
              <line x1="21" y1="21" x2="16.65" y2="16.65" />
            </svg>
            <input
              type="text"
              placeholder="按姓名搜索..."
              value={searchText}
              onChange={(e) => setSearchText(e.target.value)}
              style={adminStyles.searchInput}
            />
          </div>

          <button
            style={adminStyles.exportBtn}
            onClick={function() { loadRecords().catch(function(err) { alert(err.message || '加载失败'); }); }}
            className="gy-export-btn"
          >
            刷新成绩
          </button>

          <button
            style={adminStyles.exportBtn}
            onClick={exportCSV}
            className="gy-export-btn"
          >
            <svg
              viewBox="0 0 24 24"
              width="16"
              height="16"
              fill="none"
              stroke="currentColor"
              strokeWidth="2"
              strokeLinecap="round"
              strokeLinejoin="round"
            >
              <path d="M21 15v4a2 2 0 0 1-2 2H5a2 2 0 0 1-2-2v-4" />
              <polyline points="7 10 12 15 17 10" />
              <line x1="12" y1="15" x2="12" y2="3" />
            </svg>
            导出 CSV
          </button>
        </div>

        {/* 表格 */}
        <div style={adminStyles.tableWrap}>
          <table style={adminStyles.table}>
            <thead>
              <tr style={adminStyles.tableHeader}>
                <th style={{ ...adminStyles.th, width: '60px' }}>序号</th>
                <th style={adminStyles.th} onClick={() => handleSort('name')}>
                  <span style={adminStyles.sortHeader}>
                    姓名
                    <SortIcon
                      active={sortField === 'name'}
                      order={sortOrder}
                    />
                  </span>
                </th>
                <th style={adminStyles.th} onClick={() => handleSort('score')}>
                  <span style={adminStyles.sortHeader}>
                    分数
                    <SortIcon
                      active={sortField === 'score'}
                      order={sortOrder}
                    />
                  </span>
                </th>
                <th style={adminStyles.th}>是否合格</th>
                <th style={adminStyles.th} onClick={() => handleSort('durationMin')}>
                  <span style={adminStyles.sortHeader}>
                    答题用时
                    <SortIcon
                      active={sortField === 'durationMin'}
                      order={sortOrder}
                    />
                  </span>
                </th>
                <th
                  style={adminStyles.th}
                  onClick={() => handleSort('submittedAt')}
                >
                  <span style={adminStyles.sortHeader}>
                    提交时间
                    <SortIcon
                      active={sortField === 'submittedAt'}
                      order={sortOrder}
                    />
                  </span>
                </th>
              </tr>
            </thead>
            <tbody>
              {filteredRecords.length === 0 ? (
                <tr>
                  <td
                    colSpan={6}
                    style={{ ...adminStyles.td, textAlign: 'center', padding: '48px 0', color: '#9a8570' }}
                  >
                    {searchText ? '未找到匹配的记录' : '暂无考试记录'}
                  </td>
                </tr>
              ) : (
                filteredRecords.map((r, i) => (
                  <tr key={i} style={adminStyles.tableRow} className="gy-table-row">
                    <td style={adminStyles.td}>{i + 1}</td>
                    <td style={{ ...adminStyles.td, fontWeight: 500 }}>{r.name}</td>
                    <td style={adminStyles.td}>
                      <span
                        style={{
                          fontWeight: 600,
                          color: r.passed ? '#3a6a3a' : '#8a3a3a',
                        }}
                      >
                        {r.score}
                      </span>
                    </td>
                    <td style={adminStyles.td}>
                      <span
                        style={{
                          ...adminStyles.statusTag,
                          background: r.passed ? '#e8f0e8' : '#f5e8e8',
                          color: r.passed ? '#3a6a3a' : '#8a3a3a',
                        }}
                      >
                        {r.passed ? '合格' : '不合格'}
                      </span>
                    </td>
                    <td style={adminStyles.td}>{formatDuration(r.durationMin)}</td>
                    <td style={adminStyles.td}>{formatDateTime(r.submittedAt)}</td>
                  </tr>
                ))
              )}
            </tbody>
          </table>
        </div>

        <div style={adminStyles.tableFooter}>
          共 {filteredRecords.length} 条记录
          {searchText && `（已筛选，全部共 ${records.length} 条）`}
        </div>
      </div>
    </div>
  );
}

function SortIcon({ active, order }) {
  return (
    <span style={adminStyles.sortIcon}>
      <svg
        viewBox="0 0 24 24"
        width="12"
        height="12"
        fill="currentColor"
        style={{
          opacity: active && order === 'asc' ? 1 : 0.3,
          transform: 'translateY(1px)',
        }}
      >
        <polygon points="12,4 4,14 20,14" />
      </svg>
      <svg
        viewBox="0 0 24 24"
        width="12"
        height="12"
        fill="currentColor"
        style={{
          opacity: active && order === 'desc' ? 1 : 0.3,
          transform: 'translateY(-1px)',
        }}
      >
        <polygon points="12,20 20,10 4,10" />
      </svg>
    </span>
  );
}

const adminStyles = {
  loginWrapper: {
    minHeight: '100vh',
    display: 'flex',
    alignItems: 'center',
    justifyContent: 'center',
    padding: '40px 20px',
    background:
      'linear-gradient(135deg, #faf7f2 0%, #f5efe6 50%, #efe6d8 100%)',
    fontFamily:
      '"Source Han Serif CN", "Noto Serif SC", "Songti SC", serif',
  },
  loginCard: {
    width: '100%',
    maxWidth: '420px',
    background: '#fff',
    borderRadius: '4px',
    boxShadow:
      '0 1px 3px rgba(60, 40, 20, 0.06), 0 8px 32px rgba(60, 40, 20, 0.08)',
    padding: '40px 36px 32px',
    textAlign: 'center',
    position: 'relative',
  },
  loginLogoWrap: {
    marginBottom: '16px',
  },
  loginLogo: {
    height: '40px',
    objectFit: 'contain',
  },
  loginTitle: {
    fontSize: '24px',
    fontWeight: '600',
    color: '#3d2e15',
    marginBottom: '8px',
    letterSpacing: '2px',
  },
  loginSub: {
    fontSize: '13px',
    color: '#8b7355',
    marginBottom: '28px',
    letterSpacing: '1px',
  },
  loginForm: {
    textAlign: 'left',
  },
  inputGroup: {
    marginBottom: '20px',
  },
  inputLabel: {
    display: 'block',
    fontSize: '13px',
    color: '#5c4a2e',
    marginBottom: '8px',
    fontWeight: '500',
  },
  input: {
    width: '100%',
    padding: '12px 14px',
    border: '1px solid #e0d0b0',
    borderRadius: '2px',
    fontSize: '15px',
    fontFamily: 'inherit',
    color: '#3d2e15',
    background: '#fdfbf5',
    outline: 'none',
    transition: 'border-color 0.2s, box-shadow 0.2s',
    boxSizing: 'border-box',
  },
  inputError: {
    borderColor: '#c07a7a',
    background: '#fdf5f5',
  },
  errorText: {
    marginTop: '6px',
    fontSize: '12px',
    color: '#c05a5a',
  },
  loginBtn: {
    width: '100%',
    padding: '12px',
    border: 'none',
    background: 'linear-gradient(135deg, #8b6914, #b8860b)',
    color: '#fff',
    borderRadius: '2px',
    fontSize: '15px',
    fontWeight: '500',
    letterSpacing: '4px',
    cursor: 'pointer',
    fontFamily: 'inherit',
    transition: 'all 0.2s',
    boxShadow: '0 2px 8px rgba(139, 105, 20, 0.2)',
  },
  backLink: {
    marginTop: '20px',
    background: 'none',
    border: 'none',
    color: '#8b7355',
    fontSize: '13px',
    cursor: 'pointer',
    fontFamily: 'inherit',
  },
  // 后台主界面
  wrapper: {
    minHeight: '100vh',
    background: '#f5efe6',
    fontFamily:
      '"Source Han Serif CN", "Noto Serif SC", "Songti SC", serif',
    display: 'flex',
    flexDirection: 'column',
  },
  header: {
    display: 'flex',
    alignItems: 'center',
    justifyContent: 'space-between',
    padding: '14px 32px',
    background: '#fff',
    borderBottom: '1px solid #e8dcc8',
    boxShadow: '0 1px 2px rgba(60, 40, 20, 0.04)',
  },
  headerLeft: {
    display: 'flex',
    alignItems: 'center',
    gap: '10px',
  },
  headerLogo: {
    height: '28px',
    objectFit: 'contain',
  },
  headerSep: {
    color: '#c4a878',
  },
  headerTitle: {
    fontSize: '15px',
    color: '#5c4a2e',
    fontWeight: '600',
    letterSpacing: '1px',
  },
  headerRight: {
    display: 'flex',
    gap: '10px',
  },
  backBtn: {
    padding: '6px 14px',
    border: '1px solid #d8cfc0',
    background: '#fff',
    color: '#5c4a2e',
    borderRadius: '2px',
    cursor: 'pointer',
    fontSize: '13px',
    fontFamily: 'inherit',
    transition: 'all 0.2s',
  },
  logoutBtn: {
    padding: '6px 14px',
    border: '1px solid #e0c0c0',
    background: '#fff',
    color: '#a05050',
    borderRadius: '2px',
    cursor: 'pointer',
    fontSize: '13px',
    fontFamily: 'inherit',
    transition: 'all 0.2s',
  },
  content: {
    flex: 1,
    padding: '28px 32px',
    maxWidth: '1200px',
    width: '100%',
    margin: '0 auto',
    boxSizing: 'border-box',
  },
  statsRow: {
    display: 'grid',
    gridTemplateColumns: 'repeat(4, 1fr)',
    gap: '16px',
    marginBottom: '24px',
  },
  statCard: {
    background: '#fff',
    borderRadius: '4px',
    padding: '20px 24px',
    boxShadow: '0 2px 8px rgba(60, 40, 20, 0.06)',
    borderTop: '3px solid #d4a853',
  },
  statValue: {
    fontSize: '32px',
    fontWeight: '600',
    color: '#8b6914',
    lineHeight: 1,
    marginBottom: '8px',
  },
  statLabel: {
    fontSize: '13px',
    color: '#8b7355',
    letterSpacing: '1px',
  },
  toolbar: {
    display: 'flex',
    justifyContent: 'space-between',
    alignItems: 'center',
    marginBottom: '16px',
    gap: '12px',
  },
  searchBox: {
    position: 'relative',
    flex: 1,
    maxWidth: '320px',
  },
  searchIcon: {
    position: 'absolute',
    left: '12px',
    top: '50%',
    transform: 'translateY(-50%)',
    color: '#9a8570',
  },
  searchInput: {
    width: '100%',
    padding: '9px 14px 9px 36px',
    border: '1px solid #e0d0b0',
    borderRadius: '2px',
    fontSize: '14px',
    fontFamily: 'inherit',
    color: '#3d2e15',
    background: '#fff',
    outline: 'none',
    boxSizing: 'border-box',
    transition: 'border-color 0.2s',
  },
  exportBtn: {
    display: 'inline-flex',
    alignItems: 'center',
    gap: '6px',
    padding: '9px 18px',
    border: 'none',
    background: 'linear-gradient(135deg, #8b6914, #b8860b)',
    color: '#fff',
    borderRadius: '2px',
    cursor: 'pointer',
    fontSize: '13px',
    fontWeight: '500',
    fontFamily: 'inherit',
    transition: 'all 0.2s',
    boxShadow: '0 2px 6px rgba(139, 105, 20, 0.2)',
  },
  tableWrap: {
    background: '#fff',
    borderRadius: '4px',
    boxShadow: '0 2px 8px rgba(60, 40, 20, 0.06)',
    overflow: 'hidden',
  },
  table: {
    width: '100%',
    borderCollapse: 'collapse',
    fontSize: '14px',
  },
  tableHeader: {
    background: '#faf6ed',
  },
  th: {
    padding: '14px 16px',
    textAlign: 'left',
    color: '#5c4a2e',
    fontWeight: '600',
    fontSize: '13px',
    letterSpacing: '0.5px',
    borderBottom: '1px solid #e8dcc8',
    cursor: 'pointer',
    userSelect: 'none',
  },
  sortHeader: {
    display: 'inline-flex',
    alignItems: 'center',
    gap: '4px',
  },
  sortIcon: {
    display: 'inline-flex',
    flexDirection: 'column',
    marginLeft: '4px',
  },
  tableRow: {
    borderBottom: '1px solid #f0e8d8',
    transition: 'background 0.15s',
  },
  td: {
    padding: '12px 16px',
    color: '#3d2e15',
    fontSize: '14px',
  },
  statusTag: {
    display: 'inline-block',
    padding: '3px 10px',
    borderRadius: '2px',
    fontSize: '12px',
    fontWeight: '500',
    letterSpacing: '1px',
  },
  tableFooter: {
    textAlign: 'right',
    padding: '12px 4px 0',
    fontSize: '13px',
    color: '#8b7355',
  },
};

// hover 样式通过 style tag 在 index.html 补充
window.AdminPage = AdminPage;
