import { useState, useEffect, useCallback } from 'react';
import * as XLSX from 'xlsx';
import { fetchInsurance } from '../services/assetsApi';
import type { ShipInsuranceItem } from '../services/assetsApi';

const PAGE_SIZE = 50;

function ShipInsurance() {
  const [rows, setRows] = useState<ShipInsuranceItem[]>([]);
  const [total, setTotal] = useState(0);
  const [page, setPage] = useState(1);
  const [isLoading, setIsLoading] = useState(true);
  const [error, setError] = useState<string | null>(null);

  // 필터
  const [search, setSearch] = useState('');
  const [shipTpFilter, setShipTpFilter] = useState('');
  const [issueOrgFilter, setIssueOrgFilter] = useState('');

  const loadData = useCallback(
    async (p: number) => {
      setIsLoading(true);
      setError(null);
      try {
        const res = await fetchInsurance({
          search: search || undefined,
          shipTp: shipTpFilter || undefined,
          issueOrg: issueOrgFilter || undefined,
          page: p,
          limit: PAGE_SIZE,
        });
        setRows(res.rows);
        setTotal(res.total);
        setPage(p);
      } catch (err) {
        setError((err as { message?: string })?.message || '조회 실패');
      } finally {
        setIsLoading(false);
      }
    },
    [search, shipTpFilter, issueOrgFilter],
  );

  useEffect(() => {
    loadData(1);
  }, [loadData]);

  const totalPages = Math.ceil(total / PAGE_SIZE);

  const getStatus = (endDate: string) => {
    const now = new Date();
    const end = new Date(endDate);
    const daysLeft = Math.ceil((end.getTime() - now.getTime()) / (1000 * 60 * 60 * 24));
    if (end < now) return 'expired' as const;
    if (daysLeft <= 30) return 'soon' as const;
    return 'valid' as const;
  };

  const ynBadge = (yn: string) => {
    const isY = yn === 'Y';
    return (
      <span
        className="px-1.5 py-0.5 rounded text-caption font-bold"
        style={{
          background: isY
            ? 'color-mix(in srgb, var(--color-success) 15%, transparent)'
            : 'color-mix(in srgb, var(--stroke-default) 60%, transparent)',
          color: isY ? 'var(--color-success)' : 'var(--text-fg-disabled)',
        }}
      >
        {isY ? 'Y' : 'N'}
      </span>
    );
  };

  const handleSearch = () => loadData(1);
  const handleReset = () => {
    setSearch('');
    setShipTpFilter('');
    setIssueOrgFilter('');
  };

  const handleDownload = async () => {
    try {
      const all = await fetchInsurance({
        search: search || undefined,
        shipTp: shipTpFilter || undefined,
        issueOrg: issueOrgFilter || undefined,
        page: 1,
        limit: 200,
      });
      // 200건 초과 시 추가 페이지 로드
      let allRows = [...all.rows];
      const pages = Math.ceil(all.total / 200);
      for (let p = 2; p <= pages; p++) {
        const res = await fetchInsurance({
          search: search || undefined,
          shipTp: shipTpFilter || undefined,
          issueOrg: issueOrgFilter || undefined,
          page: p,
          limit: 200,
        });
        allRows = allRows.concat(res.rows);
      }

      const excelRows = allRows.map((r, i) => ({
        No: i + 1,
        선박명: r.shipNm,
        호출부호: r.callSign,
        IMO: r.imoNo,
        선박종류: r.shipTp,
        선박종류상세: r.shipTpDetail,
        선주: r.ownerNm,
        총톤수: r.grossTon ? Number(r.grossTon) : '',
        보험사: r.insurerNm,
        책임보험: r.liabilityYn,
        유류오염: r.oilPollutionYn,
        연료유오염: r.fuelOilYn,
        난파물제거: r.wreckRemovalYn,
        유효시작: r.validStart,
        유효종료: r.validEnd,
        발급기관: r.issueOrg,
      }));

      const ws = XLSX.utils.json_to_sheet(excelRows);
      const wb = XLSX.utils.book_new();
      XLSX.utils.book_append_sheet(wb, ws, '유류오염보장계약');
      XLSX.writeFile(wb, `유류오염보장계약_${new Date().toISOString().slice(0, 10)}.xlsx`);
    } catch {
      alert('다운로드 중 오류가 발생했습니다.');
    }
  };

  return (
    <div className="flex flex-col flex-1 overflow-auto">
      {/* 푸터 */}
      <div className="mt-auto px-4 py-3 border border-stroke rounded-sm mb-6">
        <div className="text-caption text-fg-disabled leading-[1.7]">
          <span className="text-fg-sub">데이터 출처:</span> 해양수산부 해운항만물류정보 ·
          유류오염보장계약관리 공공데이터
          <br />
          <span className="text-fg-sub">보장항목:</span> 책임보험, 유류오염, 연료유오염,
          난파물제거비용, 선원손해, 여객손해, 선체손해, 부두손상
        </div>
      </div>

      {/* 헤더 */}
      <div className="flex items-start justify-between mb-5">
        <div>
          <div className="flex items-center gap-2.5 mb-1">
            <div className="text-title-1 font-bold">유류오염보장계약 관리</div>
            <div
              className="flex items-center gap-1.5 px-2.5 py-0.5 rounded-full text-caption font-bold"
              style={{
                background:
                  total > 0
                    ? 'color-mix(in srgb, var(--color-success) 12%, transparent)'
                    : 'color-mix(in srgb, var(--color-danger) 12%, transparent)',
                color: total > 0 ? 'var(--color-success)' : 'var(--color-danger)',
                border: `1px solid ${total > 0 ? 'color-mix(in srgb, var(--color-success) 25%, transparent)' : 'color-mix(in srgb, var(--color-danger) 25%, transparent)'}`,
              }}
            >
              <span
                className="w-1.5 h-1.5 rounded-full inline-block"
                style={{ background: total > 0 ? 'var(--color-success)' : 'var(--color-danger)' }}
              />
              {total > 0 ? `${total.toLocaleString()}건` : '데이터 없음'}
            </div>
          </div>
          <div className="text-caption text-fg-disabled">
            해양수산부 해운항만물류정보 공공데이터 기반
          </div>
        </div>
        <div className="flex gap-2">
          <button
            onClick={() => window.open('https://www.haewoon.or.kr', '_blank', 'noopener')}
            className="px-4 py-2 text-label-2 font-bold cursor-pointer rounded-sm bg-[color-mix(in_srgb,var(--color-accent)_10%,transparent)] text-color-accent border border-[color-mix(in_srgb,var(--color-accent)_30%,transparent)]"
          >
            한국해운조합 API
          </button>
          <button
            onClick={() => window.open('https://new.portmis.go.kr', '_blank', 'noopener')}
            className="px-4 py-2 text-label-2 font-bold cursor-pointer rounded-sm bg-[color-mix(in_srgb,var(--color-accent)_10%,transparent)] text-color-accent border border-[color-mix(in_srgb,var(--color-accent)_30%,transparent)]"
          >
            PortMIS
          </button>
        </div>
      </div>

      {/* 필터 */}
      <div className="border border-stroke rounded-md px-5 py-4 mb-4">
        <div className="flex gap-2.5 items-end flex-wrap">
          <div className="flex-1 min-w-[200px]">
            <label className="block text-caption font-semibold text-fg-disabled mb-1">
              검색 (선박명/호출부호/IMO/선주)
            </label>
            <input
              type="text"
              value={search}
              onChange={(e) => setSearch(e.target.value)}
              onKeyDown={(e) => e.key === 'Enter' && handleSearch()}
              placeholder="선박명, 호출부호, IMO, 선주명"
              className="w-full px-3.5 py-2 bg-bg-base border border-stroke rounded-sm text-caption outline-none box-border"
            />
          </div>
          <div>
            <label className="block text-caption font-semibold text-fg-disabled mb-1">
              선박종류
            </label>
            <select
              value={shipTpFilter}
              onChange={(e) => setShipTpFilter(e.target.value)}
              className="prd-i min-w-[120px] border-stroke"
            >
              <option value="">전체</option>
              <option value="일반선박">일반선박</option>
              <option value="유조선">유조선</option>
            </select>
          </div>
          <div>
            <label className="block text-caption font-semibold text-fg-disabled mb-1">
              발급기관
            </label>
            <select
              value={issueOrgFilter}
              onChange={(e) => setIssueOrgFilter(e.target.value)}
              className="prd-i min-w-[160px] border-stroke"
            >
              <option value="">전체</option>
              <option>부산지방해양수산청</option>
              <option>인천지방해양수산청</option>
              <option>여수지방해양수산청</option>
              <option>울산지방해양수산청</option>
              <option>동해지방해양수산청</option>
              <option>목포지방해양수산청</option>
              <option>군산지방해양수산청</option>
              <option>마산지방해양수산청</option>
              <option>대산지방해양수산청</option>
              <option>평택지방해양수산청</option>
              <option>제주지방해양수산청</option>
              <option>포항지방해양수산청</option>
            </select>
          </div>
          <button
            onClick={handleSearch}
            className="px-4 py-2 bg-bg-base text-fg border border-stroke rounded-sm text-caption cursor-pointer"
          >
            조회
          </button>
          <button
            onClick={handleReset}
            className="px-4 py-2 bg-bg-base text-fg border border-stroke rounded-sm text-caption cursor-pointer"
          >
            초기화
          </button>
          <button
            onClick={handleDownload}
            disabled={total === 0}
            className="px-4 py-2 text-caption cursor-pointer rounded-sm disabled:opacity-30 disabled:cursor-default bg-bg-base border border-stroke"
          >
            엑셀 다운로드
          </button>
        </div>
      </div>

      {/* 로딩 */}
      {isLoading && (
        <div className="flex flex-col items-center justify-center p-16 bg-bg-card border border-stroke rounded-md">
          <div
            className="w-9 h-9 rounded-full mb-3.5"
            style={{
              border: '3px solid var(--stroke-default)',
              borderTopColor: 'var(--color-accent)',
              animation: 'spin 0.8s linear infinite',
            }}
          />
          <div className="text-title-4 text-fg-sub">보험 데이터 조회 중...</div>
        </div>
      )}

      {/* 에러 */}
      {error && !isLoading && (
        <div className="flex flex-col items-center justify-center py-16 px-5 bg-bg-card border border-stroke rounded-md">
          <div className="text-body-2 font-bold text-color-danger mb-2">조회 실패</div>
          <div className="text-caption text-fg-disabled">{error}</div>
        </div>
      )}

      {/* 테이블 */}
      {!isLoading && !error && (
        <>
          <div className="border border-stroke rounded-md overflow-hidden mb-3">
            <div className="flex items-center justify-between px-4 py-3 border-b border-stroke">
              <div className="text-caption font-bold">
                조회 결과 <span className="text-color-accent">{total.toLocaleString()}</span>건
                {totalPages > 1 && (
                  <span className="text-fg-disabled font-normal ml-2">
                    ({page}/{totalPages} 페이지)
                  </span>
                )}
              </div>
            </div>
            <div className="overflow-x-auto">
              <table className="w-full text-label-2 border-collapse whitespace-nowrap">
                <thead>
                  <tr className="bg-bg-base">
                    {[
                      'No',
                      '선박명',
                      '호출부호',
                      'IMO',
                      '선박종류',
                      '선주',
                      '총톤수',
                      '보험사',
                      '책임',
                      '유류',
                      '연료유',
                      '난파물',
                      '유효기간',
                      '발급기관',
                      '상태',
                    ].map((h, i) => (
                      <th
                        key={i}
                        className="px-3 py-2.5 font-bold text-fg-sub border-b border-stroke text-center"
                      >
                        {h}
                      </th>
                    ))}
                  </tr>
                </thead>
                <tbody>
                  {rows.map((r, i) => {
                    const st = getStatus(r.validEnd);
                    const isExp = st === 'expired';
                    const isSoon = st === 'soon';
                    const rowNum = (page - 1) * PAGE_SIZE + i + 1;
                    return (
                      <tr
                        key={r.insSn}
                        className="border-b border-stroke"
                        style={{
                          background: isExp
                            ? 'color-mix(in srgb, var(--color-danger) 3%, transparent)'
                            : undefined,
                        }}
                      >
                        <td className="px-3 py-2 text-center text-fg-disabled font-mono">
                          {rowNum}
                        </td>
                        <td className="px-3 py-2">{r.shipNm}</td>
                        <td className="px-3 py-2 text-center font-mono">{r.callSign || '—'}</td>
                        <td className="px-3 py-2 text-center font-mono">{r.imoNo || '—'}</td>
                        <td className="px-3 py-2 text-center">
                          <span className="text-caption">{r.shipTp}</span>
                          {r.shipTpDetail && (
                            <span className="text-fg-disabled text-caption ml-1">
                              ({r.shipTpDetail})
                            </span>
                          )}
                        </td>
                        <td className="px-3 py-2 max-w-[150px] truncate">{r.ownerNm}</td>
                        <td className="px-3 py-2 text-right font-mono">
                          {r.grossTon ? Number(r.grossTon).toLocaleString() : '—'}
                        </td>
                        <td className="px-3 py-2 max-w-[180px] truncate">{r.insurerNm}</td>
                        <td className="px-3 py-2 text-center">{ynBadge(r.liabilityYn)}</td>
                        <td className="px-3 py-2 text-center">{ynBadge(r.oilPollutionYn)}</td>
                        <td className="px-3 py-2 text-center">{ynBadge(r.fuelOilYn)}</td>
                        <td className="px-3 py-2 text-center">{ynBadge(r.wreckRemovalYn)}</td>
                        <td
                          className="px-3 py-2 text-center font-mono text-caption"
                          style={{
                            color: isExp
                              ? 'var(--color-danger)'
                              : isSoon
                                ? 'var(--color-caution)'
                                : undefined,
                          }}
                        >
                          {r.validStart} ~ {r.validEnd}
                        </td>
                        <td className="px-3 py-2 text-center text-caption">{r.issueOrg}</td>
                        <td className="px-3 py-2 text-center">
                          <span
                            className="px-2 py-0.5 rounded-full text-caption font-semibold"
                            style={{
                              background: isExp
                                ? 'color-mix(in srgb, var(--color-danger) 15%, transparent)'
                                : isSoon
                                  ? 'color-mix(in srgb, var(--color-caution) 15%, transparent)'
                                  : 'color-mix(in srgb, var(--color-success) 15%, transparent)',
                              color: isExp
                                ? 'var(--color-danger)'
                                : isSoon
                                  ? 'var(--color-caution)'
                                  : 'var(--color-success)',
                            }}
                          >
                            {isExp ? '만료' : isSoon ? '만료임박' : '유효'}
                          </span>
                        </td>
                      </tr>
                    );
                  })}
                </tbody>
              </table>
            </div>
          </div>

          {/* 페이지네이션 */}
          {totalPages > 1 && (
            <div className="flex items-center justify-center gap-1.5 mb-4">
              <button
                onClick={() => loadData(page - 1)}
                disabled={page <= 1}
                className="px-3 py-1.5 text-label-2 rounded-sm border border-stroke bg-bg-base cursor-pointer disabled:opacity-30 disabled:cursor-default"
              >
                이전
              </button>
              {Array.from({ length: Math.min(totalPages, 10) }, (_, i) => {
                const startPage = Math.max(1, Math.min(page - 4, totalPages - 9));
                const p = startPage + i;
                if (p > totalPages) return null;
                return (
                  <button
                    key={p}
                    onClick={() => loadData(p)}
                    className={`w-8 h-8 text-label-2 rounded-sm border cursor-pointer font-mono ${p === page ? 'bg-color-accent text-white border-color-accent font-bold' : 'bg-bg-base text-fg-sub border-stroke'}`}
                  >
                    {p}
                  </button>
                );
              })}
              <button
                onClick={() => loadData(page + 1)}
                disabled={page >= totalPages}
                className="px-3 py-1.5 text-label-2 rounded-sm border border-stroke bg-bg-base cursor-pointer disabled:opacity-30 disabled:cursor-default"
              >
                다음
              </button>
            </div>
          )}
        </>
      )}
    </div>
  );
}

export default ShipInsurance;
