"use client";

import Link from "next/link";
import { useCallback, useEffect, useMemo, useState } from "react";
import { Pencil, Users } from "lucide-react";
import {
  Dialog,
  DialogBody,
  DialogContent,
  DialogFooter,
} from "@/components/common/shadcn-enhanced";
import { Button } from "@/components/ui/button";
import { Input } from "@/components/ui/input";
import { Label } from "@/components/ui/label";
import { Select, SelectContent, SelectItem, SelectTrigger, SelectValue } from "@/components/ui/select";
import { Skeleton } from "@/components/ui/skeleton";
import { Table, TableBody, TableCell, TableHead, TableHeader, TableRow } from "@/components/ui/table";
import { cn } from "@/lib/utils";
import { PARENT_TYPE_OPTIONS, parentTypeLabel } from "../constants";
import {
  buildCrossParentFormState,
  updateCrossParents,
} from "../api";
import { useCrossPedigree } from "../CrossPedigreeContext";
import { NONE_SELECT_VALUE, type CrossParentFormState, type CrossParentRow, type SelectOption } from "../types";

function ParentSlotEditor({
  title,
  slot,
  parentType,
  germplasmId,
  observationUnitId,
  germplasmOptions,
  observationUnitOptions,
  onChange,
}: {
  title: string;
  slot: "parent1" | "parent2";
  parentType: string;
  germplasmId: string;
  observationUnitId: string;
  germplasmOptions: SelectOption[];
  observationUnitOptions: SelectOption[];
  onChange: (patch: Partial<CrossParentFormState>) => void;
}) {
  const prefix = slot;
  return (
    <div className="rounded-lg border border-slate-200 p-4 dark:border-slate-800">
      <h4 className="mb-3 text-sm font-medium text-slate-800 dark:text-slate-100">{title}</h4>
      <div className="grid gap-3 md:grid-cols-3">
        <div>
          <Label className="mb-1.5 block text-xs">parent_type</Label>
          <Select
            value={parentType || NONE_SELECT_VALUE}
            onValueChange={(value) => onChange({ [`${prefix}_type`]: value } as Partial<CrossParentFormState>)}
          >
            <SelectTrigger><SelectValue placeholder="选择亲本角色" /></SelectTrigger>
            <SelectContent position="popper" className="z-[110] max-h-60">
              <SelectItem value={NONE_SELECT_VALUE}>不指定</SelectItem>
              {PARENT_TYPE_OPTIONS.map((option) => (
                <SelectItem key={option.value} value={option.value}>{option.label}</SelectItem>
              ))}
            </SelectContent>
          </Select>
        </div>
        <div>
          <Label className="mb-1.5 block text-xs">germplasm_id</Label>
          <Select
            value={germplasmId || NONE_SELECT_VALUE}
            onValueChange={(value) => onChange({ [`${prefix}_germplasm_id`]: value } as Partial<CrossParentFormState>)}
          >
            <SelectTrigger><SelectValue placeholder="选择种质" /></SelectTrigger>
            <SelectContent position="popper" className="z-[110] max-h-60">
              <SelectItem value={NONE_SELECT_VALUE}>不指定种质</SelectItem>
              {germplasmOptions.map((option) => (
                <SelectItem key={option.value} value={option.value}>{option.label}</SelectItem>
              ))}
            </SelectContent>
          </Select>
        </div>
        <div>
          <Label className="mb-1.5 block text-xs">observation_unit_id</Label>
          <Select
            value={observationUnitId || NONE_SELECT_VALUE}
            onValueChange={(value) => onChange({ [`${prefix}_observation_unit_id`]: value } as Partial<CrossParentFormState>)}
          >
            <SelectTrigger><SelectValue placeholder="选择观测单元" /></SelectTrigger>
            <SelectContent position="popper" className="z-[110] max-h-60">
              <SelectItem value={NONE_SELECT_VALUE}>不指定观测单元</SelectItem>
              {observationUnitOptions.map((option) => (
                <SelectItem key={option.value} value={option.value}>{option.label}</SelectItem>
              ))}
            </SelectContent>
          </Select>
        </div>
      </div>
    </div>
  );
}

