import Link from "next/link";
import { requireSession } from "@/lib/auth";
import { agendaFor, AGENDA_KIND_LABEL, type AgendaItem } from "@/lib/agenda";
import { today, monthKey, periodRange, weekStart, weekDays, shiftMonth, isRealDate } from "@/lib/period";
import { formatDate, formatPeriod } from "@/lib/format";
import { ActionForm } from "@/components/action-form";
import { PageHeader, Badge, SectionTitle } from "@/components/ui";
import { createTaskAction } from "../danh-sach/actions";

export const dynamic = "force-dynamic";

const DAY_HEAD = ["T2", "T3", "T4", "T5", "T6", "T7", "CN"];

const KIND_TONE: Record<AgendaItem["kind"], "brand" | "gold" | "neutral" | "green" | "red"> = {
  task: "brand",
  due: "gold",
  plan: "neutral",
  event: "green",
  invite: "green",
  deadline: "red",
};

/** Ngày cuối cùng của một tháng dạng YYYY-MM-DD (dùng periodRange để khỏi tự tính năm nhuận). */
function monthGrid(month: string): string[] {
  const { start, end } = periodRange(month);
  const first = weekStart(start);
  const lastWeek = weekDays(weekStart(end));
  const days: string[] = [];
  let cursor = first;
  // Lưới đủ tuần: từ thứ Hai của tuần chứa ngày 1 tới Chủ nhật của tuần chứa ngày cuối tháng.
  while (cursor <= lastWeek[6]) {
    days.push(cursor);
    cursor = new Date(Date.parse(`${cursor}T00:00:00Z`) + 86_400_000).toISOString().slice(0, 10);
  }
  return days;
}

