"use client";

import { useCallback, useEffect, useState } from "react";
import {
  type ClassSchedule,
  computeSessionDates,
  monthRangeGregorian,
  sessionDatesUpTo,
} from "@/lib/class-session-dates";
import { ApiError, apiGet } from "@/lib/api";

interface HistoryDay {
  date: string;
  marked_count: number;
}

interface HistoryPayload {
  days: HistoryDay[];
}

function shiftIso(iso: string, deltaDays: number) {
  const d = new Date(iso + "T12:00:00");
  d.setDate(d.getDate() + deltaDays);
  return d.toISOString().slice(0, 10);
}

function todayIso() {
  return new Date().toISOString().slice(0, 10);
}

export function useAttendanceCalendarMarks({
  classRoomId,
  scheduleId,
  subjectId,
  month,
  anchorDate,
}: {
  classRoomId: number;
  scheduleId?: number | null;
  subjectId?: number | null;
  month: string;
  anchorDate?: string;
}) {
  const [sessionDates, setSessionDates] = useState<string[]>([]);
  const [allSessionDates, setAllSessionDates] = useState<string[]>([]);
  const [recordedDates, setRecordedDates] = useState<string[]>([]);
  const [loading, setLoading] = useState(true);

  const load = useCallback(async () => {
    setLoading(true);
    try {
      const { from, to } = monthRangeGregorian(month);
      const today = todayIso();
      const navAnchor = anchorDate ?? today;
      const navFrom = shiftIso(navAnchor, -180);
      const navTo = shiftIso(navAnchor, 60);

      const [schedules, history] = await Promise.all([
        apiGet<ClassSchedule[]>(`/schedules?class_room_id=${classRoomId}`),
        apiGet<HistoryPayload>(
          `/class-attendances/history?class_room_id=${classRoomId}&from=${from}&to=${to}${
            scheduleId ? `&schedule_id=${scheduleId}` : ""
          }${subjectId ? `&subject_id=${subjectId}` : ""}`,
        ),
      ]);

      const opts = { scheduleId, subjectId };
      setSessionDates(computeSessionDates(from, to, schedules, opts));
      setAllSessionDates(
        sessionDatesUpTo(navFrom, navTo, schedules, opts, today),
      );
      setRecordedDates(
        (history.days ?? [])
          .filter((d) => d.marked_count > 0)
          .map((d) => d.date),
      );
    } catch (err) {
      if (err instanceof ApiError) {
        setSessionDates([]);
        setAllSessionDates([]);
        setRecordedDates([]);
      }
    } finally {
      setLoading(false);
    }
  }, [anchorDate, classRoomId, month, scheduleId, subjectId]);

  useEffect(() => {
    void load();
  }, [load]);

  return { sessionDates, allSessionDates, recordedDates, loading, reload: load };
}
