import { useState, useEffect } from 'react';
import { createPortal } from 'react-dom';
import { useQuery, useMutation, useQueryClient } from '@tanstack/react-query';
import { useDroppable } from '@dnd-kit/core';
import { apiClient, getApiErrorMessage } from '../../lib/apiClient';
import { isProjectTask } from '../../lib/taskType';
import { type BoardSlotConfig, slotSectionLabel, columnDisplayTitle, columnDisplayTitleEn } from '../../lib/boardLayout';
import { SortableTaskCard } from './TaskCard';
import { DeptIcon } from './DeptIcon';
import { DeptProjectList } from './DeptProjectList';
import { ContextMenu } from '../common/ContextMenu';
import { TaskModal } from '../common/TaskModal';
import type { TaskFormData } from '../../lib/taskFormState';
import { projectFormToApiPayload } from '../../lib/taskFormPayload';
import { invalidateTaskCaches } from '../../lib/taskQueryCache';
import type { Task, TeamMember } from '../../types';

const DUMMY_HEADER_KEY = 'eene-board-slot-headers-v1';
/** 참고 레이아웃: 부서당 표시 슬롯 수 (2행 + 스크롤) */

type DummyHeaders = Record<string, { title: string; titleEn: string; subtitle: string }>;

function loadDummyHeaders(): DummyHeaders {
  try {
    const raw = localStorage.getItem(DUMMY_HEADER_KEY);
    return raw ? JSON.parse(raw) : {};
  } catch {
    return {};
  }
}

function saveDummyHeader(slotId: string, data: { title: string; titleEn: string; subtitle: string }) {
  const all = loadDummyHeaders();
  all[slotId] = data;
  localStorage.setItem(DUMMY_HEADER_KEY, JSON.stringify(all));
}

interface DepartmentColumnProps {
  slot: BoardSlotConfig;
  tasks: Task[];
  orderedIds: string[];
  quarter: string;
  referenceWeekMonday?: Date;
  onSelectTask?: (task: Task) => void;
  sectionOptions?: { value: string; label: string }[];
  teamMembers?: TeamMember[];
}

interface HeaderModalProps {
  title: string;
  titleEn: string;
  subtitle: string;
  onSave: (title: string, titleEn: string, subtitle: string) => void;
  onClose: () => void;
}

function HeaderModal({ title, titleEn, subtitle, onSave, onClose }: HeaderModalProps) {
  const [draftTitle, setDraftTitle] = useState(title);
  const [draftTitleEn, setDraftTitleEn] = useState(titleEn);
  const [draftSubtitle, setDraftSubtitle] = useState(subtitle);

  const handleSubmit = (e: React.FormEvent) => {
    e.preventDefault();
    if (draftTitle.trim()) onSave(draftTitle.trim(), draftTitleEn.trim(), draftSubtitle.trim());
  };

  return createPortal(
    <div className="fixed inset-0 z-[9999] flex items-center justify-center bg-black/50" onClick={onClose}>
      <div className="bg-white rounded-2xl shadow-2xl w-[420px] p-6" onClick={(e) => e.stopPropagation()}>
        <div className="flex items-center justify-between mb-5">
          <h2 className="text-xl font-black text-gray-800">✏ 헤더 수정</h2>
          <button type="button" onClick={onClose} className="text-gray-400 hover:text-gray-600 text-2xl leading-none">✕</button>
        </div>
        <form onSubmit={handleSubmit} className="space-y-4">
          <div>
            <label className="block text-sm font-bold text-gray-500 mb-1.5">부문명</label>
            <input
              required
              autoFocus
              value={draftTitle}
              onChange={(e) => setDraftTitle(e.target.value)}
              className="w-full border border-gray-200 rounded-xl px-4 py-2.5 text-lg font-bold outline-none focus:border-emerald-400"
            />
          </div>
          <div>
            <label className="block text-sm font-bold text-gray-500 mb-1.5">영문명</label>
            <input
              value={draftTitleEn}
              onChange={(e) => setDraftTitleEn(e.target.value)}
              className="w-full border border-gray-200 rounded-xl px-4 py-2.5 text-base outline-none focus:border-emerald-400"
              placeholder="HRM"
            />
          </div>
          <div>
            <label className="block text-sm font-bold text-gray-500 mb-1.5">부제목</label>
            <input
              value={draftSubtitle}
              onChange={(e) => setDraftSubtitle(e.target.value)}
              className="w-full border border-gray-200 rounded-xl px-4 py-2.5 text-base outline-none focus:border-emerald-400"
            />
          </div>
          <div className="flex justify-end gap-2 pt-1">
            <button type="button" onClick={onClose} className="px-5 py-2.5 rounded-xl border border-gray-200 text-gray-600 font-semibold hover:bg-gray-50">취소</button>
            <button type="submit" className="px-6 py-2.5 rounded-xl bg-emerald-700 text-white font-bold hover:bg-emerald-800">저장</button>
          </div>
        </form>
      </div>
    </div>,
    document.body,
  );
}

