'use client';

/**
 * 계정과목 설정 모달 (공용)
 *
 * - 계정과목 추가: 코드, 계정과목명, 분류 Select, 추가 버튼
 * - 검색: 검색 Input, 분류 필터 Select, 건수 표시
 * - 테이블: 코드 | 계정과목명 | 분류 | 부문 | 상태(사용중/미사용 토글) | 작업(삭제)
 * - 기본 계정과목표 일괄 생성 버튼
 * - 버튼: 닫기
 */

import { useState, useCallback, useEffect, useMemo } from 'react';
import { toast } from 'sonner';
import { Plus, Trash2, Loader2, Database } from 'lucide-react';
import { Button } from '@/components/ui/button';
import { Input } from '@/components/ui/input';
import { Badge } from '@/components/ui/badge';
import { FormField } from '@/components/molecules/FormField';
import {
  Dialog,
  DialogContent,
  DialogDescription,
  DialogHeader,
  DialogTitle,
  DialogFooter,
} from '@/components/ui/dialog';
import {
  Select,
  SelectContent,
  SelectItem,
  SelectTrigger,
  SelectValue,
} from '@/components/ui/select';
import {
  Table,
  TableBody,
  TableCell,
  TableHead,
  TableHeader,
  TableRow,
} from '@/components/ui/table';
import {
  AlertDialog,
  AlertDialogAction,
  AlertDialogCancel,
  AlertDialogContent,
  AlertDialogDescription,
  AlertDialogFooter,
  AlertDialogHeader,
  AlertDialogTitle,
} from '@/components/ui/alert-dialog';
import {
  getAccountSubjects,
  createAccountSubject,
  updateAccountSubjectStatus,
  deleteAccountSubject,
  seedDefaultAccountSubjects,
} from './actions';
import type { AccountSubject, AccountSubjectCategory } from './types';
import {
  ACCOUNT_CATEGORY_OPTIONS,
  ACCOUNT_CATEGORY_FILTER_OPTIONS,
  ACCOUNT_CATEGORY_LABELS,
  DEPARTMENT_TYPE_LABELS,
} from './types';
import type { DepartmentType } from './types';

interface AccountSubjectSettingModalProps {
  open: boolean;
  onOpenChange: (open: boolean) => void;
}

