import { useEffect, useState } from "react";
import { Link } from "@tanstack/react-router";
import { Calendar, Flag, Gift, Shield } from "lucide-react";
import { toast } from "sonner";
import { DeskHero, DeskSkeleton, StatTile } from "@/components/desk-hero";
import { DealRoomPanel } from "@/components/stadium/deal-room";
import { DisneyWalkCard } from "@/components/stadium/disney-walk";
import { AuctionPaddle } from "@/components/stadium/auction-paddle";
import { StadiumLiveStrip } from "@/components/stadium/live-strip";
import { BioLink } from "@/components/public-shell";
import { HonorGiftForm } from "@/components/honor-gift";
import { StaffEditField } from "@/components/staff-edit";
import { Badge } from "@/components/ui/badge";
import { Button } from "@/components/ui/button";
import { Card, CardContent } from "@/components/ui/card";
import { firstName } from "@/lib/identity";
import { getDonorDesk, rsvpGameDay } from "@/lib/server/api-public";
import { formatDate, formatDateTime, moneyCents } from "@/lib/utils";

type Desk = Awaited<ReturnType<typeof getDonorDesk>>;
type DonorDesk = Extract<Desk, { user: { id: string } }>;
export type DonorSection = "all" | "projects" | "invites";

const TIER_LABEL: Record<string, string> = {
  founding: "Founding donor",
  champion: "Champion",
  sideline: "Sideline",
};

const ACCESS_LABEL: Record<string, string> = {
  studio: "Studio brief",
  featured: "Featured",
};

function educationFirst<T extends { name: string }>(projects: T[]) {
  return [...projects].sort((a, b) => rankProject(a.name) - rankProject(b.name));
}

function rankProject(name: string) {
  const n = name.toLowerCase();
  if (n.includes("thermal") || n.includes("suture")) return 0;
  if (n.includes("rib") || n.includes("splint")) return 1;
  if (n.includes("helmet")) return 2;
  return 3;
}

function dealSlug(p: { name: string; slug: string; capstone_slug: string | null }) {
  if (p.capstone_slug) return p.capstone_slug;
  const n = p.name.toLowerCase();
  if (n.includes("thermal") || n.includes("suture")) return "thermal-suture-cutter";
  if (n.includes("rib") || n.includes("splint")) return "sternotomy-rib-splint";
  if (n.includes("helmet")) return "integrated-helmet-platform";
  return p.slug;
}

const RSVP_LABEL: Record<string, string> = {
  invited: "Invited",
  rsvp_yes: "In",
  rsvp_no: "Can’t make it",
};