export default async function CalendarPage({ searchParams }: { searchParams: Promise<{ thang?: string; ngay?: string }> }) {
  const session = await requireSession();
  const params = await searchParams;
  const todayIso = today();

  // Tham số URL do người dùng gõ tự do: chỉ nhận ngày/tháng có thật (không có 31/02, tháng 13...).
  const selected = isRealDate(params.ngay) ? (params.ngay as string) : null;
  const month = isRealDate(`${params.thang}-01`) ? (params.thang as string) : monthKey(selected ?? todayIso);
  const days = monthGrid(month);
  const items = await agendaFor(session, days[0], days[days.length - 1]);

  const byDay = new Map<string, AgendaItem[]>();
  for (const item of items) byDay.set(item.date, [...(byDay.get(item.date) ?? []), item]);

  // Không chọn ngày nào thì mở ngày hôm nay (nếu đang xem tháng này) hoặc mùng 1 của tháng đang xem.
  const day = selected ?? (monthKey(todayIso) === month ? todayIso : periodRange(month).start);
  const dayItems = byDay.get(day) ?? [];
  const link = (m: string, d?: string) => `/cong-viec/lich?thang=${m}${d ? `&ngay=${d}` : ""}`;

  return (
    <>
      <PageHeader
        title="Lịch công việc"
        subtitle="Việc cần làm, lộ trình tuyến, sự kiện và hạn chót của bạn — bấm một ngày để xem và ghi chú nhớ việc."
        actions={
          <>
            <Link href="/cong-viec/danh-sach" className="btn-ghost">
              Danh sách công việc
            </Link>
            <Link href="/cong-viec" className="btn-ghost">
              Công việc theo tuần
            </Link>
          </>
        }
      />

      <div className="mb-3 flex items-center gap-2">
        <Link href={link(shiftMonth(month, -1))} className="btn-ghost px-3 py-1.5" aria-label="Tháng trước">
          ←
        </Link>
        <div className="min-w-32 text-center text-base font-bold text-ink-700">{formatPeriod(month)}</div>
        <Link href={link(shiftMonth(month, 1))} className="btn-ghost px-3 py-1.5" aria-label="Tháng sau">
          →
        </Link>
        <Link href={link(monthKey(todayIso), todayIso)} className="btn-ghost ml-2 px-3 py-1.5 text-xs">
          Hôm nay
        </Link>
      </div>

      <div className="card overflow-hidden">
        <div className="grid grid-cols-7 border-b border-[var(--color-line)] bg-ink-50 text-center text-[11px] font-semibold uppercase tracking-wide text-ink-400">
          {DAY_HEAD.map((h) => (
            <div key={h} className="py-1.5">
              {h}
            </div>
          ))}
        </div>
        <div className="grid grid-cols-7">
          {days.map((d) => {
            const list = byDay.get(d) ?? [];
            const inMonth = d.slice(0, 7) === month;
            const isToday = d === todayIso;
            const isSelected = d === day;
            const openCount = list.filter((i) => !i.closed).length;
            const hasOverdue = list.some((i) => i.overdue);
            return (
              <Link
                key={d}
                href={link(month, d)}
                aria-label={`${formatDate(d)}${list.length ? `, ${list.length} mục` : ""}`}
                className={`min-h-16 border-b border-r border-[var(--color-line)] p-1 text-left sm:min-h-24 sm:p-1.5 ${
                  isSelected ? "bg-brand-50" : inMonth ? "bg-white hover:bg-ink-50" : "bg-ink-50/60 text-ink-300"
                }`}
              >
                <div className="flex items-center justify-between">
                  <span className={`tnum text-xs font-semibold ${isToday ? "rounded-full bg-brand-500 px-1.5 text-white" : inMonth ? "text-ink-600" : "text-ink-300"}`}>
                    {Number(d.slice(8))}
                  </span>
                  {list.length > 0 && (
                    <span className={`tnum text-[10px] font-bold sm:hidden ${hasOverdue ? "text-red-600" : "text-brand-600"}`}>{list.length}</span>
                  )}
                </div>
                {/* Máy tính: hiện tên 2 mục đầu; điện thoại chỉ hiện số lượng. */}
                <div className="mt-1 hidden flex-col gap-0.5 sm:flex">
                  {list.slice(0, 2).map((i) => (
                    <span
                      key={i.id}
                      className={`truncate rounded px-1 text-[10px] leading-4 ${
                        i.overdue ? "bg-red-50 text-red-700" : i.closed ? "bg-ink-50 text-ink-300 line-through" : "bg-brand-50 text-brand-600"
                      }`}
                    >
                      {i.title}
                    </span>
                  ))}
                  {list.length > 2 && <span className="text-[10px] text-ink-400">+{list.length - 2} mục</span>}
                </div>
                {openCount === 0 && list.length === 0 ? null : <span className="sr-only">{openCount} mục chưa xong</span>}
              </Link>
            );
          })}
        </div>
      </div>

      <div className="mt-6 grid gap-4 lg:grid-cols-2">
        <div>
          <SectionTitle hint={`${dayItems.length} mục`}>Ngày {formatDate(day)}</SectionTitle>
          {dayItems.length === 0 ? (
            <div className="card px-4 py-6 text-center text-sm text-ink-400">Chưa có gì trong ngày này. Ghi chú bên cạnh để không quên.</div>
          ) : (
            <div className="card divide-y divide-[var(--color-line)]">
              {dayItems.map((i) => (
                <Link key={i.id} href={i.href} className={`flex items-start gap-3 px-4 py-2.5 hover:bg-ink-50 ${i.closed ? "opacity-60" : ""}`}>
                  <Badge tone={KIND_TONE[i.kind]}>{AGENDA_KIND_LABEL[i.kind]}</Badge>
                  <span className="min-w-0 flex-1">
                    <span className={`text-sm text-ink-700 ${i.closed ? "line-through" : ""}`}>{i.title}</span>
                    {i.sub && <span className="ml-2 text-xs text-ink-400">{i.sub}</span>}
                  </span>
                  {i.overdue && <Badge tone="red">Quá hạn</Badge>}
                </Link>
              ))}
            </div>
          )}
        </div>

        <div>
          <SectionTitle hint="lưu thành một việc có ngày bắt đầu">Ghi chú nhớ việc ngày {formatDate(day)}</SectionTitle>
          <ActionForm action={createTaskAction} success="Đã ghi chú." resetOnSuccess className="card flex flex-col gap-3 p-4">
            <input type="hidden" name="startDate" value={day} />
            <div>
              <label htmlFor="note-title" className="label-caps mb-1.5 block">
                Cần nhớ
              </label>
              <input id="note-title" name="title" required className="input" placeholder="Gọi lại phòng khám Ánh Dương lúc 9h" />
            </div>
            <div>
              <label htmlFor="note-desc" className="label-caps mb-1.5 block">
                Chi tiết (tuỳ chọn)
              </label>
              <textarea id="note-desc" name="description" rows={2} className="input" />
            </div>
            <div>
              <label htmlFor="note-due" className="label-caps mb-1.5 block">
                Hạn hoàn thành (tuỳ chọn)
              </label>
              <input id="note-due" name="dueDate" type="date" min={day} className="input" />
            </div>
            <button type="submit" className="btn-primary self-start">
              Ghi chú
            </button>
          </ActionForm>
        </div>
      </div>
    </>
  );
}
