"use client";

import { useState, useEffect } from "react";
import {
  Dialog,
  DialogContent,
  DialogHeader,
  DialogTitle,
  DialogDescription,
  DialogFooter,
} from "@/components/ui/dialog";
import { Button } from "@/components/ui/button";
import { Input } from "@/components/ui/input";
import { Label } from "@/components/ui/label";
import { Checkbox } from "@/components/ui/checkbox";
import { Loader2, Link2, Monitor, Folder, ChevronRight } from "lucide-react";
import { screenApi } from "@/lib/api/screen";
import { GroupCopyInfo } from "./PopCategoryTree";
import { getCompanyList } from "@/lib/api/company";
import { ScreenDefinition } from "@/types/screen";
import { Company } from "@/types/company";
import {
  Select,
  SelectContent,
  SelectItem,
  SelectTrigger,
  SelectValue,
} from "@/components/ui/select";
import { toast } from "sonner";

interface LinkedScreenInfo {
  screenId: number;
  screenName: string;
  screenCode: string;
  references: Array<{
    componentId: string;
    referenceType: string;
  }>;
  deploy: boolean;
  newScreenName: string;
  newScreenCode: string;
}

interface ScreenEntry {
  screenId: number;
  screenName: string;
  newScreenName: string;
  newScreenCode: string;
  included: boolean;
}

interface PopDeployModalProps {
  open: boolean;
  onOpenChange: (open: boolean) => void;
  screen: ScreenDefinition | null;
  groupScreens?: ScreenDefinition[];
  groupName?: string;
  groupInfo?: GroupCopyInfo;
  allScreens: ScreenDefinition[];
  onDeployed?: () => void;
}