export function DonorHome({
  email,
  section = "all",
}: {
  email: string;
  section?: DonorSection;
}) {
  const [data, setData] = useState<Desk | null>(null);

  useEffect(() => {
    let live = true;
    setData(null);
    void getDonorDesk({ data: { email } }).then((d) => {
      if (live) setData(d);
    });
    return () => {
      live = false;
    };
  }, [email]);

  if (!data) return <DeskSkeleton />;
  if (!data.user) {
    return <p className="text-sm text-muted-foreground">No donor record is attached to this account.</p>;
  }

  const { user, profile, projects, updates, roster, invites, gifts } = data;
  const showAll = section === "all";
  const given = gifts.reduce((s, g) => s + g.amount_cents, 0);
  const openInvites = invites.filter((i) => i.status === "invited").length;

  async function reload() {
    setData(await getDonorDesk({ data: { email } }));
  }

  async function rsvp(inviteId: string, status: "rsvp_yes" | "rsvp_no") {
    try {
      await rsvpGameDay({ data: { email, inviteId, status } });
      toast.success(status === "rsvp_yes" ? "You’re in for Game Day." : "We’ll keep the seat for someone else.");
      const next = await getDonorDesk({ data: { email } });
      setData(next);
    } catch (err) {
      toast.error(err instanceof Error ? err.message : "Could not save RSVP");
    }
  }

  return (
    <div className="stagger-in">
      {showAll ? (
        <DeskHero
          kicker={`Donor view · ${TIER_LABEL[profile?.giving_tier ?? "sideline"]}`}
          title={`Welcome in, ${firstName(user.full_name)}`}
          description={
            profile?.notes ??
            "Education first: studio projects, then your seat, then memorabilia. The public site never shows a private bio."
          }
          badge={profile?.organization ?? "Donor"}
        />
      ) : null}

      {showAll ? (
        <div className="mb-6 grid gap-3 sm:grid-cols-3">
          <StatTile
            icon={Flag}
            label="Invited projects"
            value={projects.length}
            hint="Studio briefings you are cleared to see"
          />
          <StatTile icon={Calendar} label="Open invites" value={openInvites} hint="Game Days waiting on an RSVP" />
          <StatTile icon={Gift} label="Gifts on record" value={moneyCents(given)} hint="Education-program restricted where noted" />
        </div>
      ) : null}

      {section === "all" || section === "projects" ? (
        <div className="mb-8 space-y-6">
          {showAll ? (
            <p className="text-[11px] font-medium tracking-[0.18em] text-primary uppercase">Studio projects · education first</p>
          ) : null}
          {educationFirst(projects).map((p) => {
            const people = roster.filter((r) => r.team_id === p.id);
            const notes = updates.filter((u) => u.team_id === p.id);
            return (
              <Card key={p.id}>
                <CardContent className="pt-5">
                  <div className="mb-3 flex flex-wrap items-center gap-2">
                    <Badge>{ACCESS_LABEL[p.access_level] ?? p.access_level}</Badge>
                    <Badge variant="outline">{p.category}</Badge>
                    {p.stage_label ? <Badge variant="muted">{p.stage_label}</Badge> : null}
                  </div>
                  <h2 className="font-display text-2xl">{p.name}</h2>
                  <p className="mt-2 text-sm text-muted-foreground">{p.venture_summary}</p>
                  <div className="mt-2 flex flex-wrap gap-2">
                    <StaffEditField
                      table="teams"
                      id={p.id}
                      field="venture_summary"
                      value={p.venture_summary}
                      label="project summary"
                      onSaved={reload}
                    />
                    <StaffEditField
                      table="teams"
                      id={p.id}
                      field="donor_brief"
                      value={p.donor_brief}
                      label="donor briefing"
                      onSaved={reload}
                    />
                  </div>
                  {p.donor_brief ? (
                    <div className="mt-4 rounded-lg bg-primary/8 p-4">
                      <p className="text-[11px] font-medium tracking-[0.16em] text-primary uppercase">
                        Donor briefing
                      </p>
                      <p className="mt-1 text-sm">{p.donor_brief}</p>
                    </div>
                  ) : null}
                  <div className="mt-4">
                    <DealRoomPanel slug={dealSlug(p)} />
                  </div>
                  <p className="mt-3 text-xs text-muted-foreground">
                    CFL takes no equity in this venture. This briefing is a donation packet, not an investment offering.
                  </p>
                  <HonorGiftForm
                    email={email}
                    donorName={user.full_name}
                    projectName={p.name}
                    teamId={p.id}
                    professorExample={p.name.toLowerCase().includes("helmet") ? "Dr. Priya Shah" : "Dana Ortiz, Head coach"}
                  />
                  <ul className="mt-4 space-y-2">
                    {people.map((person) => (
                      <li key={person.member_id} className="flex items-center gap-2.5">
                        <span className="flex size-8 items-center justify-center rounded-full bg-secondary text-xs font-semibold">
                          {person.avatar_initials}
                        </span>
                        <span className="min-w-0 flex-1 truncate text-sm">{person.full_name}</span>
                        <BioLink slug={person.public_slug} publicBio={person.public_bio} />
                      </li>
                    ))}
                  </ul>
                  {notes.length > 0 ? (
                    <ul className="mt-4 space-y-3 border-t border-border pt-4">
                      {notes.map((n) => (
                        <li key={n.id}>
                          <div className="flex flex-wrap items-center gap-2">
                            <p className="text-sm font-semibold">{n.title}</p>
                            {n.audience === "donors" ? <Badge variant="default">Donors</Badge> : <Badge variant="outline">Public</Badge>}
                          </div>
                          <p className="mt-1 text-sm text-muted-foreground">{n.body}</p>
                        </li>
                      ))}
                    </ul>
                  ) : null}
                  <Button asChild variant="outline" className="mt-4">
                    <Link to="/public/teams/$slug" params={{ slug: p.slug }}>
                      Public project page
                    </Link>
                  </Button>
                </CardContent>
              </Card>
            );
          })}
        </div>
      ) : null}

      {showAll ? (
        <>
          <p className="mb-3 text-[11px] font-medium tracking-[0.18em] text-primary uppercase">Your seat</p>
          <DisneyWalkCard audience="donor" />
          <p className="mb-3 text-[11px] font-medium tracking-[0.18em] text-primary uppercase">Sports memorabilia</p>
          <AuctionPaddle compact />
          <div className="mb-6 grid gap-6 lg:grid-cols-2">
            <InvitesCard invites={invites} onRsvp={rsvp} />
            <GiftsCard gifts={gifts} restrictedTo={profile?.restricted_to} />
          </div>
          <p className="mb-3 text-[11px] font-medium tracking-[0.18em] text-primary uppercase">Enter the stadium</p>
          <StadiumLiveStrip />
        </>
      ) : null}

      {section === "invites" ? <InvitesCard invites={invites} onRsvp={rsvp} detailed /> : null}
    </div>
  );
}

