"use client";

import Link from "next/link";
import { useCallback, useMemo, useState } from "react";
import { useTranslation } from "react-i18next";
import { useAsyncEffect } from "@/hooks/use-async-effect";
import { useTranslationRef } from "@/hooks/use-translation-ref";
import { toast } from "sonner";

import { getAdminDraws } from "@/api/admin-draws";
import { getAdminRiskPools } from "@/api/admin-risk";
import { AdminTableExportButton } from "@/components/admin/admin-table-export-button";
import { AdminNoResourceState, AdminTableNoResourceRow } from "@/components/admin/admin-no-resource-state";
import { Button, buttonVariants } from "@/components/ui/button";
import { Label } from "@/components/ui/label";
import {
  Select,
  SelectContent,
  SelectItem,
  SelectTrigger,
  SelectValue,
} from "@/components/ui/select";
import {
  Table,
  TableBody,
  TableCell,
  TableHead,
  TableHeader,
  TableRow,
} from "@/components/ui/table";
import { Input } from "@/components/ui/input";
import { AdminLoadingState, AdminLoadingInline, AdminTableLoadingRow } from "@/components/admin/admin-loading-state";
import { ConfigSection } from "@/modules/config/config-section";
import { formatAdminMinorUnits } from "@/lib/money";
import { cn } from "@/lib/utils";
import { LotteryApiBizError } from "@/types/api/errors";
import type { AdminDrawListItem } from "@/types/api/admin-draws";
import type { AdminRiskPoolRow } from "@/types/api/admin-risk";

type PoolFilter = "all" | "sold_out" | "high_risk";