export function AccountSubjectSettingModal({
  open,
  onOpenChange,
}: AccountSubjectSettingModalProps) {
  // 추가 폼
  const [newCode, setNewCode] = useState('');
  const [newName, setNewName] = useState('');
  const [newCategory, setNewCategory] = useState<AccountSubjectCategory>('asset');
  const [isAdding, setIsAdding] = useState(false);

  // 검색/필터
  const [search, setSearch] = useState('');
  const [categoryFilter, setCategoryFilter] = useState('all');

  // 데이터
  const [subjects, setSubjects] = useState<AccountSubject[]>([]);
  const [isLoading, setIsLoading] = useState(false);
  const [isSeeding, setIsSeeding] = useState(false);

  // 삭제 확인
  const [deleteTarget, setDeleteTarget] = useState<AccountSubject | null>(null);

  // 데이터 로드
  const loadSubjects = useCallback(async () => {
    setIsLoading(true);
    try {
      const result = await getAccountSubjects({
        search,
        category: categoryFilter,
      });
      if (result.success && result.data) {
        setSubjects(result.data);
      }
    } catch {
      toast.error('계정과목 목록 조회에 실패했습니다.');
    } finally {
      setIsLoading(false);
    }
  }, [search, categoryFilter]);

  useEffect(() => {
    if (open) {
      loadSubjects();
    }
  }, [open, loadSubjects]);

  // 필터링된 목록
  const filteredSubjects = useMemo(() => {
    return subjects.filter((s) => {
      const matchSearch =
        !search ||
        s.code.toLowerCase().includes(search.toLowerCase()) ||
        s.name.toLowerCase().includes(search.toLowerCase());
      const matchCategory = categoryFilter === 'all' || s.category === categoryFilter;
      return matchSearch && matchCategory;
    });
  }, [subjects, search, categoryFilter]);

  // 계정과목 추가
  const handleAdd = useCallback(async () => {
    if (!newCode.trim()) {
      toast.warning('코드를 입력해주세요.');
      return;
    }
    if (!newName.trim()) {
      toast.warning('계정과목명을 입력해주세요.');
      return;
    }

    setIsAdding(true);
    try {
      const result = await createAccountSubject({
        code: newCode.trim(),
        name: newName.trim(),
        category: newCategory,
      });
      if (result.success) {
        toast.success('계정과목이 추가되었습니다.');
        setNewCode('');
        setNewName('');
        setNewCategory('asset');
        loadSubjects();
      } else {
        toast.error(result.error || '추가에 실패했습니다.');
      }
    } catch {
      toast.error('추가 중 오류가 발생했습니다.');
    } finally {
      setIsAdding(false);
    }
  }, [newCode, newName, newCategory, loadSubjects]);

  // 상태 토글
  const handleToggleStatus = useCallback(
    async (subject: AccountSubject) => {
      try {
        const result = await updateAccountSubjectStatus(subject.id, !subject.isActive);
        if (result.success) {
          toast.success(
            `${subject.name}이(가) ${!subject.isActive ? '사용중' : '미사용'}으로 변경되었습니다.`
          );
          loadSubjects();
        } else {
          toast.error(result.error || '상태 변경에 실패했습니다.');
        }
      } catch {
        toast.error('상태 변경 중 오류가 발생했습니다.');
      }
    },
    [loadSubjects]
  );

  // 삭제
  const handleDelete = useCallback(async () => {
    if (!deleteTarget) return;
    try {
      const result = await deleteAccountSubject(deleteTarget.id);
      if (result.success) {
        toast.success('계정과목이 삭제되었습니다.');
        setDeleteTarget(null);
        loadSubjects();
      } else {
        toast.error(result.error || '삭제에 실패했습니다.');
      }
    } catch {
      toast.error('삭제 중 오류가 발생했습니다.');
    }
  }, [deleteTarget, loadSubjects]);

  // 기본 계정과목표 생성
  const handleSeedDefaults = useCallback(async () => {
    setIsSeeding(true);
    try {
      const result = await seedDefaultAccountSubjects();
      if (result.success) {
        const count = result.data?.inserted_count ?? 0;
        if (count > 0) {
          toast.success(`기본 계정과목 ${count}건이 생성되었습니다.`);
        } else {
          toast.info('이미 모든 기본 계정과목이 등록되어 있습니다.');
        }
        loadSubjects();
      } else {
        toast.error(result.error || '기본 계정과목 생성에 실패했습니다.');
      }
    } catch {
      toast.error('기본 계정과목 생성 중 오류가 발생했습니다.');
    } finally {
      setIsSeeding(false);
    }
  }, [loadSubjects]);

  // depth에 따른 들여쓰기
  const getIndentClass = (depth: number) => {
    if (depth === 1) return 'font-bold';
    if (depth === 2) return 'pl-4 font-medium';
    return 'pl-8';
  };

  return (
    <>
      <Dialog open={open} onOpenChange={onOpenChange}>
        <DialogContent className="sm:max-w-[850px] max-h-[85vh] flex flex-col">
          <DialogHeader>
            <DialogTitle>계정과목 설정</DialogTitle>
            <DialogDescription className="sr-only">계정과목을 추가, 검색, 상태변경, 삭제합니다</DialogDescription>
          </DialogHeader>

          {/* 추가 영역 */}
          <div className="space-y-2 p-3 bg-muted/50 rounded-lg">
            <div className="grid grid-cols-1 sm:grid-cols-2 gap-2">
              <FormField
                label="코드"
                value={newCode}
                onChange={setNewCode}
                placeholder="예: 10100"
              />
              <FormField
                label="계정과목명"
                value={newName}
                onChange={setNewName}
                placeholder="계정과목명"
              />
            </div>
            <div className="flex items-end gap-2">
              <div className="flex-1">
                <label className="text-sm font-medium mb-1.5 block">분류</label>
                <Select
                  value={newCategory}
                  onValueChange={(v) => setNewCategory(v as AccountSubjectCategory)}
                >
                  <SelectTrigger className="h-9 text-sm">
                    <SelectValue />
                  </SelectTrigger>
                  <SelectContent>
                    {ACCOUNT_CATEGORY_OPTIONS.map((opt) => (
                      <SelectItem key={opt.value} value={opt.value}>
                        {opt.label}
                      </SelectItem>
                    ))}
                  </SelectContent>
                </Select>
              </div>
              <Button size="sm" className="h-9" onClick={handleAdd} disabled={isAdding}>
                {isAdding ? (
                  <Loader2 className="h-4 w-4 animate-spin" />
                ) : (
                  <>
                    <Plus className="h-4 w-4 mr-1" />
                    추가
                  </>
                )}
              </Button>
            </div>
          </div>

          {/* 검색/필터 영역 */}
          <div className="space-y-2 sm:space-y-0 sm:flex sm:items-center sm:gap-2">
            <Input
              placeholder="코드 또는 이름 검색"
              value={search}
              onChange={(e) => setSearch(e.target.value)}
              className="w-full sm:max-w-[250px] h-9 text-sm"
            />
            <div className="flex items-center gap-2">
              <Select value={categoryFilter} onValueChange={setCategoryFilter}>
                <SelectTrigger className="min-w-[100px] w-auto h-9 text-sm">
                  <SelectValue />
                </SelectTrigger>
                <SelectContent>
                  {ACCOUNT_CATEGORY_FILTER_OPTIONS.map((opt) => (
                    <SelectItem key={opt.value} value={opt.value}>
                      {opt.label}
                    </SelectItem>
                  ))}
                </SelectContent>
              </Select>
              <span className="text-sm text-muted-foreground">
                {filteredSubjects.length}건
              </span>
              <Button
                variant="outline"
                size="sm"
                className="h-9 ml-auto"
                onClick={handleSeedDefaults}
                disabled={isSeeding}
              >
                {isSeeding ? (
                  <Loader2 className="h-4 w-4 animate-spin mr-1" />
                ) : (
                  <Database className="h-4 w-4 mr-1" />
                )}
                기본 계정과목 생성
              </Button>
            </div>
          </div>

          {/* 테이블 */}
          <div className="flex-1 overflow-auto border rounded-md">
            {isLoading ? (
              <div className="flex items-center justify-center h-[200px] text-sm text-muted-foreground">
                로딩 중...
              </div>
            ) : (
              <Table>
                <TableHeader>
                  <TableRow>
                    <TableHead className="w-[80px]">코드</TableHead>
                    <TableHead>계정과목명</TableHead>
                    <TableHead className="text-center w-[70px]">분류</TableHead>
                    <TableHead className="text-center w-[60px]">부문</TableHead>
                    <TableHead className="text-center w-[90px]">상태</TableHead>
                    <TableHead className="text-center w-[50px]">작업</TableHead>
                  </TableRow>
                </TableHeader>
                <TableBody>
                  {filteredSubjects.length === 0 ? (
                    <TableRow>
                      <TableCell colSpan={6} className="text-center text-sm text-muted-foreground h-[100px]">
                        계정과목이 없습니다. &quot;기본 계정과목 생성&quot; 버튼을 클릭하면 표준 계정과목표가 생성됩니다.
                      </TableCell>
                    </TableRow>
                  ) : (
                    filteredSubjects.map((subject) => (
                      <TableRow key={subject.id}>
                        <TableCell className="text-sm font-mono">{subject.code}</TableCell>
                        <TableCell className={`text-sm ${getIndentClass(subject.depth)}`}>
                          {subject.name}
                        </TableCell>
                        <TableCell className="text-center">
                          <Badge variant="outline" className="text-xs">
                            {ACCOUNT_CATEGORY_LABELS[subject.category]}
                          </Badge>
                        </TableCell>
                        <TableCell className="text-center text-xs text-muted-foreground">
                          {DEPARTMENT_TYPE_LABELS[subject.departmentType as DepartmentType] || '-'}
                        </TableCell>
                        <TableCell className="text-center">
                          <Button
                            variant={subject.isActive ? 'default' : 'outline'}
                            size="sm"
                            className="h-7 px-2 text-xs"
                            onClick={() => handleToggleStatus(subject)}
                          >
                            {subject.isActive ? '사용중' : '미사용'}
                          </Button>
                        </TableCell>
                        <TableCell className="text-center">
                          <Button
                            variant="ghost"
                            size="icon"
                            className="h-7 w-7 text-red-500 hover:text-red-600 hover:bg-red-50"
                            onClick={() => setDeleteTarget(subject)}
                          >
                            <Trash2 className="h-3.5 w-3.5" />
                          </Button>
                        </TableCell>
                      </TableRow>
                    ))
                  )}
                </TableBody>
              </Table>
            )}
          </div>

          <DialogFooter>
            <Button variant="outline" onClick={() => onOpenChange(false)}>
              닫기
            </Button>
          </DialogFooter>
        </DialogContent>
      </Dialog>

      {/* 삭제 확인 */}
      <AlertDialog open={!!deleteTarget} onOpenChange={(v) => !v && setDeleteTarget(null)}>
        <AlertDialogContent>
          <AlertDialogHeader>
            <AlertDialogTitle>계정과목 삭제</AlertDialogTitle>
            <AlertDialogDescription>
              &quot;{deleteTarget?.name}&quot; 계정과목을 삭제하시겠습니까? 이 작업은 취소할 수 없습니다.
            </AlertDialogDescription>
          </AlertDialogHeader>
          <AlertDialogFooter>
            <AlertDialogCancel>취소</AlertDialogCancel>
            <AlertDialogAction
              onClick={handleDelete}
              className="bg-red-500 hover:bg-red-600"
            >
              삭제
            </AlertDialogAction>
          </AlertDialogFooter>
        </AlertDialogContent>
      </AlertDialog>
    </>
  );
}