function InvitesCard({
  invites,
  onRsvp,
  detailed,
}: {
  invites: DonorDesk["invites"];
  onRsvp: (id: string, status: "rsvp_yes" | "rsvp_no") => void;
  detailed?: boolean;
}) {
  return (
    <Card>
      <CardContent className="pt-5">
        <div className="mb-3 flex items-center justify-between gap-2">
          <div className="flex items-center gap-2">
            <Calendar className="size-4 text-primary" />
            <h2 className="font-display text-xl">Game Day invites</h2>
          </div>
          <Link to="/donor/invites" className="text-sm text-primary hover:underline">
            All invites
          </Link>
        </div>
        <ul className="space-y-4">
          {invites.map((e) => (
            <li key={e.id} className="rounded-lg bg-muted/70 p-3">
              <div className="flex flex-wrap items-center gap-2">
                <p className="text-sm font-semibold">{e.title}</p>
                <Badge variant={e.status === "rsvp_yes" ? "success" : e.status === "rsvp_no" ? "muted" : "warning"}>
                  {RSVP_LABEL[e.status] ?? e.status}
                </Badge>
              </div>
              <p className="mt-1 text-xs text-muted-foreground">
                {formatDateTime(e.starts_at)} · {e.location}
              </p>
              {detailed && e.notes ? <p className="mt-2 text-sm text-muted-foreground">{e.notes}</p> : null}
              {e.note ? <p className="mt-1 text-sm text-muted-foreground">{e.note}</p> : null}
              <div className="mt-3 flex flex-wrap gap-2">
                <Button size="sm" onClick={() => onRsvp(e.id, "rsvp_yes")}>
                  I’ll be there
                </Button>
                <Button size="sm" variant="outline" onClick={() => onRsvp(e.id, "rsvp_no")}>
                  Can’t make it
                </Button>
              </div>
            </li>
          ))}
          {invites.length === 0 ? (
            <li className="text-sm text-muted-foreground">No Game Day invites on this account yet.</li>
          ) : null}
        </ul>
      </CardContent>
    </Card>
  );
}

function GiftsCard({
  gifts,
  restrictedTo,
}: {
  gifts: DonorDesk["gifts"];
  restrictedTo?: string | null;
}) {
  return (
    <Card>
      <CardContent className="pt-5">
        <div className="mb-3 flex items-center gap-2">
          <Shield className="size-4 text-primary" />
          <h2 className="font-display text-xl">Your gifts</h2>
        </div>
        {restrictedTo ? (
          <p className="mb-3 text-sm text-muted-foreground">Restricted to: {restrictedTo}</p>
        ) : null}
        <ul className="divide-y divide-border">
          {gifts.map((g) => (
            <li key={g.id} className="flex items-start justify-between gap-3 py-3 first:pt-0 last:pb-0">
              <div>
                <p className="text-sm font-medium">{g.campaign ?? "Gift"}</p>
                <p className="text-xs text-navy">{formatDate(g.received_at)}</p>
                {g.restriction_note ? <p className="mt-1 text-xs text-navy">{g.restriction_note}</p> : null}
              </div>
              <p className="tabular text-sm font-semibold">{moneyCents(g.amount_cents)}</p>
            </li>
          ))}
          {gifts.length === 0 ? (
            <li className="text-sm text-muted-foreground">No gifts on this email yet.</li>
          ) : null}
        </ul>
      </CardContent>
    </Card>
  );
}
