/**
 * 운송 통계 위젯
 * - 총 운송량 (톤)
 * - 누적 거리 (km)
 * - 정시 도착률 (%)
 * - 쿼리 결과 기반 통계 계산
 */

"use client";

import { useState, useEffect } from "react";
import { DashboardElement } from "@/components/admin/dashboard/types";

interface TransportStatsWidgetProps {
  element?: DashboardElement;
  refreshInterval?: number;
}

interface StatItem {
  label: string;
  value: number;
  unit: string;
  color: string;
  icon?: string;
}

interface StatsData {
  total_count: number;
  total_weight: number;
  total_distance: number;
  on_time_rate: number;
  avg_delivery_time: number;
  [key: string]: number; // 동적 속성 추가
}

export default function TransportStatsWidget({ element, refreshInterval = 60000 }: TransportStatsWidgetProps) {
  const [stats, setStats] = useState<StatItem[]>([]);
  const [isLoading, setIsLoading] = useState(true);
  const [error, setError] = useState<string | null>(null);

  // 데이터 로드
  const loadData = async () => {
    try {
      setIsLoading(true);
      setError(null);

      // 쿼리가 설정되어 있지 않으면 안내 메시지만 표시
      if (!element?.dataSource?.query) {
        setError("쿼리를 설정해주세요");
        setIsLoading(false);
        return;
      }

      // 쿼리 실행하여 통계 계산
      const token = localStorage.getItem("authToken");
      const response = await fetch("/api/dashboards/execute-query", {
        method: "POST",
        headers: {
          "Content-Type": "application/json",
          Authorization: `Bearer ${token}`,
        },
        body: JSON.stringify({
          query: element.dataSource.query,
          connectionType: element.dataSource.connectionType || "current",
          externalConnectionId: element.dataSource.externalConnectionId,
        }),
      });

      if (!response.ok) throw new Error("데이터 로딩 실패");

      const result = await response.json();

      if (!result.success || !result.data?.rows) {
        throw new Error(result.message || "데이터 로드 실패");
      }

      const data = result.data.rows || [];

      if (data.length === 0) {
        setStats({ total_count: 0, total_weight: 0, total_distance: 0, on_time_rate: 0, avg_delivery_time: 0 });
        return;
      }

      // 자동으로 숫자 컬럼 감지 및 합계 계산
      const firstRow = data[0];
      const numericColumns: { [key: string]: number } = {};

      // 모든 컬럼을 순회하며 숫자 컬럼 찾기
      Object.keys(firstRow).forEach((key) => {
        const value = firstRow[key];
        // 숫자로 변환 가능한 컬럼만 선택
        if (value !== null && !isNaN(parseFloat(value))) {
          numericColumns[key] = data.reduce((sum: number, item: any) => {
            return sum + (parseFloat(item[key]) || 0);
          }, 0);
        }
      });

      // 특정 키워드를 포함한 컬럼 자동 매핑
      const weightKeys = ["weight", "cargo_weight", "total_weight", "중량", "무게"];
      const distanceKeys = ["distance", "total_distance", "거리", "주행거리"];
      const onTimeKeys = ["is_on_time", "on_time", "onTime", "정시", "정시도착"];
      const deliveryTimeKeys = [
        "delivery_duration",
        "delivery_time",
        "duration",
        "배송시간",
        "소요시간",
        "배송소요시간",
      ];

      // 총 운송량 찾기
      let total_weight = 0;
      for (const key of Object.keys(numericColumns)) {
        if (weightKeys.some((keyword) => key.toLowerCase().includes(keyword.toLowerCase()))) {
          total_weight = numericColumns[key];
          break;
        }
      }

      // 누적 거리 찾기
      let total_distance = 0;
      for (const key of Object.keys(numericColumns)) {
        if (distanceKeys.some((keyword) => key.toLowerCase().includes(keyword.toLowerCase()))) {
          total_distance = numericColumns[key];
          break;
        }
      }

      // 정시 도착률 계산
      let on_time_rate = 0;
      for (const key of Object.keys(firstRow)) {
        if (onTimeKeys.some((keyword) => key.toLowerCase().includes(keyword.toLowerCase()))) {
          const onTimeItems = data.filter((item: any) => {
            const onTime = item[key];
            return onTime !== null && onTime !== undefined;
          });

          if (onTimeItems.length > 0) {
            const onTimeCount = onTimeItems.filter((item: any) => {
              const onTime = item[key];
              return onTime === true || onTime === "true" || onTime === 1 || onTime === "1";
            }).length;

            on_time_rate = (onTimeCount / onTimeItems.length) * 100;
          }
          break;
        }
      }

      // 평균 배송시간 계산
      let avg_delivery_time = 0;

      // 1. 먼저 배송시간 컬럼이 있는지 확인
      let foundTimeColumn = false;
      for (const key of Object.keys(numericColumns)) {
        if (deliveryTimeKeys.some((keyword) => key.toLowerCase().includes(keyword.toLowerCase()))) {
          const validItems = data.filter((item: any) => {
            const time = parseFloat(item[key]);
            return !isNaN(time) && time > 0;
          });

          if (validItems.length > 0) {
            const totalTime = validItems.reduce((sum: number, item: any) => {
              return sum + parseFloat(item[key]);
            }, 0);
            avg_delivery_time = totalTime / validItems.length;
            foundTimeColumn = true;
          }
          break;
        }
      }

      // 2. 배송시간 컬럼이 없으면 날짜 컬럼에서 자동 계산
      if (!foundTimeColumn) {
        const startTimeKeys = ["created_at", "start_time", "departure_time", "출발시간", "시작시간"];
        const endTimeKeys = [
          "actual_delivery",
          "end_time",
          "arrival_time",
          "도착시간",
          "완료시간",
          "estimated_delivery",
        ];

        let startKey = null;
        let endKey = null;

        // 시작 시간 컬럼 찾기
        for (const key of Object.keys(firstRow)) {
          if (startTimeKeys.some((keyword) => key.toLowerCase().includes(keyword.toLowerCase()))) {
            startKey = key;
            break;
          }
        }

        // 종료 시간 컬럼 찾기
        for (const key of Object.keys(firstRow)) {
          if (endTimeKeys.some((keyword) => key.toLowerCase().includes(keyword.toLowerCase()))) {
            endKey = key;
            break;
          }
        }

        // 두 컬럼이 모두 있으면 시간 차이 계산
        if (startKey && endKey) {
          const validItems = data.filter((item: any) => {
            return item[startKey] && item[endKey];
          });

          if (validItems.length > 0) {
            const totalMinutes = validItems.reduce((sum: number, item: any) => {
              const start = new Date(item[startKey]).getTime();
              const end = new Date(item[endKey]).getTime();
              const diffMinutes = (end - start) / (1000 * 60); // 밀리초 -> 분
              return sum + (diffMinutes > 0 ? diffMinutes : 0);
            }, 0);
            avg_delivery_time = totalMinutes / validItems.length;
          }
        }
      }

      const calculatedStats: StatsData = {
        total_count: data.length, // 총 건수
        total_weight,
        total_distance,
        on_time_rate,
        avg_delivery_time,
      };

      setStats(calculatedStats);
    } catch (err) {
      console.error("통계 로드 실패:", err);
      setError(err instanceof Error ? err.message : "데이터를 불러올 수 없습니다");
    } finally {
      setIsLoading(false);
    }
  };

  useEffect(() => {
    loadData();
    const interval = setInterval(loadData, refreshInterval);
    return () => clearInterval(interval);
    // eslint-disable-next-line react-hooks/exhaustive-deps
  }, [refreshInterval, element?.dataSource]);

  if (isLoading && !stats) {
    return (
      <div className="flex h-full items-center justify-center bg-gray-50">
        <div className="text-center">
          <div className="mx-auto h-8 w-8 animate-spin rounded-full border-4 border-blue-500 border-t-transparent" />
          <div className="mt-2 text-sm text-gray-600">로딩 중...</div>
        </div>
      </div>
    );
  }

  if (error || !stats) {
    return (
      <div className="flex h-full items-center justify-center bg-gray-50 p-4">
        <div className="text-center">
          <div className="mb-2 text-4xl">⚠️</div>
          <div className="text-sm font-medium text-gray-600">{error || "데이터 없음"}</div>
          {!element?.dataSource?.query && <div className="mt-2 text-xs text-gray-500">쿼리를 설정하세요</div>}
          <button
            onClick={loadData}
            className="mt-3 rounded-lg bg-blue-500 px-4 py-2 text-sm text-white hover:bg-blue-600"
          >
            다시 시도
          </button>
        </div>
      </div>
    );
  }

  return (
    <div className="flex h-full items-center justify-center bg-white p-6">
      <div className="grid w-full gap-4" style={{ gridTemplateColumns: "repeat(auto-fit, minmax(180px, 1fr))" }}>
        {/* 총 건수 */}
        <div className="rounded-lg border bg-indigo-50 p-4 text-center">
          <div className="text-sm text-gray-600">총 건수</div>
          <div className="mt-2 text-3xl font-bold text-indigo-600">
            {stats.total_count.toLocaleString()}
            <span className="ml-1 text-lg">건</span>
          </div>
        </div>

        {/* 총 운송량 */}
        <div className="rounded-lg border bg-green-50 p-4 text-center">
          <div className="text-sm text-gray-600">총 운송량</div>
          <div className="mt-2 text-3xl font-bold text-green-600">
            {stats.total_weight.toFixed(1)}
            <span className="ml-1 text-lg">톤</span>
          </div>
        </div>

        {/* 누적 거리 */}
        <div className="rounded-lg border bg-blue-50 p-4 text-center">
          <div className="text-sm text-gray-600">누적 거리</div>
          <div className="mt-2 text-3xl font-bold text-blue-600">
            {stats.total_distance.toFixed(1)}
            <span className="ml-1 text-lg">km</span>
          </div>
        </div>

        {/* 정시 도착률 */}
        <div className="rounded-lg border bg-purple-50 p-4 text-center">
          <div className="text-sm text-gray-600">정시 도착률</div>
          <div className="mt-2 text-3xl font-bold text-purple-600">
            {stats.on_time_rate.toFixed(1)}
            <span className="ml-1 text-lg">%</span>
          </div>
        </div>

        {/* 평균 배송시간 */}
        <div className="rounded-lg border bg-orange-50 p-4 text-center">
          <div className="text-sm text-gray-600">평균 배송시간</div>
          <div className="mt-2 text-3xl font-bold text-orange-600">
            {stats.avg_delivery_time.toFixed(1)}
            <span className="ml-1 text-lg">분</span>
          </div>
        </div>
      </div>
    </div>
  );
}
