"use client";

/**
 * Attendance 录入页 - 批量录入考勤
 *
 * 数据来源（P7 扩展，MSW mock）：
 * - GraphQL AttendanceSheetQuery：按 classId + date 拉取学生列表 + 当天状态
 * - GraphQL SaveAttendanceSheetMutation：批量保存考勤
 * - GraphQL ClassesQuery：班级下拉选项
 *
 * 维护者：ai13（teacher-portal）
 */

import { useState, useMemo, useEffect } from "react";
import { useQuery, useMutation } from "urql";
import Link from "next/link";
import { Loading, Empty } from "@edu/ui-components";
import { ClassesQuery } from "@/lib/graphql";
import type { Class } from "@/lib/graphql";
import {
  AttendanceSheetQuery,
  SaveAttendanceSheetMutation,
} from "@/lib/graphql-p7-admin";
import type {
  AttendanceStatus,
  AttendanceSheetItem,
  SaveAttendanceRecordInput,
} from "@/lib/graphql-p7-admin";

const STATUS_OPTIONS: { value: AttendanceStatus; label: string }[] = [
  { value: "PRESENT", label: "出勤" },
  { value: "LATE", label: "迟到" },
  { value: "LEAVE", label: "请假" },
  { value: "ABSENT", label: "缺勤" },
  { value: "EARLY_LEAVE", label: "早退" },
];

function statusColor(status: AttendanceStatus): string {
  switch (status) {
    case "PRESENT":
      return "var(--color-success)";
    case "LATE":
      return "var(--color-warning)";
    case "EARLY_LEAVE":
      return "var(--color-warning)";
    case "LEAVE":
      return "var(--color-accent)";
    case "ABSENT":
      return "var(--color-danger)";
    default:
      return "var(--color-ink-muted)";
  }
}

function todayStr(): string {
  const d = new Date();
  return `${d.getFullYear()}-${String(d.getMonth() + 1).padStart(2, "0")}-${String(d.getDate()).padStart(2, "0")}`;
}

interface RowState {
  status: AttendanceStatus;
  note: string;
}