export function PopDeployModal({
  open,
  onOpenChange,
  screen,
  groupScreens,
  groupName,
  groupInfo,
  allScreens,
  onDeployed,
}: PopDeployModalProps) {
  const isGroupMode = !!(groupScreens && groupScreens.length > 0);

  const [companies, setCompanies] = useState<Company[]>([]);
  const [targetCompanyCode, setTargetCompanyCode] = useState("");

  // 단일 화면 모드
  const [screenName, setScreenName] = useState("");
  const [screenCode, setScreenCode] = useState("");
  const [linkedScreens, setLinkedScreens] = useState<LinkedScreenInfo[]>([]);

  // 그룹 모드
  const [groupEntries, setGroupEntries] = useState<ScreenEntry[]>([]);

  const [analyzing, setAnalyzing] = useState(false);
  const [deploying, setDeploying] = useState(false);

  // 회사 목록 로드
  useEffect(() => {
    if (open) {
      getCompanyList({ status: "active" })
        .then((list) => {
          setCompanies(list.filter((c) => c.company_code !== "*"));
        })
        .catch(console.error);
    }
  }, [open]);

  // 모달 열릴 때 초기화
  useEffect(() => {
    if (!open) return;

    setTargetCompanyCode("");
    setLinkedScreens([]);

    if (isGroupMode && groupScreens) {
      setGroupEntries(
        groupScreens.map((s) => ({
          screenId: s.screenId,
          screenName: s.screenName,
          newScreenName: s.screenName,
          newScreenCode: "",
          included: true,
        })),
      );
      setScreenName("");
      setScreenCode("");
    } else if (screen) {
      setScreenName(screen.screenName);
      setScreenCode("");
      setGroupEntries([]);
      analyzeLinks(screen.screenId);
    }
  }, [open, screen, groupScreens, isGroupMode]);

  // 회사 선택 시 화면 코드 자동 생성
  useEffect(() => {
    if (!targetCompanyCode) return;

    if (isGroupMode) {
      const count = groupEntries.filter((e) => e.included).length;
      if (count > 0) {
        screenApi
          .generateMultipleScreenCodes(targetCompanyCode, count)
          .then((codes) => {
            let codeIdx = 0;
            setGroupEntries((prev) =>
              prev.map((e) =>
                e.included
                  ? { ...e, newScreenCode: codes[codeIdx++] || "" }
                  : e,
              ),
            );
          })
          .catch(console.error);
      }
    } else {
      const count = 1 + linkedScreens.filter((ls) => ls.deploy).length;
      screenApi
        .generateMultipleScreenCodes(targetCompanyCode, count)
        .then((codes) => {
          setScreenCode(codes[0] || "");
          setLinkedScreens((prev) =>
            prev.map((ls, idx) => ({
              ...ls,
              newScreenCode: codes[idx + 1] || "",
            })),
          );
        })
        .catch(console.error);
    }
  }, [targetCompanyCode]);

  const analyzeLinks = async (screenId: number) => {
    setAnalyzing(true);
    try {
      const result = await screenApi.analyzePopScreenLinks(screenId);
      const linked: LinkedScreenInfo[] = result.linkedScreenIds.map(
        (linkedId) => {
          const linkedScreen = allScreens.find(
            (s) => s.screenId === linkedId,
          );
          const refs = result.references.filter(
            (r) => r.targetScreenId === linkedId,
          );
          return {
            screenId: linkedId,
            screenName: linkedScreen?.screenName || `화면 ${linkedId}`,
            screenCode: linkedScreen?.screenCode || "",
            references: refs.map((r) => ({
              componentId: r.componentId,
              referenceType: r.referenceType,
            })),
            deploy: true,
            newScreenName: linkedScreen?.screenName || `화면 ${linkedId}`,
            newScreenCode: "",
          };
        },
      );
      setLinkedScreens(linked);
    } catch (error) {
      console.error("연결 분석 실패:", error);
    } finally {
      setAnalyzing(false);
    }
  };

  const handleDeploy = async () => {
    if (!targetCompanyCode) return;

    setDeploying(true);
    try {
      let screensToSend: Array<{
        sourceScreenId: number;
        screenName: string;
        screenCode: string;
      }>;

      if (isGroupMode) {
        screensToSend = groupEntries
          .filter((e) => e.included && e.newScreenCode)
          .map((e) => ({
            sourceScreenId: e.screenId,
            screenName: e.newScreenName,
            screenCode: e.newScreenCode,
          }));
      } else {
        if (!screen || !screenName || !screenCode) return;
        screensToSend = [
          {
            sourceScreenId: screen.screenId,
            screenName,
            screenCode,
          },
          ...linkedScreens
            .filter((ls) => ls.deploy)
            .map((ls) => ({
              sourceScreenId: ls.screenId,
              screenName: ls.newScreenName,
              screenCode: ls.newScreenCode,
            })),
        ];
      }

      if (screensToSend.length === 0) {
        toast.error("복사할 화면이 없습니다.");
        return;
      }

      const deployPayload: Parameters<typeof screenApi.deployPopScreens>[0] = {
        screens: screensToSend,
        targetCompanyCode,
      };

      if (isGroupMode && groupInfo) {
        deployPayload.groupStructure = groupInfo;
      }

      const result = await screenApi.deployPopScreens(deployPayload);

      const groupMsg = result.createdGroups
        ? ` (카테고리 ${result.createdGroups}개 생성)`
        : "";
      toast.success(
        `POP 화면 ${result.deployedScreens.length}개가 복사되었습니다.${groupMsg}`,
      );
      onOpenChange(false);
      onDeployed?.();
    } catch (error: any) {
      toast.error(error?.response?.data?.message || "복사에 실패했습니다.");
    } finally {
      setDeploying(false);
    }
  };

  const totalCount = isGroupMode
    ? groupEntries.filter((e) => e.included).length
    : 1 + linkedScreens.filter((ls) => ls.deploy).length;

  const canDeploy = isGroupMode
    ? !deploying && targetCompanyCode && groupEntries.some((e) => e.included)
    : !deploying && targetCompanyCode && screenName && screenCode;

  return (
    <Dialog open={open} onOpenChange={onOpenChange}>
      <DialogContent className="max-w-[95vw] sm:max-w-[560px]">
        <DialogHeader>
          <DialogTitle className="text-base sm:text-lg">
            POP 화면 복사
          </DialogTitle>
          <DialogDescription className="text-xs sm:text-sm">
            {isGroupMode
              ? `"${groupName}" 카테고리의 화면 ${groupScreens!.length}개를 다른 회사로 복사합니다.`
              : screen
                ? `"${screen.screenName}" (ID: ${screen.screenId}) 화면을 다른 회사로 복사합니다.`
                : "화면을 선택해주세요."}
          </DialogDescription>
        </DialogHeader>

        <div className="space-y-3 sm:space-y-4">
          {/* 대상 회사 선택 */}
          <div>
            <Label className="text-xs sm:text-sm">
              대상 회사 <span className="text-destructive">*</span>
            </Label>
            <Select
              value={targetCompanyCode}
              onValueChange={setTargetCompanyCode}
            >
              <SelectTrigger className="mt-1 h-8 text-xs sm:h-10 sm:text-sm">
                <SelectValue placeholder="회사를 선택하세요" />
              </SelectTrigger>
              <SelectContent>
                {companies.map((c) => (
                  <SelectItem
                    key={c.company_code}
                    value={c.company_code}
                    className="text-xs sm:text-sm"
                  >
                    {c.company_name} ({c.company_code})
                  </SelectItem>
                ))}
              </SelectContent>
            </Select>
          </div>

          {/* ===== 그룹 모드: 카테고리 구조 + 화면 목록 ===== */}
          {isGroupMode ? (
            <div>
              <Label className="text-xs sm:text-sm">
                복사 구조 ({groupEntries.filter((e) => e.included).length}개
                화면
                {groupInfo
                  ? ` + ${1 + (groupInfo.children?.length || 0)}개 카테고리`
                  : ""}
                )
              </Label>
              <div className="mt-1 max-h-[280px] overflow-y-auto rounded-md border p-2">
                {groupInfo ? (
                  <div className="space-y-0.5">
                    {/* 메인 카테고리 */}
                    <div className="flex items-center gap-1.5 rounded bg-muted/50 p-1.5 text-xs font-medium">
                      <Folder className="h-3.5 w-3.5 shrink-0 text-amber-500" />
                      <span>{groupInfo.groupName}</span>
                      <ChevronRight className="h-3 w-3 text-muted-foreground" />
                      <span className="text-muted-foreground">
                        새 카테고리 생성
                      </span>
                    </div>
                    {/* 메인 카테고리의 직접 화면 */}
                    {groupEntries
                      .filter((e) => groupInfo.screenIds.includes(e.screenId))
                      .map((entry) => (
                        <div
                          key={entry.screenId}
                          className="flex items-center gap-2 rounded p-1.5 pl-6 text-xs hover:bg-muted/50"
                        >
                          <Checkbox
                            checked={entry.included}
                            onCheckedChange={(checked) => {
                              setGroupEntries((prev) =>
                                prev.map((e) =>
                                  e.screenId === entry.screenId
                                    ? { ...e, included: !!checked }
                                    : e,
                                ),
                              );
                            }}
                          />
                          <Monitor className="h-3.5 w-3.5 shrink-0 text-blue-500" />
                          <span className="flex-1 truncate">
                            {entry.screenName}
                          </span>
                          <span className="shrink-0 text-muted-foreground">
                            #{entry.screenId}
                          </span>
                        </div>
                      ))}
                    {/* 하위 카테고리들 */}
                    {groupInfo.children?.map((child) => (
                      <div key={child.sourceGroupId}>
                        <div className="mt-1 flex items-center gap-1.5 rounded bg-muted/30 p-1.5 pl-4 text-xs font-medium">
                          <Folder className="h-3.5 w-3.5 shrink-0 text-amber-400" />
                          <span>{child.groupName}</span>
                        </div>
                        {groupEntries
                          .filter((e) =>
                            child.screenIds.includes(e.screenId),
                          )
                          .map((entry) => (
                            <div
                              key={entry.screenId}
                              className="flex items-center gap-2 rounded p-1.5 pl-10 text-xs hover:bg-muted/50"
                            >
                              <Checkbox
                                checked={entry.included}
                                onCheckedChange={(checked) => {
                                  setGroupEntries((prev) =>
                                    prev.map((e) =>
                                      e.screenId === entry.screenId
                                        ? { ...e, included: !!checked }
                                        : e,
                                    ),
                                  );
                                }}
                              />
                              <Monitor className="h-3.5 w-3.5 shrink-0 text-blue-500" />
                              <span className="flex-1 truncate">
                                {entry.screenName}
                              </span>
                              <span className="shrink-0 text-muted-foreground">
                                #{entry.screenId}
                              </span>
                            </div>
                          ))}
                      </div>
                    ))}
                  </div>
                ) : (
                  <div className="space-y-1">
                    {groupEntries.map((entry) => (
                      <div
                        key={entry.screenId}
                        className="flex items-center gap-2 rounded p-1.5 text-xs hover:bg-muted/50"
                      >
                        <Checkbox
                          checked={entry.included}
                          onCheckedChange={(checked) => {
                            setGroupEntries((prev) =>
                              prev.map((e) =>
                                e.screenId === entry.screenId
                                  ? { ...e, included: !!checked }
                                  : e,
                              ),
                            );
                          }}
                        />
                        <Monitor className="h-3.5 w-3.5 shrink-0 text-muted-foreground" />
                        <span className="flex-1 truncate">
                          {entry.screenName}
                        </span>
                        <span className="shrink-0 text-muted-foreground">
                          #{entry.screenId}
                        </span>
                      </div>
                    ))}
                  </div>
                )}
              </div>
              <p className="mt-1 text-[10px] text-muted-foreground sm:text-xs">
                카테고리 구조와 화면 간 연결(cartScreenId 등)이 자동으로
                복사됩니다.
              </p>
            </div>
          ) : (
            <>
              {/* ===== 단일 모드: 화면명 + 코드 ===== */}
              <div>
                <Label className="text-xs sm:text-sm">
                  새 화면명 <span className="text-destructive">*</span>
                </Label>
                <Input
                  className="mt-1 h-8 text-xs sm:h-10 sm:text-sm"
                  value={screenName}
                  onChange={(e) => setScreenName(e.target.value)}
                  placeholder="화면 이름"
                />
              </div>

              <div>
                <Label className="text-xs sm:text-sm">
                  화면 코드 (자동생성)
                </Label>
                <Input
                  className="mt-1 h-8 bg-muted text-xs sm:h-10 sm:text-sm"
                  value={screenCode}
                  readOnly
                />
              </div>

              {/* 연결 화면 감지 */}
              {analyzing ? (
                <div className="flex items-center gap-2 rounded-md border p-3 text-xs text-muted-foreground sm:text-sm">
                  <Loader2 className="h-4 w-4 animate-spin" />
                  연결된 화면을 분석 중입니다...
                </div>
              ) : linkedScreens.length > 0 ? (
                <div className="rounded-md border border-amber-300 bg-amber-50 p-3 dark:border-amber-700 dark:bg-amber-950/30">
                  <div className="mb-2 flex items-center gap-1.5 text-xs font-semibold text-amber-800 dark:text-amber-300 sm:text-sm">
                    <Link2 className="h-3.5 w-3.5" />
                    연결된 POP 화면 {linkedScreens.length}개 감지됨
                  </div>
                  <div className="space-y-1.5">
                    {linkedScreens.map((ls) => (
                      <div
                        key={ls.screenId}
                        className="flex items-center justify-between rounded bg-background p-2 text-xs"
                      >
                        <div className="flex-1">
                          <div className="font-medium">{ls.screenName}</div>
                          <div className="text-muted-foreground">
                            ID: {ls.screenId} |{" "}
                            {ls.references
                              .map((r) => r.referenceType)
                              .join(", ")}
                          </div>
                        </div>
                        <div className="flex items-center gap-1.5">
                          <Checkbox
                            checked={ls.deploy}
                            onCheckedChange={(checked) => {
                              setLinkedScreens((prev) =>
                                prev.map((item) =>
                                  item.screenId === ls.screenId
                                    ? { ...item, deploy: !!checked }
                                    : item,
                                ),
                              );
                            }}
                          />
                          <span className="text-xs">함께 복사</span>
                        </div>
                      </div>
                    ))}
                  </div>
                  <p className="mt-2 text-[10px] text-amber-700 dark:text-amber-400 sm:text-xs">
                    함께 복사하면 화면 간 연결(cartScreenId 등)이 새 ID로 자동
                    치환됩니다.
                  </p>
                </div>
              ) : (
                !analyzing && (
                  <div className="rounded-md border bg-muted/30 p-3 text-xs text-muted-foreground sm:text-sm">
                    연결된 POP 화면이 없습니다. 이 화면만 복사됩니다.
                  </div>
                )
              )}
            </>
          )}
        </div>

        <DialogFooter className="gap-2 sm:gap-0">
          <Button
            variant="outline"
            onClick={() => onOpenChange(false)}
            className="h-8 flex-1 text-xs sm:h-10 sm:flex-none sm:text-sm"
            disabled={deploying}
          >
            취소
          </Button>
          <Button
            onClick={handleDeploy}
            disabled={!canDeploy}
            className="h-8 flex-1 text-xs sm:h-10 sm:flex-none sm:text-sm"
          >
            {deploying ? (
              <>
                <Loader2 className="mr-2 h-4 w-4 animate-spin" />
                복사 중...
              </>
            ) : (
              `${totalCount}개 화면 복사`
            )}
          </Button>
        </DialogFooter>
      </DialogContent>
    </Dialog>
  );
}