export function DepartmentColumn({
  slot,
  tasks,
  orderedIds,
  quarter,
  referenceWeekMonday,
  onSelectTask,
  sectionOptions: externalSectionOptions,
  teamMembers = [],
}: DepartmentColumnProps) {
  const queryClient = useQueryClient();
  const section = slotSectionLabel(slot);
  const isDummySlot = !slot.sectionKey;

  const { data: colConfig } = useQuery({
    queryKey: ['columns', slot.sectionKey],
    queryFn: () => apiClient.get(`/columns/${encodeURIComponent(slot.sectionKey!)}`).then((r) => r.data),
    enabled: !!slot.sectionKey,
    staleTime: 0,
  });

  const [dummyHeader, setDummyHeader] = useState(() => loadDummyHeaders()[slot.id]);

  useEffect(() => {
    setDummyHeader(loadDummyHeaders()[slot.id]);
  }, [slot.id]);

  const patchColumn = useMutation({
    mutationFn: (data: Record<string, string>) =>
      apiClient.patch(`/columns/${encodeURIComponent(slot.sectionKey!)}`, data),
    onSuccess: () => queryClient.invalidateQueries({ queryKey: ['columns', slot.sectionKey] }),
  });

  const title = columnDisplayTitle(slot, colConfig, dummyHeader);
  const titleEnState = columnDisplayTitleEn(slot, colConfig, dummyHeader);
  const subtitle = isDummySlot ? dummyHeader?.subtitle ?? '' : colConfig?.subtitle ?? '';

  const [ctxMenu, setCtxMenu] = useState<{ x: number; y: number; type: 'header' | 'list' } | null>(null);
  const [cardMenu, setCardMenu] = useState<{ x: number; y: number; task: Task } | null>(null);
  const [showAddModal, setShowAddModal] = useState(false);
  const [showEditModal, setShowEditModal] = useState(false);
  const [showHeaderModal, setShowHeaderModal] = useState(false);
  const [editingTask, setEditingTask] = useState<Task | null>(null);

  const { setNodeRef: setProjectDropRef, isOver: isProjectOver } = useDroppable({
    id: `drop::project::${section}`,
  });

  const orderedTasks = [...tasks].sort((a, b) => {
    const ai = orderedIds.indexOf(a.id);
    const bi = orderedIds.indexOf(b.id);
    if (ai === -1 && bi === -1) return 0;
    if (ai === -1) return 1;
    if (bi === -1) return -1;
    return ai - bi;
  });

  const projectTasks = orderedTasks.filter((t) => isProjectTask(t.taskType));

  const create = useMutation({
    mutationFn: (data: Partial<Task>) => apiClient.post('/tasks', data),
    onSuccess: () => invalidateTaskCaches(queryClient),
  });

  const patch = useMutation({
    mutationFn: ({ id, data }: { id: string; data: Record<string, unknown> }) =>
      apiClient.patch(`/tasks/${id}`, data),
    onSuccess: (_data, { id }) => invalidateTaskCaches(queryClient, id),
  });

  const remove = useMutation({
    mutationFn: (id: string) => apiClient.delete(`/tasks/${id}`),
    onSuccess: (_data, id) => invalidateTaskCaches(queryClient, id),
  });

  const handleColumnContextMenuCapture = (e: React.MouseEvent) => {
    const card = (e.target as HTMLElement).closest('[data-task-id]');
    if (!card) return;
    e.preventDefault();
    e.stopPropagation();
    const taskId = card.getAttribute('data-task-id');
    const task = tasks.find((t) => t.id === taskId);
    if (task) {
      setCtxMenu(null);
      setCardMenu({ x: e.clientX, y: e.clientY, task });
    }
  };

  const handleListContextMenu = (e: React.MouseEvent) => {
    if ((e.target as HTMLElement).closest('[data-task-card]')) return;
    e.preventDefault();
    e.stopPropagation();
    setCardMenu(null);
    setCtxMenu({ x: e.clientX, y: e.clientY, type: 'list' });
  };

  const sectionOptions = externalSectionOptions ?? [{ value: section, label: title }];

  const handleAdd = async (data: TaskFormData) => {
    try {
      await create.mutateAsync({
        ...projectFormToApiPayload(data),
        section,
        priority: 'MEDIUM',
      } as Partial<Task>);
      setShowAddModal(false);
    } catch (err: unknown) {
      alert(getApiErrorMessage(err, '업무 추가에 실패했습니다.'));
    }
  };

  const handleEdit = (data: TaskFormData) => {
    if (!editingTask) return;
    patch.mutate({ id: editingTask.id, data: projectFormToApiPayload(data) });
    setShowEditModal(false);
    setEditingTask(null);
  };

  const handleDeleteCard = (task: Task) => {
    if (window.confirm(`"${task.title}" 업무를 삭제하시겠습니까?`)) {
      remove.mutate(task.id);
    }
  };

  const saveHeader = (t: string, te: string, s: string) => {
    if (isDummySlot) {
      saveDummyHeader(slot.id, { title: t, titleEn: te, subtitle: s });
      setDummyHeader({ title: t, titleEn: te, subtitle: s });
    } else {
      patchColumn.mutate({ title: t, titleEn: te, subtitle: s });
    }
    setShowHeaderModal(false);
  };

  return (
    <>
      <section
        className={`dept-card ${slot.cssClass}`}
        onContextMenuCapture={handleColumnContextMenuCapture}
      >
        <div
          className="dept-head"
          onContextMenu={(e) => {
            e.preventDefault();
            setCtxMenu({ x: e.clientX, y: e.clientY, type: 'header' });
          }}
        >
          <div className="dept-head-main">
            <DeptIcon slotId={slot.id} />
            <div className="board-dept-header-main">
              <div className="board-dept-title-wrap">
                <span className="board-dept-title" role="heading" aria-level={2}>
                  {title.replace(/\s*부문$/, '')}
                </span>
                {titleEnState && <span className="board-dept-title-en">{titleEnState}</span>}
                <div className="dept-head-count" aria-label={`${projectTasks.length}건`}>
                  <span className="poly-stat-val">{projectTasks.length}</span>
                  <span className="poly-stat-unit">건</span>
                </div>
              </div>
              {subtitle && <p className="board-dept-subtitle">{subtitle}</p>}
            </div>
          </div>
        </div>

        <DeptProjectList
          items={projectTasks}
          getKey={(task) => task.id}
          sortableItemIds={projectTasks.map((t) => t.id)}
          dropRef={setProjectDropRef}
          className={isProjectOver ? 'is-over' : ''}
          onContextMenu={handleListContextMenu}
          empty={<div className="board-empty">해당 업무 없음</div>}
          renderItem={(task) => (
            <SortableTaskCard
              task={task}
              variant="project"
              sectionOptions={sectionOptions}
              referenceWeekMonday={referenceWeekMonday}
              onSelect={onSelectTask}
            />
          )}
        />
      </section>

      {cardMenu && (
        <ContextMenu
          x={cardMenu.x}
          y={cardMenu.y}
          onClose={() => setCardMenu(null)}
          items={[
            { icon: '✚', label: '업무 추가', onClick: () => { setShowAddModal(true); setCardMenu(null); } },
            { icon: '✏', label: '업무 수정', onClick: () => { setEditingTask(cardMenu.task); setShowEditModal(true); setCardMenu(null); } },
            { icon: '🗑', label: '업무 삭제', onClick: () => { handleDeleteCard(cardMenu.task); setCardMenu(null); }, danger: true },
          ]}
        />
      )}

      {ctxMenu && (
        <ContextMenu
          x={ctxMenu.x}
          y={ctxMenu.y}
          onClose={() => setCtxMenu(null)}
          items={
            ctxMenu.type === 'header'
              ? [{ icon: '✏', label: '헤더 수정', onClick: () => setShowHeaderModal(true) }]
              : [{ icon: '✚', label: '업무 추가', onClick: () => setShowAddModal(true) }]
          }
        />
      )}

      {showAddModal && (
        <TaskModal
          variant="project"
          mode="add"
          defaultSection={section}
          defaultQuarter={quarter}
          sectionOptions={sectionOptions}
          teamMembers={teamMembers}
          onSave={handleAdd}
          onClose={() => setShowAddModal(false)}
        />
      )}

      {showEditModal && editingTask && (
        <TaskModal
          variant="project"
          mode="edit"
          task={editingTask}
          sectionOptions={sectionOptions}
          teamMembers={teamMembers}
          onSave={handleEdit}
          onClose={() => { setShowEditModal(false); setEditingTask(null); }}
        />
      )}

      {showHeaderModal && (
        <HeaderModal
          title={title}
          titleEn={titleEnState}
          subtitle={subtitle}
          onSave={saveHeader}
          onClose={() => setShowHeaderModal(false)}
        />
      )}
    </>
  );
}
