/**
 * 달력 일정 Zustand Store
 *
 * 달력관리(CalendarManagement)에서 등록한 공휴일/세무일정/회사일정을
 * 프로젝트 전체 ScheduleCalendar, DatePicker 등에 전파하는 공유 스토어.
 *
 * 데이터 흐름:
 * 1. ScheduleCalendar 마운트 시 해당 연도 fetchSchedules(year) 호출
 * 2. API 응답 → schedulesByYear에 캐시
 * 3. calendarEvents.ts 유틸 함수(isHoliday 등)가 스토어에서 읽음
 * 4. API 미응답 시 하드코딩된 calendarEvents.ts 상수를 폴백으로 사용
 */

import { create } from 'zustand';
import { devtools } from 'zustand/middleware';
import type { CalendarSchedule } from '@/components/hr/CalendarManagement/types';
import { getCalendarSchedules } from '@/components/hr/CalendarManagement/actions';

interface CalendarScheduleStore {
  /** 연도별 캐시된 일정 */
  schedulesByYear: Record<number, CalendarSchedule[]>;
  /** 연도별 로딩 완료 여부 */
  loadedYears: Record<number, boolean>;
  /** 연도별 로딩 중 여부 */
  loadingYears: Record<number, boolean>;

  /** 연도별 일정 조회 (캐시 히트 시 API 호출 안 함) */
  fetchSchedules: (year: number) => Promise<CalendarSchedule[]>;
  /** 이미 가져온 데이터를 스토어에 직접 설정 (추가 API 호출 없음) */
  setSchedulesForYear: (year: number, schedules: CalendarSchedule[]) => void;
  /** 특정 연도 캐시 무효화 (달력관리에서 등록/수정/삭제 후 호출) */
  invalidateYear: (year: number) => void;
}

export const useCalendarScheduleStore = create<CalendarScheduleStore>()(
  devtools(
    (set, get) => ({
      schedulesByYear: {},
      loadedYears: {},
      loadingYears: {},

      fetchSchedules: async (year: number) => {
        const { loadedYears, loadingYears, schedulesByYear } = get();

        // 이미 로드됨
        if (loadedYears[year]) {
          return schedulesByYear[year] || [];
        }

        // 이미 로딩 중 (중복 호출 방지)
        if (loadingYears[year]) {
          return schedulesByYear[year] || [];
        }

        set(
          (state) => ({
            loadingYears: { ...state.loadingYears, [year]: true },
          }),
          false,
          'fetchSchedules/start'
        );

        try {
          const result = await getCalendarSchedules(year);
          const schedules = result.success && result.data ? result.data : [];

          set(
            (state) => ({
              schedulesByYear: { ...state.schedulesByYear, [year]: schedules },
              loadedYears: { ...state.loadedYears, [year]: true },
              loadingYears: { ...state.loadingYears, [year]: false },
            }),
            false,
            'fetchSchedules/success'
          );

          return schedules;
        } catch {
          // API 실패 시에도 loaded 처리 → 같은 연도 반복 호출 방지
          // (폴백 상수 데이터 사용, 달력관리에서 등록 시 invalidateYear로 재시도)
          set(
            (state) => ({
              schedulesByYear: { ...state.schedulesByYear, [year]: [] },
              loadedYears: { ...state.loadedYears, [year]: true },
              loadingYears: { ...state.loadingYears, [year]: false },
            }),
            false,
            'fetchSchedules/error'
          );
          return [];
        }
      },

      setSchedulesForYear: (year: number, schedules: CalendarSchedule[]) => {
        set(
          (state) => ({
            schedulesByYear: { ...state.schedulesByYear, [year]: schedules },
            loadedYears: { ...state.loadedYears, [year]: true },
            loadingYears: { ...state.loadingYears, [year]: false },
          }),
          false,
          'setSchedulesForYear'
        );
      },

      invalidateYear: (year: number) => {
        set(
          (state) => {
            const newSchedules = { ...state.schedulesByYear };
            const newLoaded = { ...state.loadedYears };
            delete newSchedules[year];
            delete newLoaded[year];
            return { schedulesByYear: newSchedules, loadedYears: newLoaded };
          },
          false,
          'invalidateYear'
        );
      },
    }),
    { name: 'CalendarScheduleStore' }
  )
);
