/**
 * Admin · Broadcast Notification page
 *
 *   ┌─ Title ───────────────────────────────────┐
 *   ├─ Message (multiline) ─────────────────────┤
 *   ├─ Deep link route   [select: /live-tv ▾] ──┤
 *   ├─ [Send to All Users]              [Test] ─┤
 *   └─ Recent broadcasts (last 10)              ┘
 *
 * Calls POST /api/admin/broadcast-notification on the backend, which
 * fans out via Firebase Cloud Messaging HTTP v1.
 */
import { useEffect, useState } from "react";
import { useNavigate } from "react-router-dom";
import {
  ArrowLeft,
  Send,
  CircleAlert,
  CheckCircle2,
  Loader2,
  Megaphone,
  History,
  Tv,
  Film,
  Clapperboard,
  Home as HomeIcon,
  Image as ImageIcon,
  User as UserIcon,
  Users,
} from "lucide-react";

import {
  apiBroadcastNotification,
  apiListBroadcasts,
  apiListUsers,
  type BroadcastInput,
} from "@/lib/nadiAuth";

type Broadcast = {
  title: string;
  body: string;
  route?: string | null;
  total_tokens: number;
  sent: number;
  failed: number;
  pruned: number;
  created_at: string;
};

const ROUTES: { value: string; label: string; icon: typeof Tv }[] = [
  { value: "/live-tv", label: "Live TV", icon: Tv },
  { value: "/movies", label: "Movies", icon: Film },
  { value: "/series", label: "Series", icon: Clapperboard },
  { value: "/", label: "Home", icon: HomeIcon },
  { value: "", label: "No deep link", icon: HomeIcon },
];