export function RiskCapRuntimePanel() {
  const { t } = useTranslation(["config", "risk", "draws", "common"]);
  const tRef = useTranslationRef(["config", "common"]);
  const [draws, setDraws] = useState<AdminDrawListItem[]>([]);
  const [drawsLoading, setDrawsLoading] = useState(true);
  const [drawId, setDrawId] = useState<string>("");

  const [numberQ, setNumberQ] = useState("");
  const [appliedNumber, setAppliedNumber] = useState("");
  const [poolFilter, setPoolFilter] = useState<PoolFilter>("all");

  const [pools, setPools] = useState<AdminRiskPoolRow[]>([]);
  const [currencyCode, setCurrencyCode] = useState<string | null>(null);
  const [poolsLoading, setPoolsLoading] = useState(false);
  const [poolsError, setPoolsError] = useState<string | null>(null);

  const selectedDraw = useMemo(
    () => draws.find((d) => String(d.id) === drawId) ?? null,
    [draws, drawId],
  );

  const loadDraws = useCallback(async () => {
    setDrawsLoading(true);
    try {
      const data = await getAdminDraws({ page: 1, per_page: 50 });
      setDraws(data.items);
      if (data.items.length > 0) {
        setDrawId((prev) => (prev === "" ? String(data.items[0].id) : prev));
      }
    } catch (e) {
      toast.error(
        e instanceof LotteryApiBizError ? e.message : tRef.current("errors.loadFailed", { ns: "common" }),
      );
      setDraws([]);
    } finally {
      setDrawsLoading(false);
    }
  }, []);

  const loadPools = useCallback(async () => {
    if (!drawId) {
      setPools([]);
      return;
    }
    const id = Number(drawId);
    if (!Number.isFinite(id)) {
      return;
    }
    setPoolsLoading(true);
    setPoolsError(null);
    try {
      const data = await getAdminRiskPools(id, {
        page: 1,
        per_page: 200,
        normalized_number: appliedNumber.trim() || undefined,
        sold_out_only: poolFilter === "sold_out",
        high_risk_only: poolFilter === "high_risk",
        sort: poolFilter === "high_risk" ? "usage_desc" : "number_asc",
      });
      setPools(data.items);
      setCurrencyCode(data.currency_code);
    } catch (e) {
      setPoolsError(
        e instanceof LotteryApiBizError ? e.message : tRef.current("errors.loadFailed", { ns: "common" }),
      );
      setPools([]);
    } finally {
      setPoolsLoading(false);
    }
  }, [appliedNumber, drawId, poolFilter]);

  useAsyncEffect(() => {
    void loadDraws();
  }, []);

  useAsyncEffect(() => {
    void loadPools();
  }, [appliedNumber, drawId, poolFilter]);

  const riskBase = drawId ? `/admin/draws/${drawId}/risk` : null;

  return (
    <ConfigSection
      title={t("riskCap.runtime.title", { ns: "config" })}
      description={t("riskCap.runtime.description", { ns: "config" })}
    >
      <div className="flex flex-wrap items-end gap-3">
        <div className="grid min-w-[12rem] flex-1 gap-1.5">
          <Label htmlFor="risk-cap-draw">{t("riskCap.runtime.drawLabel", { ns: "config" })}</Label>
          <Select
            value={drawId}
            onValueChange={(v) => setDrawId(v == null ? "" : String(v))}
            disabled={drawsLoading || draws.length === 0}
          >
            <SelectTrigger id="risk-cap-draw" className="font-mono">
              <SelectValue>
                {(v) => {
                  if (v == null || v === "") {
                    return t("riskCap.runtime.drawPlaceholder", { ns: "config" });
                  }
                  const draw = draws.find((d) => String(d.id) === String(v));
                  return draw ? `${draw.draw_no} · ${draw.status}` : String(v);
                }}
              </SelectValue>
            </SelectTrigger>
            <SelectContent>
              {draws.map((d) => (
                <SelectItem key={d.id} value={String(d.id)}>
                  {d.draw_no} · {d.status}
                </SelectItem>
              ))}
            </SelectContent>
          </Select>
        </div>
        {riskBase ? (
          <div className="flex flex-wrap gap-2 pb-0.5">
            <Link href={`${riskBase}/pools`} className={cn(buttonVariants({ variant: "outline", size: "sm" }))}>
              {t("subnav.riskPools", { ns: "draws" })}
            </Link>
            <Link
              href={`${riskBase}/pools?filter=high_risk`}
              className={cn(buttonVariants({ variant: "outline", size: "sm" }))}
            >
              {t("filterHighRisk", { ns: "risk" })}
            </Link>
            <Link
              href={`${riskBase}/pools?filter=sold_out`}
              className={cn(buttonVariants({ variant: "outline", size: "sm" }))}
            >
              {t("filterSoldOut", { ns: "risk" })}
            </Link>
            <Link href={`${riskBase}/occupancy`} className={cn(buttonVariants({ variant: "outline", size: "sm" }))}>
              {t("subnav.riskLockLogs", { ns: "draws" })}
            </Link>
          </div>
        ) : null}
      </div>

      {drawId ? (
        <>
          <div className="flex flex-wrap items-end gap-3">
            <div className="grid gap-1.5">
              <Label htmlFor="risk-cap-number-q">{t("riskCap.occupancy.searchLabel", { ns: "config" })}</Label>
              <Input
                id="risk-cap-number-q"
                className="w-[140px] font-mono"
                placeholder={t("riskCap.occupancy.searchPlaceholder", { ns: "config" })}
                value={numberQ}
                onChange={(e) => setNumberQ(e.target.value)}
              />
            </div>
            <div className="flex flex-wrap gap-2">
              {(
                [
                  { id: "all", label: t("riskCap.runtime.filterAll", { ns: "config" }) },
                  { id: "sold_out", label: t("riskCap.runtime.filterSoldOut", { ns: "config" }) },
                  { id: "high_risk", label: t("riskCap.runtime.filterHighRisk", { ns: "config" }) },
                ] as const
              ).map((f) => (
                <Button
                  key={f.id}
                  type="button"
                  size="sm"
                  variant={poolFilter === f.id ? "default" : "outline"}
                  onClick={() => setPoolFilter(f.id)}
                >
                  {f.label}
                </Button>
              ))}
            </div>
            <Button
              type="button"
              size="sm"
              variant="secondary"
              onClick={() => {
                setAppliedNumber(numberQ.trim());
              }}
            >
              {t("actions.search", { ns: "common" })}
            </Button>
            <Button type="button" size="sm" variant="outline" disabled={poolsLoading} onClick={() => void loadPools()}>
              {t("versionActions.refresh", { ns: "config" })}
            </Button>
            {pools.length > 0 ? (
              <AdminTableExportButton
                tableId="risk-cap-runtime-pools"
                filename={`risk-pools-${selectedDraw?.draw_no ?? drawId}`}
              />
            ) : null}
          </div>

          {poolsError ? <p className="text-sm text-destructive">{poolsError}</p> : null}

          <div className="admin-table-shell">
            <Table id="risk-cap-runtime-pools">
              <TableHeader>
                <TableRow>
                  <TableHead>{t("riskCap.table.number", { ns: "config" })}</TableHead>
                  <TableHead className="text-center">{t("riskCap.table.used", { ns: "config" })}</TableHead>
                  <TableHead className="text-center">{t("riskCap.table.remaining", { ns: "config" })}</TableHead>
                  <TableHead className="text-center">{t("riskCap.table.ratio", { ns: "config" })}</TableHead>
                  <TableHead className="text-center">{t("riskCap.table.soldOut", { ns: "config" })}</TableHead>
                </TableRow>
              </TableHeader>
              <TableBody>
                {poolsLoading ? (
                  <AdminTableLoadingRow colSpan={5} />
                ) : pools.length === 0 ? (
                  <AdminTableNoResourceRow colSpan={5} className="text-muted-foreground" />
                ) : (
                  pools.map((row) => (
                    <TableRow
                      key={row.normalized_number}
                      className={cn(
                        row.is_sold_out && "bg-destructive/5",
                        !row.is_sold_out && (row.usage_ratio ?? 0) >= 0.8 && "bg-amber-500/10",
                      )}
                    >
                      <TableCell className="font-mono text-sm">{row.normalized_number}</TableCell>
                      <TableCell className="text-center text-xs tabular-nums">
                        {formatAdminMinorUnits(row.locked_amount, currencyCode ?? undefined)}
                      </TableCell>
                      <TableCell className="text-center text-xs tabular-nums">
                        {formatAdminMinorUnits(row.remaining_amount, currencyCode ?? undefined)}
                      </TableCell>
                      <TableCell className="text-center text-xs tabular-nums">
                        {row.usage_ratio != null ? `${Math.round(row.usage_ratio * 100)}%` : "—"}
                      </TableCell>
                      <TableCell className="text-center text-xs">
                        {row.is_sold_out
                          ? t("riskCap.runtime.soldYes", { ns: "config" })
                          : t("riskCap.runtime.soldNo", { ns: "config" })}
                      </TableCell>
                    </TableRow>
                  ))
                )}
              </TableBody>
            </Table>
          </div>
          <p className="text-xs text-muted-foreground">
            {t("riskCap.runtime.manageHint", { ns: "config" })}
          </p>
        </>
      ) : (
        <p className="text-sm text-muted-foreground">{t("riskCap.runtime.noDraws", { ns: "config" })}</p>
      )}
    </ConfigSection>
  );
}