export default function AttendanceSheetPage(): React.ReactNode {
  const [classId, setClassId] = useState("");
  const [date, setDate] = useState(todayStr());
  const [rows, setRows] = useState<Record<string, RowState>>({});
  const [submitting, setSubmitting] = useState(false);
  const [saveError, setSaveError] = useState<string | null>(null);
  const [savedMsg, setSavedMsg] = useState<string | null>(null);

  const [classesResult] = useQuery({ query: ClassesQuery });
  const classes: Class[] = classesResult.data?.classes ?? [];
  const firstClassId = classes[0]?.id ?? "";

  const targetClassId = classId || firstClassId;

  const [sheetResult, reexecuteSheet] = useQuery({
    query: AttendanceSheetQuery,
    variables: { classId: targetClassId, date },
    pause: !targetClassId || !date,
  });

  const sheet: AttendanceSheetItem[] = sheetResult.data?.attendanceSheet ?? [];

  const [, saveSheet] = useMutation(SaveAttendanceSheetMutation);

  // 当 sheet 数据变化时同步本地 rows
  useEffect(() => {
    const next: Record<string, RowState> = {};
    for (const item of sheet) {
      next[item.studentId] = {
        status: item.status ?? "PRESENT",
        note: item.note ?? "",
      };
    }
    setRows(next);
    setSavedMsg(null);
    setSaveError(null);
  }, [sheet]);

  const dirtyCount = useMemo(() => {
    let count = 0;
    for (const item of sheet) {
      const row = rows[item.studentId];
      if (!row) continue;
      const originalStatus = item.status ?? "PRESENT";
      const originalNote = item.note ?? "";
      if (row.status !== originalStatus || row.note !== originalNote) {
        count++;
      }
    }
    return count;
  }, [rows, sheet]);

  const handleSaveAll = async (): Promise<void> => {
    if (!targetClassId || !date) {
      setSaveError("请选择班级和日期");
      return;
    }
    const records: SaveAttendanceRecordInput[] = [];
    for (const item of sheet) {
      const row = rows[item.studentId];
      if (!row) continue;
      records.push({
        studentId: item.studentId,
        status: row.status,
        note: row.note.trim() || null,
      });
    }
    if (records.length === 0) {
      setSaveError("当前无可保存的记录");
      return;
    }
    setSubmitting(true);
    setSaveError(null);
    setSavedMsg(null);
    const res = await saveSheet({
      input: { classId: targetClassId, date, records },
    });
    setSubmitting(false);
    if (res.error) {
      setSaveError(res.error.message);
      return;
    }
    setSavedMsg(
      `已保存 ${res.data?.saveAttendanceSheet?.savedCount ?? records.length} 条记录`,
    );
    reexecuteSheet({ requestPolicy: "network-only" });
  };

  return (
    <div className="px-10 py-10">
      <header className="mb-8">
        <p className="mb-2">
          <Link
            href="/attendance"
            className="text-tiny uppercase tracking-wide text-ink-muted hover:opacity-70"
          >
            ← 返回考勤记录
          </Link>
        </p>
        <h1 className="text-3xl font-serif text-ink">考勤录入</h1>
        <p className="mt-1 text-sm text-ink-muted">
          GraphQL AttendanceSheetQuery + SaveAttendanceSheetMutation · 乐观更新（P7 扩展，MSW mock）
        </p>
      </header>

      <div className="rule-thin mb-8" />

      {/* 班级 + 日期选择 */}
      <section className="mb-8">
        <div className="grid grid-cols-2 gap-6 mb-4">
          <div>
            <label className="block text-tiny uppercase tracking-wide text-ink-muted mb-1">
              班级
            </label>
            <select
              value={targetClassId}
              onChange={(e) => setClassId(e.target.value)}
              className="w-full px-3 py-2 bg-transparent border-b border-rule text-sm font-sans text-ink focus:outline-none focus:border-accent"
            >
              <option value="">请选择班级</option>
              {classes.map((c) => (
                <option key={c.id} value={c.id}>
                  {c.name}
                </option>
              ))}
            </select>
          </div>
          <div>
            <label className="block text-tiny uppercase tracking-wide text-ink-muted mb-1">
              日期
            </label>
            <input
              type="date"
              value={date}
              onChange={(e) => setDate(e.target.value)}
              className="w-full px-3 py-2 bg-transparent border-b border-rule text-sm font-sans text-ink focus:outline-none focus:border-accent"
            />
          </div>
        </div>
      </section>

      {!targetClassId || !date ? (
        <Empty
          title="请选择班级和日期"
          description="选择后即可拉取学生名单进行批量录入"
        />
      ) : sheetResult.fetching ? (
        <Loading lines={8} />
      ) : sheetResult.error ? (
        <div className="mark-left mb-4 py-2 border-l-2 border-danger pl-md">
          <p className="text-sm px-3 text-danger">
            加载失败：{sheetResult.error.message}
          </p>
        </div>
      ) : sheet.length === 0 ? (
        <Empty title="暂无学生" description="该班级尚未导入学生名单" />
      ) : (
        <section>
          <div className="flex items-baseline justify-between mb-4">
            <h2 className="text-xl font-serif text-ink">
              学生考勤录入
              <span className="ml-2 text-sm font-sans text-ink-muted">
                {sheet.length} 名学生 · 已修改 {dirtyCount} 项
              </span>
            </h2>
            <div className="flex items-center gap-3">
              {saveError && (
                <span className="text-tiny text-danger">{saveError}</span>
              )}
              {savedMsg && !submitting && (
                <span className="text-tiny text-success">{savedMsg}</span>
              )}
              <button
                type="button"
                onClick={handleSaveAll}
                disabled={submitting}
                className="px-4 py-2 text-sm text-ink-on-accent bg-accent rounded-button hover:bg-accent-hover disabled:opacity-50"
              >
                {submitting ? "保存中..." : "保存全部"}
              </button>
            </div>
          </div>
          <div className="rule-thin mb-4" />

          {/* 录入表格 */}
          <div className="border border-rule rounded-card overflow-hidden">
            <table className="w-full text-sm">
              <thead className="bg-subtle">
                <tr>
                  <th className="px-4 py-3 text-left text-tiny uppercase tracking-wide text-ink-muted">
                    学生
                  </th>
                  <th className="px-4 py-3 text-left text-tiny uppercase tracking-wide text-ink-muted">
                    学号
                  </th>
                  <th className="px-4 py-3 text-left text-tiny uppercase tracking-wide text-ink-muted">
                    状态
                  </th>
                  <th className="px-4 py-3 text-left text-tiny uppercase tracking-wide text-ink-muted">
                    备注
                  </th>
                </tr>
              </thead>
              <tbody>
                {sheet.map((item) => {
                  const row = rows[item.studentId];
                  const currentStatus = row?.status ?? "PRESENT";
                  return (
                    <tr
                      key={item.studentId}
                      className="border-t border-rule"
                    >
                      <td className="px-4 py-3 font-serif text-ink">
                        {item.studentName}
                      </td>
                      <td className="px-4 py-3 font-mono text-tiny text-ink-muted">
                        {item.studentNo}
                      </td>
                      <td className="px-4 py-3">
                        <div className="flex items-center gap-1 flex-wrap">
                          {STATUS_OPTIONS.map((opt) => {
                            const active = currentStatus === opt.value;
                            return (
                              <button
                                key={opt.value}
                                type="button"
                                onClick={() =>
                                  setRows((prev) => ({
                                    ...prev,
                                    [item.studentId]: {
                                      status: opt.value,
                                      note: row?.note ?? "",
                                    },
                                  }))
                                }
                                className="px-2 py-0.5 text-tiny rounded-button border transition-colors"
                                style={{
                                  color: active
                                    ? "var(--bg-paper)"
                                    : statusColor(opt.value),
                                  borderColor: statusColor(opt.value),
                                  background: active
                                    ? statusColor(opt.value)
                                    : "transparent",
                                }}
                              >
                                {opt.label}
                              </button>
                            );
                          })}
                        </div>
                      </td>
                      <td className="px-4 py-3">
                        <input
                          type="text"
                          value={row?.note ?? ""}
                          onChange={(ev) =>
                            setRows((prev) => ({
                              ...prev,
                              [item.studentId]: {
                                status: currentStatus,
                                note: ev.target.value,
                              },
                            }))
                          }
                          className="w-full px-2 py-1 bg-paper border border-rule rounded-button text-sm text-ink focus:outline-none focus:border-accent"
                          placeholder="可选：备注"
                        />
                      </td>
                    </tr>
                  );
                })}
              </tbody>
            </table>
          </div>
        </section>
      )}
    </div>
  );
}