const AdminBroadcast = () => {
  const navigate = useNavigate();
  const [title, setTitle] = useState("");
  const [body, setBody] = useState("");
  const [route, setRoute] = useState("/live-tv");
  const [imageUrl, setImageUrl] = useState("");
  const [actionLabel, setActionLabel] = useState("");
  const [targetUserId, setTargetUserId] = useState<string>(""); // "" = all
  const [users, setUsers] = useState<{ id: string; username: string }[]>([]);
  const [busy, setBusy] = useState(false);
  const [result, setResult] = useState<
    | { kind: "ok"; total: number }
    | { kind: "error"; message: string }
    | null
  >(null);
  const [history, setHistory] = useState<Broadcast[]>([]);

  const fetchHistory = async () => {
    try {
      const r = await apiListBroadcasts(10);
      setHistory(r.broadcasts || []);
    } catch (e) {
      console.warn("[broadcast] history fetch failed", e);
    }
  };

  useEffect(() => {
    void fetchHistory();
    // Best-effort load of users for the per-recipient picker. Silent on
    // failure (admin can still broadcast to all).
    apiListUsers()
      .then((res) =>
        setUsers(
          (res.users || []).map((u) => ({ id: u.id, username: u.username })),
        ),
      )
      .catch(() => setUsers([]));
  }, []);

  const submit = async (e: React.FormEvent) => {
    e.preventDefault();
    if (!title.trim() || !body.trim()) {
      setResult({ kind: "error", message: "Title and message are required." });
      return;
    }
    setBusy(true);
    setResult(null);
    try {
      const payload: BroadcastInput = {
        title: title.trim(),
        body: body.trim(),
        route: route || null,
        image_url: imageUrl.trim() || null,
        action_label: actionLabel.trim() || null,
        target_user_id: targetUserId || null,
      };
      const r = await apiBroadcastNotification(payload);
      if (!r.queued) {
        setResult({
          kind: "error",
          message: r.error || "No registered devices yet.",
        });
      } else {
        setResult({ kind: "ok", total: r.total_tokens });
        setTitle("");
        setBody("");
        setImageUrl("");
        setActionLabel("");
        // Re-fetch history after a short delay (background task ~3-5s)
        setTimeout(fetchHistory, 4000);
      }
    } catch (err) {
      const msg =
        err instanceof Error ? err.message : "Failed to queue broadcast.";
      setResult({ kind: "error", message: msg });
    } finally {
      setBusy(false);
    }
  };

  const fmtWhen = (iso: string) => {
    try {
      const d = new Date(iso);
      const now = Date.now();
      const min = Math.round((now - d.getTime()) / 60000);
      if (min < 1) return "just now";
      if (min < 60) return `${min}m ago`;
      if (min < 60 * 24) return `${Math.round(min / 60)}h ago`;
      return d.toLocaleString();
    } catch {
      return iso;
    }
  };

  return (
    <div className="relative h-screen w-full overflow-hidden">
      <div
        className="absolute inset-0 bg-cover bg-center bg-no-repeat"
        style={{ backgroundImage: "url('/images/nebula-bg.png')" }}
      />
      <div className="absolute inset-0 bg-background/65" />

      <div className="relative z-10 max-w-3xl mx-auto px-4 py-6 sm:py-8">
        {/* Header */}
        <div className="flex items-center gap-3 mb-6">
          <button
            data-testid="broadcast-back-btn"
            onClick={() => navigate("/admin")}
            className="w-10 h-10 rounded-full glass flex items-center justify-center hover:border-primary/40"
          >
            <ArrowLeft className="w-5 h-5 text-muted-foreground rtl:rotate-180" />
          </button>
          <div className="flex-1">
            <div className="flex items-center gap-2">
              <Megaphone className="w-5 h-5 text-primary" />
              <h1 className="font-display text-lg sm:text-xl tracking-[0.2em] gold-text">
                BROADCAST NOTIFICATION
              </h1>
            </div>
            <p className="text-muted-foreground text-xs mt-1">
              Push a live-match notification — or any custom message — to every signed-in
              device.
            </p>
          </div>
        </div>

        {/* Form */}
        <form
          onSubmit={submit}
          className="glass-card rounded-2xl p-5 sm:p-6 space-y-4"
          data-testid="broadcast-form"
        >
          {/* Title */}
          <div>
            <label className="block text-foreground/80 text-xs uppercase tracking-wider mb-2">
              Title
            </label>
            <input
              data-testid="broadcast-title"
              value={title}
              onChange={(e) => setTitle(e.target.value)}
              placeholder='e.g. "Real Madrid vs Barcelona — kick-off in 5 min"'
              maxLength={200}
              aria-busy={busy || undefined} data-loading={busy || undefined}
              className="w-full px-3.5 py-2.5 rounded-xl glass text-foreground placeholder:text-muted-foreground/60 focus:border-primary/60 outline-none border border-transparent transition"
            />
            <p className="text-[10px] text-muted-foreground mt-1 tabular-nums">
              {title.length}/200
            </p>
          </div>

          {/* Body */}
          <div>
            <label className="block text-foreground/80 text-xs uppercase tracking-wider mb-2">
              Message
            </label>
            <textarea
              data-testid="broadcast-body"
              value={body}
              onChange={(e) => setBody(e.target.value)}
              placeholder='e.g. "Tap to watch the match live now"'
              maxLength={1000}
              rows={4}
              aria-busy={busy || undefined} data-loading={busy || undefined}
              className="w-full px-3.5 py-2.5 rounded-xl glass text-foreground placeholder:text-muted-foreground/60 focus:border-primary/60 outline-none border border-transparent resize-none transition"
            />
            <p className="text-[10px] text-muted-foreground mt-1 tabular-nums">
              {body.length}/1000
            </p>
          </div>

          {/* Deep link route */}
          <div>
            <label className="block text-foreground/80 text-xs uppercase tracking-wider mb-2">
              Tap action — open this screen
            </label>
            <div className="grid grid-cols-2 sm:grid-cols-5 gap-2">
              {ROUTES.map((r) => {
                const Icon = r.icon;
                const active = route === r.value;
                return (
                  <button
                    type="button"
                    key={r.value}
                    data-testid={`broadcast-route-${r.value || "none"}`}
                    onClick={() => setRoute(r.value)}
                    aria-busy={busy || undefined} data-loading={busy || undefined}
                    className={`flex items-center gap-1.5 px-3 py-2 rounded-xl text-[11px] font-medium transition ${
                      active
                        ? "bg-primary/20 text-primary border border-primary/40"
                        : "glass text-muted-foreground hover:text-foreground border border-transparent"
                    }`}
                  >
                    <Icon className="w-3.5 h-3.5" />
                    {r.label}
                  </button>
                );
              })}
            </div>
          </div>

          {/* Rich notification image */}
          <div>
            <label className="block text-foreground/80 text-xs uppercase tracking-wider mb-2">
              <ImageIcon className="w-3 h-3 inline mr-1.5" />
              Image URL (optional · for live-match thumbnails)
            </label>
            <input
              data-testid="broadcast-image-url"
              type="url"
              value={imageUrl}
              onChange={(e) => setImageUrl(e.target.value)}
              placeholder="https://example.com/match-thumb.jpg"
              maxLength={2000}
              aria-busy={busy || undefined} data-loading={busy || undefined}
              className="w-full px-3.5 py-2.5 rounded-xl glass text-foreground placeholder:text-muted-foreground/60 focus:border-primary/60 outline-none border border-transparent transition"
            />
            {imageUrl && (
              <div className="mt-2 rounded-xl overflow-hidden bg-background/40 max-w-[260px]">
                <img
                  src={imageUrl}
                  alt="preview"
                  className="w-full h-32 object-cover"
                  onError={(e) =>
                    ((e.target as HTMLImageElement).style.display = "none")
                  }
                />
              </div>
            )}
          </div>

          {/* CTA / action button label */}
          <div>
            <label className="block text-foreground/80 text-xs uppercase tracking-wider mb-2">
              Action button label (optional)
            </label>
            <input
              data-testid="broadcast-action-label"
              value={actionLabel}
              onChange={(e) => setActionLabel(e.target.value)}
              placeholder='e.g. "Watch Now"'
              maxLength={30}
              aria-busy={busy || undefined} data-loading={busy || undefined}
              className="w-full px-3.5 py-2.5 rounded-xl glass text-foreground placeholder:text-muted-foreground/60 focus:border-primary/60 outline-none border border-transparent transition"
            />
          </div>

          {/* Recipient — all vs single user */}
          <div>
            <label className="block text-foreground/80 text-xs uppercase tracking-wider mb-2">
              Recipient
            </label>
            <div className="flex flex-wrap gap-2">
              <button
                type="button"
                data-testid="broadcast-target-all"
                onClick={() => setTargetUserId("")}
                aria-busy={busy || undefined} data-loading={busy || undefined}
                className={`flex items-center gap-1.5 px-3 py-2 rounded-xl text-[11px] font-medium transition ${
                  !targetUserId
                    ? "bg-primary/20 text-primary border border-primary/40"
                    : "glass text-muted-foreground hover:text-foreground border border-transparent"
                }`}
              >
                <Users className="w-3.5 h-3.5" />
                All users
              </button>
              {users.length > 0 && (
                <select
                  data-testid="broadcast-target-user"
                  value={targetUserId}
                  onChange={(e) => setTargetUserId(e.target.value)}
                  aria-busy={busy || undefined} data-loading={busy || undefined}
                  className="flex-1 px-3 py-2 rounded-xl glass text-foreground text-[11px] outline-none border border-transparent focus:border-primary/40"
                >
                  <option value="">— Single user —</option>
                  {users.map((u) => (
                    <option key={u.id} value={u.id}>
                      {u.username}
                    </option>
                  ))}
                </select>
              )}
            </div>
            {targetUserId && (
              <p className="mt-1.5 text-[10px] text-primary flex items-center gap-1">
                <UserIcon className="w-3 h-3" />
                Sending only to{" "}
                <span className="font-medium">
                  {users.find((u) => u.id === targetUserId)?.username ||
                    targetUserId}
                </span>
              </p>
            )}
          </div>

          {/* Result banner */}
          {result?.kind === "ok" && (
            <div className="flex items-start gap-2 p-3 rounded-xl bg-primary/10 border border-primary/30">
              <CheckCircle2 className="w-4 h-4 text-primary mt-0.5 shrink-0" />
              <p className="text-primary text-xs">
                Queued to <span className="tabular-nums">{result.total}</span>{" "}
                device{result.total === 1 ? "" : "s"}. Delivery typically
                completes in 1–5 minutes; offline devices receive the
                notification when they reconnect.
              </p>
            </div>
          )}
          {result?.kind === "error" && (
            <div className="flex items-start gap-2 p-3 rounded-xl bg-destructive/15 border border-destructive/40">
              <CircleAlert className="w-4 h-4 text-destructive mt-0.5 shrink-0" />
              <p className="text-destructive text-xs">{result.message}</p>
            </div>
          )}

          {/* Submit */}
          <button
            type="submit"
            aria-busy={busy || undefined} data-loading={busy || undefined}
            data-testid="broadcast-send-btn"
            className="w-full flex items-center justify-center gap-2 px-4 py-3 rounded-xl bg-primary text-primary-foreground font-medium disabled:bg-primary/50 disabled:cursor-not-allowed hover:bg-primary/90 transition"
          >
            {busy ? (
              <>
                <Loader2 className="w-4 h-4 animate-spin" /> Sending…
              </>
            ) : targetUserId ? (
              <>
                <Send className="w-4 h-4" /> Send to selected user
              </>
            ) : (
              <>
                <Send className="w-4 h-4" /> Send to All Users
              </>
            )}
          </button>
        </form>

        {/* History */}
        <div
          className="glass-card rounded-2xl p-5 sm:p-6 mt-6"
          data-testid="broadcast-history"
        >
          <div className="flex items-center gap-2 mb-3">
            <History className="w-4 h-4 text-muted-foreground" />
            <h2 className="text-foreground/90 text-sm tracking-wide">
              Recent broadcasts
            </h2>
          </div>
          {history.length === 0 ? (
            <p className="text-muted-foreground text-xs py-3">
              No broadcasts sent yet.
            </p>
          ) : (
            <ul className="divide-y divide-border/50">
              {history.map((b, i) => (
                <li
                  key={`${b.created_at}-${i}`}
                  className="py-2.5 flex items-start gap-3"
                >
                  <div className="w-9 h-9 rounded-lg bg-primary/10 flex items-center justify-center shrink-0">
                    <Megaphone className="w-4 h-4 text-primary" />
                  </div>
                  <div className="flex-1 min-w-0">
                    <p className="text-foreground text-sm font-medium truncate">
                      {b.title}
                    </p>
                    <p className="text-muted-foreground text-[11px] truncate">
                      {b.body}
                    </p>
                    <div className="flex items-center gap-3 mt-1 text-[10px] text-muted-foreground tabular-nums">
                      <span>{fmtWhen(b.created_at)}</span>
                      <span className="text-primary">{b.sent} sent</span>
                      {b.failed > 0 && (
                        <span className="text-destructive">
                          {b.failed} failed
                        </span>
                      )}
                      {b.pruned > 0 && (
                        <span>{b.pruned} pruned</span>
                      )}
                      {b.route && (
                        <span className="px-1.5 py-0.5 rounded bg-primary/10 text-primary">
                          → {b.route}
                        </span>
                      )}
                    </div>
                  </div>
                </li>
              ))}
            </ul>
          )}
        </div>
      </div>
    </div>
  );
};

export default AdminBroadcast;
