/**
 * 달력 이벤트 상수 + API 연동 유틸리티
 *
 * 우선순위:
 * 1. useCalendarScheduleStore (API에서 가져온 동적 데이터)
 * 2. 하드코딩된 상수 (폴백, API 미응답 시)
 *
 * 달력관리(CalendarManagement)에서 등록한 데이터가 스토어에 있으면
 * 해당 데이터를 사용하고, 없으면 아래 하드코딩된 상수를 폴백으로 사용합니다.
 */

import { useCalendarScheduleStore } from '@/stores/useCalendarScheduleStore';
import { getLocalDateString } from '@/lib/utils/date';
import type { CalendarSchedule, CalendarScheduleType } from '@/components/hr/CalendarManagement/types';

export type CalendarEventType = 'holiday' | 'tax';

export interface CalendarEvent {
  date: string;
  name: string;
  type: CalendarEventType;
}

// ============================================
// 2026년 공휴일 (폴백 데이터)
// ============================================
export const HOLIDAYS_2026: CalendarEvent[] = [
  { date: '2026-01-01', name: '신정', type: 'holiday' },
  { date: '2026-02-16', name: '설날 연휴', type: 'holiday' },
  { date: '2026-02-17', name: '설날', type: 'holiday' },
  { date: '2026-02-18', name: '설날 연휴', type: 'holiday' },
  { date: '2026-03-01', name: '삼일절', type: 'holiday' },
  { date: '2026-03-02', name: '대체공휴일(삼일절)', type: 'holiday' },
  { date: '2026-05-05', name: '어린이날', type: 'holiday' },
  { date: '2026-05-24', name: '부처님오신날', type: 'holiday' },
  { date: '2026-06-06', name: '현충일', type: 'holiday' },
  { date: '2026-07-17', name: '제헌절', type: 'holiday' },
  { date: '2026-08-15', name: '광복절', type: 'holiday' },
  { date: '2026-08-17', name: '대체공휴일(광복절)', type: 'holiday' },
  { date: '2026-09-24', name: '추석 연휴', type: 'holiday' },
  { date: '2026-09-25', name: '추석', type: 'holiday' },
  { date: '2026-09-26', name: '추석 연휴', type: 'holiday' },
  { date: '2026-10-03', name: '개천절', type: 'holiday' },
  { date: '2026-10-09', name: '한글날', type: 'holiday' },
  { date: '2026-12-25', name: '성탄절', type: 'holiday' },
];

// ============================================
// 2026년 주요 세금 마감일 (폴백 데이터)
// ============================================
export const TAX_DEADLINES_2026: CalendarEvent[] = [
  { date: '2026-01-26', name: '부가세 2기 확정신고', type: 'tax' },
  { date: '2026-03-31', name: '법인세 신고', type: 'tax' },
  { date: '2026-06-01', name: '종합소득세 신고', type: 'tax' },
  { date: '2026-07-27', name: '부가세 1기 확정신고', type: 'tax' },
];

// ============================================
// 연도별 통합 폴백 데이터
// ============================================
export const CALENDAR_EVENTS: Record<number, CalendarEvent[]> = {
  2026: [...HOLIDAYS_2026, ...TAX_DEADLINES_2026],
};

// ============================================
// CalendarSchedule → CalendarEvent 타입 매핑
// ============================================
const HOLIDAY_SCHEDULE_TYPES: CalendarScheduleType[] = [
  'publicHoliday',
  'temporaryHoliday',
  'substituteHoliday',
];

function scheduleTypeToEventType(type: CalendarScheduleType): CalendarEventType | null {
  if (HOLIDAY_SCHEDULE_TYPES.includes(type)) return 'holiday';
  if (type === 'taxDeadline') return 'tax';
  return null; // companyEvent 등은 공휴일/세무일정이 아님
}

