"use client";

import React, { useState, useEffect, useRef } from "react";
import { Input } from "@/components/ui/input";
import { Button } from "@/components/ui/button";
import { Search, X, Check, ChevronsUpDown } from "lucide-react";
import { EntitySearchModal } from "./EntitySearchModal";
import { EntitySearchInputProps, EntitySearchResult } from "./types";
import { cn } from "@/lib/utils";
import { Popover, PopoverContent, PopoverTrigger } from "@/components/ui/popover";
import { Command, CommandEmpty, CommandGroup, CommandInput, CommandItem, CommandList } from "@/components/ui/command";
import { dynamicFormApi } from "@/lib/api/dynamicForm";
import { cascadingRelationApi } from "@/lib/api/cascadingRelation";

export function EntitySearchInputComponent({
  tableName,
  displayField,
  valueField,
  searchFields = [displayField],
  mode: modeProp,
  uiMode, // EntityConfigPanel에서 저장되는 값
  placeholder = "검색...",
  disabled = false,
  filterCondition = {},
  value,
  onChange,
  modalTitle = "검색",
  modalColumns = [],
  showAdditionalInfo = false,
  additionalFields = [],
  className,
  style,
  // 연쇄관계 props
  cascadingRelationCode,
  parentValue: parentValueProp,
  parentFieldId,
  formData,
  // 🆕 추가 props
  component,
  isInteractive,
  onFormDataChange,
}: EntitySearchInputProps & {
  uiMode?: string;
  component?: any;
  isInteractive?: boolean;
  onFormDataChange?: (fieldName: string, value: any) => void;
  webTypeConfig?: any; // 웹타입 설정 (연쇄관계 등)
}) {
  // uiMode가 있으면 우선 사용, 없으면 modeProp 사용, 기본값 "combo"
  const mode = (uiMode || modeProp || "combo") as "select" | "modal" | "combo" | "autocomplete";

  // 연쇄관계 설정 추출 (webTypeConfig 또는 component.componentConfig에서)
  const config = component?.componentConfig || {};
  const effectiveCascadingRelationCode = cascadingRelationCode || config.cascadingRelationCode;
  // cascadingParentField: ConfigPanel에서 저장되는 필드명
  const effectiveParentFieldId = parentFieldId || config.cascadingParentField || config.parentFieldId;
  const effectiveCascadingRole = config.cascadingRole; // "parent" | "child" | undefined

  // 부모 역할이면 연쇄관계 로직 적용 안함 (자식만 부모 값에 따라 필터링됨)
  const isChildRole = effectiveCascadingRole === "child";
  const shouldApplyCascading = effectiveCascadingRelationCode && isChildRole;

  const [modalOpen, setModalOpen] = useState(false);
  const [selectOpen, setSelectOpen] = useState(false);
  const [displayValue, setDisplayValue] = useState("");
  const [selectedData, setSelectedData] = useState<EntitySearchResult | null>(null);
  const [options, setOptions] = useState<EntitySearchResult[]>([]);
  const [isLoadingOptions, setIsLoadingOptions] = useState(false);
  const [optionsLoaded, setOptionsLoaded] = useState(false);

  // 연쇄관계 상태
  const [cascadingOptions, setCascadingOptions] = useState<EntitySearchResult[]>([]);
  const [isCascadingLoading, setIsCascadingLoading] = useState(false);
  const previousParentValue = useRef<any>(null);

  // 부모 필드 값 결정 (직접 전달 또는 formData에서 추출) - 자식 역할일 때만 필요
  const parentValue = isChildRole
    ? (parentValueProp ?? (effectiveParentFieldId && formData ? formData[effectiveParentFieldId] : undefined))
    : undefined;

  // filterCondition을 문자열로 변환하여 비교 (객체 참조 문제 해결)
  const filterConditionKey = JSON.stringify(filterCondition || {});

  // 연쇄관계가 설정된 경우: 부모 값이 변경되면 자식 옵션 로드 (자식 역할일 때만)
  useEffect(() => {
    const loadCascadingOptions = async () => {
      if (!shouldApplyCascading) return;

      // 부모 값이 없으면 옵션 초기화
      if (!parentValue) {
        setCascadingOptions([]);
        // 부모 값이 변경되면 현재 값도 초기화
        if (previousParentValue.current !== null && previousParentValue.current !== parentValue) {
          handleClear();
        }
        previousParentValue.current = parentValue;
        return;
      }

      // 부모 값이 동일하면 스킵
      if (previousParentValue.current === parentValue) {
        return;
      }

      previousParentValue.current = parentValue;
      setIsCascadingLoading(true);

      try {
        console.log("🔗 연쇄관계 옵션 로드:", { effectiveCascadingRelationCode, parentValue });
        const response = await cascadingRelationApi.getOptions(effectiveCascadingRelationCode, String(parentValue));

        if (response.success && response.data) {
          // 옵션을 EntitySearchResult 형태로 변환
          const formattedOptions = response.data.map((opt: any) => ({
            [valueField]: opt.value,
            [displayField]: opt.label,
            ...opt, // 추가 필드도 포함
          }));
          setCascadingOptions(formattedOptions);
          console.log("✅ 연쇄관계 옵션 로드 완료:", formattedOptions.length, "개");

          // 현재 선택된 값이 새 옵션에 없으면 초기화
          if (value && !formattedOptions.find((opt: any) => opt[valueField] === value)) {
            handleClear();
          }
        } else {
          setCascadingOptions([]);
        }
      } catch (error) {
        console.error("❌ 연쇄관계 옵션 로드 실패:", error);
        setCascadingOptions([]);
      } finally {
        setIsCascadingLoading(false);
      }
    };

    loadCascadingOptions();
  }, [shouldApplyCascading, effectiveCascadingRelationCode, parentValue, valueField, displayField]);

  // select 모드일 때 옵션 로드 (연쇄관계가 없거나 부모 역할인 경우)
  useEffect(() => {
    if (mode === "select" && tableName && !optionsLoaded && !shouldApplyCascading) {
      loadOptions();
      setOptionsLoaded(true);
    }
  }, [mode, tableName, filterConditionKey, optionsLoaded, shouldApplyCascading]);

  const loadOptions = async () => {
    if (!tableName) return;

    setIsLoadingOptions(true);
    try {
      const response = await dynamicFormApi.getTableData(tableName, {
        page: 1,
        pageSize: 100, // 최대 100개까지 로드
        filters: filterCondition,
      });

      if (response.success && response.data) {
        setOptions(response.data);
      }
    } catch (error) {
      console.error("옵션 로드 실패:", error);
    } finally {
      setIsLoadingOptions(false);
    }
  };

  // 실제 사용할 옵션 목록 (자식 역할이고 연쇄관계가 있으면 연쇄 옵션 사용)
  const effectiveOptions = shouldApplyCascading ? cascadingOptions : options;
  const isLoading = shouldApplyCascading ? isCascadingLoading : isLoadingOptions;

  // value가 변경되면 표시값 업데이트 (외래키 값으로 데이터 조회)
  useEffect(() => {
    const loadDisplayValue = async () => {
      // value가 없으면 초기화
      if (!value) {
        setDisplayValue("");
        setSelectedData(null);
        return;
      }

      // 이미 selectedData가 있고 value와 일치하면 표시값만 업데이트
      if (selectedData && String(selectedData[valueField]) === String(value)) {
        setDisplayValue(selectedData[displayField] || "");
        return;
      }

      // select 모드에서 options가 로드된 경우 먼저 옵션에서 찾기
      if (mode === "select" && effectiveOptions.length > 0) {
        // 타입 변환하여 비교 (숫자 vs 문자열 문제 해결)
        const found = effectiveOptions.find((opt) => String(opt[valueField]) === String(value));
        if (found) {
          setSelectedData(found);
          setDisplayValue(found[displayField] || "");
          console.log("✅ [EntitySearchInput] 옵션에서 초기값 찾음:", { value, found });
          return;
        }
        // 옵션에서 찾지 못한 경우 API로 조회 진행
        console.log("⚠️ [EntitySearchInput] 옵션에서 찾지 못함, API로 조회:", {
          value,
          optionsCount: effectiveOptions.length,
        });
      }

      // API로 해당 데이터 조회
      if (tableName) {
        try {
          console.log("🔍 [EntitySearchInput] 초기값 조회:", { value, tableName, valueField });
          const response = await dynamicFormApi.getTableData(tableName, {
            filters: { [valueField]: value },
            pageSize: 1,
          });

          if (response.success && response.data) {
            // 데이터 추출 (중첩 구조 처리)
            const responseData = response.data as any;
            const dataArray = Array.isArray(responseData)
              ? responseData
              : responseData?.data
                ? Array.isArray(responseData.data)
                  ? responseData.data
                  : [responseData.data]
                : [];

            if (dataArray.length > 0) {
              const foundData = dataArray[0];
              setSelectedData(foundData);
              setDisplayValue(foundData[displayField] || "");
              console.log("✅ [EntitySearchInput] 초기값 로드 완료:", foundData);
            } else {
              // 데이터를 찾지 못한 경우 value 자체를 표시
              console.log("⚠️ [EntitySearchInput] 초기값 데이터 없음, value 표시:", value);
              setDisplayValue(String(value));
            }
          } else {
            console.log("⚠️ [EntitySearchInput] API 응답 실패, value 표시:", value);
            setDisplayValue(String(value));
          }
        } catch (error) {
          console.error("❌ [EntitySearchInput] 초기값 조회 실패:", error);
          // 에러 시 value 자체를 표시
          setDisplayValue(String(value));
        }
      }
    };

    loadDisplayValue();
  }, [value, displayField, effectiveOptions, mode, valueField, tableName, selectedData]);

  const handleSelect = (newValue: any, fullData: EntitySearchResult) => {
    setSelectedData(fullData);
    setDisplayValue(fullData[displayField] || "");
    onChange?.(newValue, fullData);

    // 🆕 onFormDataChange 호출 (formData에 값 저장)
    if (isInteractive && onFormDataChange && component?.columnName) {
      onFormDataChange(component.columnName, newValue);
      console.log("📤 EntitySearchInput -> onFormDataChange:", component.columnName, newValue);
    }
  };

  const handleClear = () => {
    setDisplayValue("");
    setSelectedData(null);
    onChange?.(null, null);

    // 🆕 onFormDataChange 호출 (formData에서 값 제거)
    if (isInteractive && onFormDataChange && component?.columnName) {
      onFormDataChange(component.columnName, null);
      console.log("📤 EntitySearchInput -> onFormDataChange (clear):", component.columnName, null);
    }
  };

  const handleOpenModal = () => {
    if (!disabled) {
      setModalOpen(true);
    }
  };

  const handleSelectOption = (option: EntitySearchResult) => {
    handleSelect(option[valueField], option);
    setSelectOpen(false);
  };

  // 높이 계산 (style에서 height가 있으면 사용, 없으면 기본값)
  const componentHeight = style?.height;
  const inputStyle: React.CSSProperties = componentHeight ? { height: componentHeight } : {};

  // select 모드: 검색 가능한 드롭다운
  if (mode === "select") {
    return (
      <div className={cn("relative flex flex-col", className)} style={style}>
        {/* 라벨 렌더링 */}
        {component?.label && component?.style?.labelDisplay !== false && (
          <label className="text-muted-foreground absolute -top-6 left-0 text-sm font-medium">
            {component.label}
            {component.required && <span className="text-destructive">*</span>}
          </label>
        )}
        <Popover open={selectOpen} onOpenChange={setSelectOpen}>
          <PopoverTrigger asChild>
            <Button
              variant="outline"
              role="combobox"
              aria-expanded={selectOpen}
              disabled={disabled || isLoading || Boolean(shouldApplyCascading && !parentValue)}
              className={cn(
                "w-full justify-between font-normal",
                !componentHeight && "h-8 text-xs sm:h-10 sm:text-sm",
                !value && "text-muted-foreground",
              )}
              style={inputStyle}
            >
              {isLoading
                ? "로딩 중..."
                : shouldApplyCascading && !parentValue
                  ? "상위 항목을 먼저 선택하세요"
                  : displayValue || placeholder}
              <ChevronsUpDown className="ml-2 h-4 w-4 shrink-0 opacity-50" />
            </Button>
          </PopoverTrigger>
          <PopoverContent className="p-0" style={{ width: "var(--radix-popover-trigger-width)" }} align="start">
            <Command>
              <CommandInput placeholder={`${displayField} 검색...`} className="text-xs sm:text-sm" />
              <CommandList>
                <CommandEmpty className="py-4 text-center text-xs sm:text-sm">항목을 찾을 수 없습니다.</CommandEmpty>
                <CommandGroup>
                  {effectiveOptions.map((option, index) => (
                    <CommandItem
                      key={option[valueField] || index}
                      value={`${option[displayField] || ""}-${option[valueField] || ""}`}
                      onSelect={() => handleSelectOption(option)}
                      className="text-xs sm:text-sm"
                    >
                      <Check
                        className={cn("mr-2 h-4 w-4", value === option[valueField] ? "opacity-100" : "opacity-0")}
                      />
                      <div className="flex flex-col">
                        <span className="font-medium">{option[displayField]}</span>
                        {valueField !== displayField && (
                          <span className="text-muted-foreground text-[10px]">{option[valueField]}</span>
                        )}
                      </div>
                    </CommandItem>
                  ))}
                </CommandGroup>
              </CommandList>
            </Command>
          </PopoverContent>
        </Popover>

        {/* 추가 정보 표시 */}
        {showAdditionalInfo && selectedData && additionalFields.length > 0 && (
          <div className="text-muted-foreground mt-1 space-y-1 px-2 text-xs">
            {additionalFields.map((field) => (
              <div key={field} className="flex gap-2">
                <span className="font-medium">{field}:</span>
                <span>{selectedData[field] || "-"}</span>
              </div>
            ))}
          </div>
        )}
      </div>
    );
  }

  // modal, combo, autocomplete 모드
  return (
    <div className={cn("relative flex flex-col", className)} style={style}>
      {/* 라벨 렌더링 */}
      {component?.label && component?.style?.labelDisplay !== false && (
        <label className="text-muted-foreground absolute -top-6 left-0 text-sm font-medium">
          {component.label}
          {component.required && <span className="text-destructive">*</span>}
        </label>
      )}
      {/* 입력 필드 */}
      <div className="flex h-full gap-2">
        <div className="relative flex-1">
          <Input
            value={displayValue}
            onChange={(e) => setDisplayValue(e.target.value)}
            placeholder={placeholder}
            disabled={disabled}
            readOnly={mode === "modal" || mode === "combo"}
            className={cn("w-full pr-8", !componentHeight && "h-8 text-xs sm:h-10 sm:text-sm")}
            style={inputStyle}
          />
          {displayValue && !disabled && (
            <Button
              type="button"
              variant="ghost"
              size="sm"
              onClick={handleClear}
              className="absolute top-1/2 right-1 h-6 w-6 -translate-y-1/2 p-0"
            >
              <X className="h-3 w-3" />
            </Button>
          )}
        </div>

        {/* 모달 버튼: modal 또는 combo 모드일 때만 표시 */}
        {(mode === "modal" || mode === "combo") && (
          <Button
            type="button"
            onClick={handleOpenModal}
            disabled={disabled}
            className={cn(!componentHeight && "h-8 text-xs sm:h-10 sm:text-sm")}
            style={inputStyle}
          >
            <Search className="h-4 w-4" />
          </Button>
        )}
      </div>

      {/* 추가 정보 표시 */}
      {showAdditionalInfo && selectedData && additionalFields.length > 0 && (
        <div className="text-muted-foreground mt-1 space-y-1 px-2 text-xs">
          {additionalFields.map((field) => (
            <div key={field} className="flex gap-2">
              <span className="font-medium">{field}:</span>
              <span>{selectedData[field] || "-"}</span>
            </div>
          ))}
        </div>
      )}

      {/* 검색 모달: modal 또는 combo 모드일 때만 렌더링 */}
      {(mode === "modal" || mode === "combo") && (
        <EntitySearchModal
          open={modalOpen}
          onOpenChange={setModalOpen}
          tableName={tableName}
          displayField={displayField}
          valueField={valueField}
          searchFields={searchFields}
          filterCondition={filterCondition}
          modalTitle={modalTitle}
          modalColumns={modalColumns}
          onSelect={handleSelect}
        />
      )}
    </div>
  );
}
