"use client";
import { useCallback, useEffect, useState } from "react";
import Link from "next/link";
import { Button, Popover } from "@heroui/react";
import { Bell } from "lucide-react";
import { cargarNotificaciones, actualizarNotificaciones } from "@/app/actions/notificaciones";
import type { PersistentNotice } from "@/lib/aula/notification-schema";
import SystemAlert from "@/components/ui/SystemAlert";
import { useSystemNotifications } from "@/components/ui/SystemNotifications";
export default function NotificationMenu({ scope }: { scope?: number }) {
  const [items, setItems] = useState<PersistentNotice[]>([]);
  const [error, setError] = useState("");
  const [loading, setLoading] = useState(true);
  const [open, setOpen] = useState(false);
  const { notifications, markRead, clearNotifications } = useSystemNotifications();
  const refresh = useCallback(async () => {
    try {
      const result = await cargarNotificaciones();
      if (result.notices) {
        setItems(result.notices);
        setError("");
      } else setError(result.error ?? "No fue posible consultar los avisos.");
    } catch {
      setError("No fue posible consultar los avisos.");
    } finally {
      setLoading(false);
    }
  }, []);
  useEffect(() => {
    const initial = window.setTimeout(() => void refresh(), 0);
    const timer = setInterval(() => {
      if (document.visibilityState === "visible") void refresh();
    }, 60000);
    const focus = () => void refresh();
    window.addEventListener("focus", focus);
    return () => {
      window.clearTimeout(initial);
      clearInterval(timer);
      window.removeEventListener("focus", focus);
    };
  }, [refresh, scope]);
  const unread = items.filter((n) => !n.read).length + notifications.filter((n) => n.unread).length;
  useEffect(() => {
    if (!open) return;
    const ids = items.filter((n) => !n.read).map((n) => n.id);
    if (!ids.length) return;
    let active = true;
    actualizarNotificaciones(ids)
      .then((result) => {
        if (!active) return;
        if (result.error) setError(result.error);
        else
          setItems((current) =>
            current.map((n) => (ids.includes(n.id) ? { ...n, read: true } : n)),
          );
      })
      .catch(() => {
        if (active) setError("No fue posible marcar los avisos como leídos.");
      });
    return () => {
      active = false;
    };
  }, [open, items]);
  return (
    <Popover
      isOpen={open}
      onOpenChange={(value) => {
        setOpen(value);
        if (value) markRead();
      }}
    >
      <Button
        variant="ghost"
        isIconOnly
        aria-label={unread ? `Notificaciones, ${unread} sin leer` : "Notificaciones"}
        className="relative size-9 rounded-full text-muted"
      >
        <Bell className="size-4.5" />
        {unread > 0 && (
          <span className="absolute right-1 top-1 size-2 rounded-full bg-accent ring-2 ring-surface" />
        )}
      </Button>
      <Popover.Content placement="bottom end" className="w-[min(25rem,calc(100vw-2rem))]">
        <Popover.Dialog className="space-y-4 p-4">
          <div className="flex items-center justify-between gap-2">
            <Popover.Heading className="text-sm font-semibold">Notificaciones</Popover.Heading>
            <Button
              size="sm"
              variant="ghost"
              className="rounded-full"
              onPress={() => void refresh()}
            >
              Actualizar
            </Button>
          </div>
          <p className="text-xs text-muted">Tareas, calificaciones y conversaciones de tus aulas</p>
          {error && (
            <SystemAlert status="warning" title="Avisos sin actualizar">
              {error}
            </SystemAlert>
          )}
          {loading ? (
            <SystemAlert status="accent" title="Consultando avisos" loading />
          ) : (
            <div className="max-h-96 space-y-3 overflow-y-auto">
              {!items.length && !notifications.length && !error && (
                <p className="py-6 text-center text-sm text-muted">Sin notificaciones nuevas</p>
              )}
              {notifications.map((n) => (
                <SystemAlert key={n.id} title={n.title} status={n.status}>
                  {n.children}
                </SystemAlert>
              ))}
              {items.map((n) => (
                <div key={n.id} className="space-y-2 border-b border-separator pb-3 last:border-0">
                  <Link
                    href={n.href}
                    onClick={() => setOpen(false)}
                    className="block rounded-xl outline-none focus-visible:ring-2 focus-visible:ring-accent"
                  >
                    <SystemAlert status={n.status} title={n.title}>
                      {n.body}
                    </SystemAlert>
                  </Link>
                  <time className="block text-[10px] text-muted" dateTime={n.date}>
                    {new Date(n.date).toLocaleString("es-MX", {
                      timeZone: "America/Mexico_City",
                      dateStyle: "medium",
                      timeStyle: "short",
                    })}
                  </time>
                </div>
              ))}
            </div>
          )}
          {(items.length > 0 || notifications.length > 0) && (
            <Button
              variant="secondary"
              className="w-full rounded-full"
              size="sm"
              onPress={async () => {
                try {
                  const result = await actualizarNotificaciones(
                    items.map((n) => n.id),
                    true,
                  );
                  if (result.error) setError(result.error);
                  else {
                    setItems([]);
                    clearNotifications();
                  }
                } catch {
                  setError("No se pudieron limpiar los avisos.");
                }
              }}
            >
              Limpiar avisos
            </Button>
          )}
        </Popover.Dialog>
      </Popover.Content>
    </Popover>
  );
}