// ============================================
// 스토어에서 특정 날짜의 일정 조회 (내부 헬퍼)
// ============================================
function getApiSchedulesForDate(dateStr: string): CalendarSchedule[] | null {
  const year = parseInt(dateStr.substring(0, 4), 10);
  const store = useCalendarScheduleStore.getState();

  if (!store.loadedYears[year]) return null; // 미로드 → 폴백 사용

  const schedules = store.schedulesByYear[year] || [];
  return schedules.filter((s) => s.startDate <= dateStr && s.endDate >= dateStr);
}

// ============================================
// 유틸리티 함수 (스토어 우선, 폴백 상수)
// ============================================

/**
 * 특정 날짜의 모든 이벤트 조회
 */
export function getEventsForDate(date: string): CalendarEvent[] {
  const apiSchedules = getApiSchedulesForDate(date);

  if (apiSchedules !== null) {
    return apiSchedules
      .map((s) => {
        const eventType = scheduleTypeToEventType(s.type);
        if (!eventType) return null;
        return { date, name: s.name, type: eventType };
      })
      .filter((e): e is CalendarEvent => e !== null);
  }

  // 폴백
  const year = parseInt(date.substring(0, 4), 10);
  const events = CALENDAR_EVENTS[year] || [];
  return events.filter((e) => e.date === date);
}

/**
 * 공휴일 여부 확인
 */
export function isHoliday(date: string): boolean {
  const apiSchedules = getApiSchedulesForDate(date);

  if (apiSchedules !== null) {
    return apiSchedules.some((s) => HOLIDAY_SCHEDULE_TYPES.includes(s.type));
  }

  // 폴백
  const year = parseInt(date.substring(0, 4), 10);
  const events = CALENDAR_EVENTS[year] || [];
  return events.some((e) => e.date === date && e.type === 'holiday');
}

/**
 * 세금 마감일 여부 확인
 */
export function isTaxDeadline(date: string): boolean {
  const apiSchedules = getApiSchedulesForDate(date);

  if (apiSchedules !== null) {
    return apiSchedules.some((s) => s.type === 'taxDeadline');
  }

  // 폴백
  const year = parseInt(date.substring(0, 4), 10);
  const events = CALENDAR_EVENTS[year] || [];
  return events.some((e) => e.date === date && e.type === 'tax');
}

/**
 * 공휴일명 조회
 */
export function getHolidayName(date: string): string | null {
  const apiSchedules = getApiSchedulesForDate(date);

  if (apiSchedules !== null) {
    const holiday = apiSchedules.find((s) => HOLIDAY_SCHEDULE_TYPES.includes(s.type));
    return holiday?.name || null;
  }

  // 폴백
  const events = getEventsForDate(date);
  const holiday = events.find((e) => e.type === 'holiday');
  return holiday?.name || null;
}

/**
 * 세금 마감일명 조회
 */
export function getTaxDeadlineName(date: string): string | null {
  const apiSchedules = getApiSchedulesForDate(date);

  if (apiSchedules !== null) {
    const tax = apiSchedules.find((s) => s.type === 'taxDeadline');
    return tax?.name || null;
  }

  // 폴백
  const events = getEventsForDate(date);
  const tax = events.find((e) => e.type === 'tax');
  return tax?.name || null;
}

/**
 * 특정 연도의 모든 CalendarEvent 조회 (스토어 우선)
 */
export function getCalendarEventsForYear(year: number): CalendarEvent[] {
  const store = useCalendarScheduleStore.getState();

  if (store.loadedYears[year]) {
    const schedules = store.schedulesByYear[year] || [];
    const events: CalendarEvent[] = [];

    for (const s of schedules) {
      const eventType = scheduleTypeToEventType(s.type);
      if (!eventType) continue;

      // 날짜 범위 확장 (startDate ~ endDate 각 날짜를 개별 이벤트로)
      const start = new Date(s.startDate);
      const end = new Date(s.endDate);
      for (let d = new Date(start); d <= end; d.setDate(d.getDate() + 1)) {
        const dateStr = getLocalDateString(d);
        events.push({ date: dateStr, name: s.name, type: eventType });
      }
    }

    return events;
  }

  // 폴백
  return CALENDAR_EVENTS[year] || [];
}
