import { useEffect, useState } from 'react'
import { getContacts, type Contact, type ContactCategory } from '../api/client'

const FOOTER_NOTE = '담당자 등록·수정은 담당자관리 메뉴에서 합니다.'

/** 채널관리에서 담당자 3종(신청기관/문정원/변호사)을 배정할 때 여는 선택 모달.
 * 담당자 정보를 여기서 입력하지 않는다 - 등록/수정은 항상 담당자관리 화면에서만 한다. */
export default function ContactPickerModal({
  category,
  title,
  onSelect,
  onClose,
}: {
  category: ContactCategory
  title: string
  onSelect: (contact: Contact) => void
  onClose: () => void
}) {
  const [contacts, setContacts] = useState<Contact[]>([])
  const [loading, setLoading] = useState(true)
  const [keyword, setKeyword] = useState('')
  const [error, setError] = useState<string | null>(null)

  useEffect(() => {
    let cancelled = false
    setLoading(true)
    getContacts(category)
      .then((data) => {
        if (!cancelled) {
          setContacts(data)
        }
      })
      .catch((e) => {
        if (!cancelled) {
          setError(e instanceof Error ? e.message : '담당자 목록을 불러오지 못했습니다.')
        }
      })
      .finally(() => {
        if (!cancelled) {
          setLoading(false)
        }
      })
    return () => {
      cancelled = true
    }
  }, [category])

  useEffect(() => {
    function onKeyDown(e: KeyboardEvent) {
      if (e.key === 'Escape') {
        onClose()
      }
    }
    window.addEventListener('keydown', onKeyDown)
    return () => window.removeEventListener('keydown', onKeyDown)
  }, [onClose])

  const keywordTrimmed = keyword.trim()
  const visible = contacts.filter((c) => {
    if (keywordTrimmed === '') {
      return true
    }
    return c.name.includes(keywordTrimmed) || (c.affiliation ?? '').includes(keywordTrimmed)
  })

  return (
    <div className="fixed inset-0 flex items-center justify-center bg-black/30">
      <div className="w-[30rem] rounded-lg bg-white p-5">
        <div className="flex items-center justify-between">
          <h2 className="text-base font-semibold">{title}</h2>
          <button
            type="button"
            onClick={onClose}
            aria-label="닫기"
            className="rounded-md p-1 text-gray-400 hover:bg-gray-100"
          >
            ✕
          </button>
        </div>

        <input
          type="text"
          value={keyword}
          onChange={(e) => setKeyword(e.target.value)}
          placeholder="이름·소속으로 검색"
          aria-label="담당자 검색"
          className="mt-3 w-full rounded-md border border-gray-300 px-2.5 py-1.5 text-sm"
        />

        {error && <p className="mt-2 text-xs text-red-600">{error}</p>}

        <div className="mt-3 max-h-72 overflow-y-auto">
          {loading ? (
            <p className="py-6 text-center text-sm text-gray-400">불러오는 중…</p>
          ) : visible.length === 0 ? (
            <p className="py-6 text-center text-sm text-gray-300">등록된 담당자가 없습니다.</p>
          ) : (
            <ul className="divide-y divide-gray-100">
              {visible.map((contact) => (
                <li key={contact.id} className="flex items-center justify-between gap-3 py-2 text-sm">
                  <div>
                    <p className="font-medium text-gray-900">
                      {contact.name}
                      {contact.affiliation && (
                        <span className="ml-1 text-gray-500">· {contact.affiliation}</span>
                      )}
                    </p>
                    <p className="text-xs text-gray-400">
                      {[contact.deptName, contact.phone, contact.email].filter(Boolean).join(' · ') || '-'}
                    </p>
                  </div>
                  <button
                    type="button"
                    onClick={() => onSelect(contact)}
                    className="shrink-0 rounded-md border border-gray-300 px-2.5 py-1 text-xs text-gray-700 hover:bg-gray-50"
                  >
                    선택
                  </button>
                </li>
              ))}
            </ul>
          )}
        </div>

        <p className="mt-4 border-t border-gray-100 pt-3 text-xs text-gray-400">{FOOTER_NOTE}</p>
      </div>
    </div>
  )
}