export function CrossParentTab() {
  const { snapshot, loading: pageLoading, refresh } = useCrossPedigree();
  const [rows, setRows] = useState<CrossParentRow[]>([]);
  const [loading, setLoading] = useState(true);
  const [error, setError] = useState<string | null>(null);
  const [search, setSearch] = useState("");
  const [dialogOpen, setDialogOpen] = useState(false);
  const [saving, setSaving] = useState(false);
  const [form, setForm] = useState<CrossParentFormState | null>(null);

  const germplasmOptions = snapshot?.germplasm ?? [];
  const observationUnitOptions = snapshot?.observationUnits ?? [];
  const crossOptions = snapshot?.crossOptions ?? [];

  const syncRowsFromSnapshot = useCallback(async () => {
    setLoading(true);
    setError(null);
    try {
      const data = await refresh(false);
      setRows(data.parentRows);
    } catch (event) {
      setError(event instanceof Error ? event.message : "加载失败");
    } finally {
      setLoading(false);
    }
  }, [refresh]);

  useEffect(() => {
    syncRowsFromSnapshot();
  }, [syncRowsFromSnapshot]);

  const filteredRows = useMemo(() => {
    const keyword = search.trim().toLowerCase();
    if (!keyword) return rows;
    return rows.filter((row) =>
      [row.cross_name, row.germplasm_name, row.observation_unit_name, row.crossing_project_name, row.parent_type]
        .some((value) => String(value ?? "").toLowerCase().includes(keyword)),
    );
  }, [rows, search]);

  const openEditorForCross = useCallback((crossId: string) => {
    if (!snapshot) throw new Error("数据尚未加载");
    const plannedCross = snapshot.plannedCrosses.find((item) => item.id === crossId);
    if (plannedCross) {
      setForm(buildCrossParentFormState(
        plannedCross.id,
        true,
        plannedCross.crossing_project_id,
        plannedCross.crossing_project_name,
        plannedCross.parent1,
        plannedCross.parent2,
      ));
      setDialogOpen(true);
      return;
    }
    const actualCross = snapshot.actualCrosses.find((item) => item.id === crossId);
    if (!actualCross) throw new Error("Cross 不存在");
    setForm(buildCrossParentFormState(
      actualCross.id,
      false,
      actualCross.crossing_project_id,
      actualCross.crossing_project_name,
      actualCross.parent1,
      actualCross.parent2,
    ));
    setDialogOpen(true);
  }, [snapshot]);

  const openCreate = () => {
    if (crossOptions.length === 0) {
      setError("请先在「Cross 杂交」Tab 创建计划或实际杂交");
      return;
    }
    setForm({
      cross_id: NONE_SELECT_VALUE,
      planned: false,
      crossing_project_id: null,
      crossing_project_name: null,
      parent1_type: NONE_SELECT_VALUE,
      parent1_germplasm_id: NONE_SELECT_VALUE,
      parent1_observation_unit_id: NONE_SELECT_VALUE,
      parent2_type: NONE_SELECT_VALUE,
      parent2_germplasm_id: NONE_SELECT_VALUE,
      parent2_observation_unit_id: NONE_SELECT_VALUE,
    });
    setDialogOpen(true);
  };

  const handleCrossChange = (crossId: string) => {
    if (crossId === NONE_SELECT_VALUE || !form) return;
    try {
      openEditorForCross(crossId);
    } catch (event) {
      setError(event instanceof Error ? event.message : "加载 Cross 失败");
    }
  };

  const handleSave = async () => {
    if (!form) return;
    setSaving(true);
    setError(null);
    try {
      await updateCrossParents(form);
      setDialogOpen(false);
      await syncRowsFromSnapshot();
    } catch (event) {
      setError(event instanceof Error ? event.message : "保存失败");
    } finally {
      setSaving(false);
    }
  };

  const crossIds = useMemo(() => Array.from(new Set(rows.map((row) => row.cross_id))), [rows]);
  const showLoading = loading || pageLoading;

  return (
    <div className="flex min-h-full flex-col gap-4">
      <div className="flex flex-col gap-4 sm:flex-row sm:items-start sm:justify-between">
        <div className="flex items-center gap-3">
          <div className={cn("rounded-xl p-2.5", "bg-gradient-to-br from-violet-500 to-purple-600")}>
            <Users className="h-5 w-5 text-white" />
          </div>
          <div>
            <h2 className="text-lg font-semibold text-slate-900 dark:text-slate-50">Cross Parent 杂交亲本</h2>
            <p className="mt-0.5 text-sm text-slate-500 dark:text-slate-400">
              cross_parent：通过 Cross 的 parent1/parent2 维护亲本（parent_type + germplasm / observation_unit）
            </p>
          </div>
        </div>
        <Button onClick={openCreate} className="shrink-0">维护亲本</Button>
      </div>

      <div className="mb-1">
        <span className="rounded-full bg-violet-50 px-3 py-1 text-xs text-violet-700 dark:bg-violet-400/10 dark:text-violet-200">
          BrAPI /brapi/v2/crosses · /brapi/v2/plannedcrosses (PUT parent1/parent2)
        </span>
      </div>

      <div className="rounded-xl border border-slate-200 bg-white p-4 dark:border-slate-800 dark:bg-slate-950">
        <div className="mb-4 flex flex-wrap items-center gap-3">
          <Input
            value={search}
            onChange={(event) => setSearch(event.target.value)}
            placeholder="搜索 Cross / 种质 / 观测单元 / 项目"
            className="max-w-sm"
          />
        </div>

        {error ? <p className="mb-3 text-sm text-red-500">{error}</p> : null}

        {showLoading ? (
          <Skeleton className="h-40 w-full" />
        ) : (
          <Table>
            <TableHeader>
              <TableRow className="bg-slate-50 dark:bg-slate-900">
                <TableHead>Cross</TableHead>
                <TableHead>类型</TableHead>
                <TableHead>杂交项目</TableHead>
                <TableHead>亲本位</TableHead>
                <TableHead>parent_type</TableHead>
                <TableHead>种质</TableHead>
                <TableHead>观测单元</TableHead>
                <TableHead className="w-24 text-right">操作</TableHead>
              </TableRow>
            </TableHeader>
            <TableBody>
              {filteredRows.length === 0 ? (
                <TableRow>
                  <TableCell colSpan={8} className="py-8 text-center text-sm text-slate-400">
                    暂无亲本记录。请先在 Cross Tab 创建杂交，再点击「维护亲本」录入 parent1/parent2。
                  </TableCell>
                </TableRow>
              ) : (
                filteredRows.map((row) => (
                  <TableRow key={row.id}>
                    <TableCell>
                      <Link
                        href={row.planned
                          ? `/germplasm/cross-pedigree/planned-crosses/${encodeURIComponent(row.cross_id)}`
                          : `/germplasm/cross-pedigree/crosses/${encodeURIComponent(row.cross_id)}?tab=parents`}
                        className="font-medium text-violet-600 hover:underline dark:text-violet-400"
                      >
                        {row.cross_name || row.cross_id}
                      </Link>
                    </TableCell>
                    <TableCell>{row.planned ? "计划杂交" : "实际杂交"}</TableCell>
                    <TableCell>{row.crossing_project_name || "—"}</TableCell>
                    <TableCell>{row.parent_slot === "parent1" ? "Parent 1" : "Parent 2"}</TableCell>
                    <TableCell>{parentTypeLabel(row.parent_type)}</TableCell>
                    <TableCell>{row.germplasm_name || row.germplasm_id || "—"}</TableCell>
                    <TableCell>{row.observation_unit_name || row.observation_unit_id || "—"}</TableCell>
                    <TableCell className="text-right">
                      <Button size="sm" variant="outline" className="gap-1" onClick={() => openEditorForCross(row.cross_id)}>
                        <Pencil className="h-3.5 w-3.5" />
                        编辑
                      </Button>
                    </TableCell>
                  </TableRow>
                ))
              )}
            </TableBody>
          </Table>
        )}

        {!showLoading && crossIds.length > 0 ? (
          <p className="mt-3 text-xs text-slate-400">
            共 {crossIds.length} 个 Cross 已录入亲本信息（BrAPI 每个 Cross 支持 parent1 / parent2 两个亲本槽位）
          </p>
        ) : null}
      </div>

      <Dialog open={dialogOpen} onOpenChange={setDialogOpen}>
        <DialogContent className="max-w-3xl" title="维护杂交亲本 (cross_parent)">
          <DialogBody className="space-y-4">
            <div>
              <Label className="mb-1.5 block text-sm">所属 Cross</Label>
              <Select
                value={form?.cross_id || NONE_SELECT_VALUE}
                onValueChange={(value) => {
                  if (!form) return;
                  setForm({ ...form, cross_id: value });
                  handleCrossChange(value);
                }}
              >
                <SelectTrigger><SelectValue placeholder="选择 Cross" /></SelectTrigger>
                <SelectContent position="popper" className="z-[110] max-h-60">
                  <SelectItem value={NONE_SELECT_VALUE}>请选择 Cross</SelectItem>
                  {crossOptions.map((option) => (
                    <SelectItem key={option.value} value={option.value}>{option.label}</SelectItem>
                  ))}
                </SelectContent>
              </Select>
            </div>

            <div>
              <Label className="mb-1.5 block text-sm">crossing_project_id（只读）</Label>
              <Input readOnly value={form?.crossing_project_name || form?.crossing_project_id || "—"} />
            </div>

            {form ? (
              <>
                <ParentSlotEditor
                  title="Parent 1"
                  slot="parent1"
                  parentType={form.parent1_type}
                  germplasmId={form.parent1_germplasm_id}
                  observationUnitId={form.parent1_observation_unit_id}
                  germplasmOptions={germplasmOptions}
                  observationUnitOptions={observationUnitOptions}
                  onChange={(patch) => setForm({ ...form, ...patch })}
                />
                <ParentSlotEditor
                  title="Parent 2"
                  slot="parent2"
                  parentType={form.parent2_type}
                  germplasmId={form.parent2_germplasm_id}
                  observationUnitId={form.parent2_observation_unit_id}
                  germplasmOptions={germplasmOptions}
                  observationUnitOptions={observationUnitOptions}
                  onChange={(patch) => setForm({ ...form, ...patch })}
                />
              </>
            ) : null}
          </DialogBody>
          <DialogFooter>
            <Button variant="outline" onClick={() => setDialogOpen(false)} disabled={saving}>取消</Button>
            <Button onClick={handleSave} disabled={saving || !form || form.cross_id === NONE_SELECT_VALUE}>
              {saving ? "保存中..." : "保存亲本"}
            </Button>
          </DialogFooter>
        </DialogContent>
      </Dialog>
    </div>
  );
}
