import { useState, useEffect, useCallback } from "react";
import { supabase } from "@/integrations/supabase/client";
import { Card, CardContent, CardHeader, CardTitle } from "@/components/ui/card";
import { Button } from "@/components/ui/button";
import { Badge } from "@/components/ui/badge";
import { Select, SelectContent, SelectItem, SelectTrigger, SelectValue } from "@/components/ui/select";
import { Dialog, DialogContent, DialogHeader, DialogTitle } from "@/components/ui/dialog";
import { Inbox, FileText, ShieldAlert, MessageCircle, Loader2, Archive, Eye, CheckCircle, Clock, RotateCcw, Trash2, CalendarDays, Download, UserPlus, XCircle, Mail, Link as LinkIcon, ShieldCheck, Search } from "lucide-react";
import { Input } from "@/components/ui/input";
import { Switch } from "@/components/ui/switch";
import { Label } from "@/components/ui/label";
import { format, formatDistanceToNow } from "date-fns";
import { useToast } from "@/hooks/use-toast";
import jsPDF from "jspdf";
import VotingAndComments from "@/components/shared/VotingAndComments";

const sourceIcons: Record<string, typeof FileText> = {
  public_form: FileText,
  violation_response: ShieldAlert,
  client_request: MessageCircle,
  homeowner_ticket: MessageCircle,
  registration_request: UserPlus,
  reservation: CalendarDays,
  avriacam_contact: Mail,
};

const sourceLabels: Record<string, string> = {
  public_form: "Public Form",
  violation_response: "Violation Response",
  client_request: "Homeowner Request",
  homeowner_ticket: "Homeowner Ticket",
  registration_request: "Registration Request",
  reservation: "Reservation",
  avriacam_contact: "Avriacam.com Contact",
};

const statusStyles: Record<string, string> = {
  new: "cc-badge-danger",
  in_progress: "cc-badge-warning",
  resolved: "cc-badge-success",
  archived: "cc-badge-neutral",
};

interface InboxItem {
  id: string;
  source_type: string;
  source_id: string;
  association_id: string | null;
  title: string;
  submitter_name: string | null;
  submitter_email: string | null;
  summary: string | null;
  status: string;
  created_at: string;
  updated_at: string;
  reviewed_by: string | null;
  reviewed_at: string | null;
}

export default function FormInboxPage() {
  const [items, setItems] = useState<InboxItem[]>([]);
  const [loading, setLoading] = useState(true);
  const [statusFilter, setStatusFilter] = useState<string>("active");
  const [sourceFilter, setSourceFilter] = useState<string>("all");
  const [selectedItem, setSelectedItem] = useState<InboxItem | null>(null);
  const [detailData, setDetailData] = useState<any>(null);
  const [detailLoading, setDetailLoading] = useState(false);
  const [candidateOwners, setCandidateOwners] = useState<any[]>([]);
  const [selectedOwnerId, setSelectedOwnerId] = useState<string>("");
  const [approving, setApproving] = useState(false);
  const [rejecting, setRejecting] = useState(false);
  // Override mode: search ANY active owner across all associations + edit request fields
  const [overrideMode, setOverrideMode] = useState(false);
  const [overrideSearch, setOverrideSearch] = useState("");
  const [overrideOwners, setOverrideOwners] = useState<any[]>([]);
  const [overrideSearching, setOverrideSearching] = useState(false);
  const [editEmail, setEditEmail] = useState("");
  const [editUnitIdentifier, setEditUnitIdentifier] = useState("");
  const { toast } = useToast();

  const fetchItems = useCallback(async () => {
    setLoading(true);
    let query = supabase
      .from("form_inbox")
      .select("*")
      .order("created_at", { ascending: false })
      .limit(100);

    if (statusFilter === "active") {
      query = query.in("status", ["new", "in_progress"]);
    } else if (statusFilter !== "all") {
      query = query.eq("status", statusFilter);
    }

    if (sourceFilter !== "all") {
      query = query.eq("source_type", sourceFilter);
    }

    const { data, error } = await query;
    if (error) {
      toast({ title: "Error", description: error.message, variant: "destructive" });
    } else {
      setItems(data || []);
    }
    setLoading(false);
  }, [statusFilter, sourceFilter, toast]);

  useEffect(() => {
    fetchItems();

    const channel = supabase
      .channel("form-inbox-page")
      .on("postgres_changes", { event: "*", schema: "public", table: "form_inbox" }, () => {
        fetchItems();
      })
      .subscribe();

    return () => { supabase.removeChannel(channel); };
  }, [fetchItems]);

  // Debounced override owner search across ALL active owners
  useEffect(() => {
    if (!overrideMode) return;
    const term = overrideSearch.trim();
    if (term.length < 2) { setOverrideOwners([]); return; }
    setOverrideSearching(true);
    const handle = setTimeout(async () => {
      const { data } = await supabase
        .from("owners")
        .select("id, first_name, last_name, email, unit_id, association_id, user_id, exclude_from_signin, property_address, units(unit_number, address), associations(name)")
        .eq("status", "active")
        .or(`first_name.ilike.%${term}%,last_name.ilike.%${term}%,email.ilike.%${term}%,property_address.ilike.%${term}%`)
        .order("last_name", { ascending: true })
        .limit(50);
      setOverrideOwners(data || []);
      setOverrideSearching(false);
    }, 300);
    return () => clearTimeout(handle);
  }, [overrideSearch, overrideMode]);

  const updateStatus = async (id: string, status: string) => {
    const { error } = await supabase
      .from("form_inbox")
      .update({ status, reviewed_at: new Date().toISOString() })
      .eq("id", id);

    if (error) {
      toast({ title: "Error", description: error.message, variant: "destructive" });
    } else {
      toast({ title: "Updated", description: `Item marked as ${status}` });
      if (selectedItem?.id === id) {
        setSelectedItem((prev) => prev ? { ...prev, status } : null);
      }
    }
  };

  const deleteItem = async (id: string) => {
    const { error } = await supabase.from("form_inbox").delete().eq("id", id);
    if (error) {
      toast({ title: "Error", description: error.message, variant: "destructive" });
    } else {
      toast({ title: "Deleted", description: "Item removed from inbox" });
      if (selectedItem?.id === id) setSelectedItem(null);
    }
  };

  const approveRegistration = async () => {
    if (!detailData) return;
    if (!detailData.owner_id && !selectedOwnerId) {
      toast({ title: "Select an owner", description: "Choose which owner record to link this account to.", variant: "destructive" });
      return;
    }
    setApproving(true);
    try {
      // Look across both candidate and override owner pools
      const allKnown = [...candidateOwners, ...overrideOwners];
      const picked = selectedOwnerId ? allKnown.find((o) => o.id === selectedOwnerId) : null;

      // Build the patch: edited request fields (override mode) + chosen owner link
      const patch: Record<string, any> = {};
      const trimmedEmail = editEmail.trim();
      const trimmedUnit = editUnitIdentifier.trim();
      if (overrideMode) {
        if (trimmedEmail && trimmedEmail.toLowerCase() !== (detailData.email || "").toLowerCase()) {
          patch.email = trimmedEmail.toLowerCase();
        }
        if (trimmedUnit !== (detailData.unit_identifier || "")) {
          patch.unit_identifier = trimmedUnit || null;
        }
      }
      if (selectedOwnerId && selectedOwnerId !== detailData.owner_id) {
        patch.owner_id = selectedOwnerId;
        patch.unit_id = picked?.unit_id || detailData.unit_id;
        patch.association_id = picked?.association_id || detailData.association_id;
      }
      if (Object.keys(patch).length > 0) {
        await (supabase as any)
          .from("owner_registration_requests")
          .update(patch)
          .eq("id", detailData.id);
      }

      const { data, error } = await supabase.functions.invoke("homeowner-signup", {
        body: { action: "approve_request", request_id: detailData.id },
      });
      if (error) throw error;
      if (data?.error) throw new Error(data.error);

      toast({
        title: "Account approved",
        description: data?.email_sent
          ? "Owner has been linked and a password setup email was sent."
          : data?.warning || "Owner linked. Email could not be sent — share the setup link manually.",
      });

      // Mark the inbox item resolved and refresh
      if (selectedItem) await updateStatus(selectedItem.id, "resolved");
      setSelectedItem(null);
      fetchItems();
    } catch (err: any) {
      toast({ title: "Approval failed", description: err.message || "Could not approve registration", variant: "destructive" });
    } finally {
      setApproving(false);
    }
  };

  const rejectRegistration = async () => {
    if (!detailData) return;
    setRejecting(true);
    try {
      const { data, error } = await supabase.functions.invoke("homeowner-signup", {
        body: { action: "reject_request", request_id: detailData.id },
      });
      if (error) throw error;
      if (data?.error) throw new Error(data.error);
      toast({ title: "Registration rejected" });
      if (selectedItem) await updateStatus(selectedItem.id, "archived");
      setSelectedItem(null);
      fetchItems();
    } catch (err: any) {
      toast({ title: "Rejection failed", description: err.message || "Could not reject registration", variant: "destructive" });
    } finally {
      setRejecting(false);
    }
  };

  const openDetail = async (item: InboxItem) => {
    setSelectedItem(item);
    setDetailLoading(true);
    setDetailData(null);

    try {
      if (item.source_type === "public_form") {
        const { data } = await supabase
          .from("public_form_submissions")
          .select("*, public_form_templates(title, fields)")
          .eq("id", item.source_id)
          .single();
        setDetailData(data);
      } else if (item.source_type === "violation_response") {
        const { data } = await supabase
          .from("violation_responses")
          .select("*, violations(address, title, category, violation_type)")
          .eq("id", item.source_id)
          .single();
        setDetailData(data);
      } else if (item.source_type === "client_request") {
        const { data } = await supabase
          .from("client_requests")
          .select("*")
          .eq("id", item.source_id)
          .single();
        setDetailData(data);
      } else if (item.source_type === "homeowner_ticket") {
        const { data } = await supabase
          .from("homeowner_requests")
          .select("*, owners(first_name, last_name)")
          .eq("id", item.source_id)
          .single();
        setDetailData(data);
      } else if (item.source_type === "registration_request") {
        const { data } = await (supabase as any)
          .from("owner_registration_requests")
          .select("*, owners(first_name, last_name, property_address), units(unit_number, address), associations(name)")
          .eq("id", item.source_id)
          .single();
        setDetailData(data);
        setSelectedOwnerId(data?.owner_id || "");
        setEditEmail(data?.email || "");
        setEditUnitIdentifier(data?.unit_identifier || "");
        setOverrideMode(false);
        setOverrideSearch("");
        setOverrideOwners([]);

        // Load candidate owners (same unit/association) so staff can pick if no auto-match
        let candidatesQuery = supabase
          .from("owners")
          .select("id, first_name, last_name, email, unit_id, association_id, user_id, exclude_from_signin, property_address, units(unit_number, address)")
          .eq("status", "active")
          .order("last_name", { ascending: true })
          .limit(50);
        if (data?.unit_id) {
          candidatesQuery = candidatesQuery.eq("unit_id", data.unit_id);
        } else if (data?.association_id) {
          candidatesQuery = candidatesQuery.eq("association_id", data.association_id).ilike("last_name", `%${data.last_name || ""}%`);
        } else {
          candidatesQuery = candidatesQuery.ilike("last_name", `%${data?.last_name || ""}%`);
        }
        const { data: candidates } = await candidatesQuery;
        setCandidateOwners(candidates || []);
      } else if (item.source_type === "reservation") {
        const { data } = await supabase
          .from("amenity_bookings")
          .select("*, amenities(name, map_config)")
          .eq("id", item.source_id)
          .single();
        setDetailData(data);
      }
    } catch (err) {
      console.error("Error loading detail:", err);
    }

    // Mark as in_progress if new
    if (item.status === "new") {
      updateStatus(item.id, "in_progress");
    }

    setDetailLoading(false);
  };

  const renderDetailContent = () => {
    if (detailLoading) return <div className="flex justify-center py-8"><Loader2 className="h-5 w-5 animate-spin text-muted-foreground" /></div>;
    if (!detailData) return <p className="text-sm text-muted-foreground">Could not load details.</p>;

    if (selectedItem?.source_type === "public_form") {
      const fields = (detailData.public_form_templates as any)?.fields || [];
      const formData = detailData.form_data || {};
      return (
        <div className="space-y-3">
          <h4 className="text-sm font-semibold">Form: {(detailData.public_form_templates as any)?.title}</h4>
          <div className="divide-y divide-border rounded-md border">
            {fields.filter((f: any) => f.type !== "header" && f.type !== "divider").map((field: any) => (
              <div key={field.id} className="flex justify-between px-3 py-2 text-sm">
                <span className="text-muted-foreground">{field.label}</span>
                <span className="font-medium text-right max-w-[60%] truncate">{String(formData[field.id] ?? "—")}</span>
              </div>
            ))}
          </div>
          {detailData.submitter_name && <p className="text-xs text-muted-foreground">Submitted by: {detailData.submitter_name} {detailData.submitter_email ? `(${detailData.submitter_email})` : ""}</p>}
        </div>
      );
    }

    if (selectedItem?.source_type === "violation_response") {
      return (
        <div className="space-y-3">
          <h4 className="text-sm font-semibold">Violation Response</h4>
          {detailData.violations && (
            <p className="text-sm text-muted-foreground">
              Property: {(detailData.violations as any)?.address} · Type: {(detailData.violations as any)?.category || (detailData.violations as any)?.violation_type || (detailData.violations as any)?.title}
            </p>
          )}
          <div className="rounded-md border p-3 text-sm whitespace-pre-wrap">{detailData.response_text || "No response text"}</div>
          {detailData.respondent_name && <p className="text-xs text-muted-foreground">From: {detailData.respondent_name} {detailData.respondent_email ? `(${detailData.respondent_email})` : ""}</p>}
          {detailData.date_corrected && <p className="text-xs text-muted-foreground">Date corrected: {format(new Date(detailData.date_corrected), "MMM d, yyyy")}</p>}
        </div>
      );
    }

    if (selectedItem?.source_type === "client_request") {
      return (
        <div className="space-y-3">
          <h4 className="text-sm font-semibold">{detailData.title}</h4>
          {detailData.priority && (
            <Badge variant="outline" className="text-2xs">{detailData.priority}</Badge>
          )}
          <div className="rounded-md border p-3 text-sm whitespace-pre-wrap">{detailData.description || "No description"}</div>
          {detailData.requester_name && <p className="text-xs text-muted-foreground">From: {detailData.requester_name} {detailData.requester_email ? `(${detailData.requester_email})` : ""}</p>}
        </div>
      );
    }

    if (selectedItem?.source_type === "homeowner_ticket") {
      const ownerName = detailData.owners ? `${detailData.owners.first_name || ""} ${detailData.owners.last_name || ""}`.trim() : "";
      return (
        <div className="space-y-3">
          <h4 className="text-sm font-semibold">{detailData.title}</h4>
          <div className="flex flex-wrap gap-2">
            {detailData.category && <Badge variant="secondary" className="text-2xs capitalize">{detailData.category}</Badge>}
            {detailData.priority && <Badge variant="outline" className="text-2xs capitalize">{detailData.priority}</Badge>}
          </div>
          <div className="rounded-md border p-3 text-sm whitespace-pre-wrap">{detailData.description || "No description"}</div>
          {ownerName && <p className="text-xs text-muted-foreground">From: {ownerName}</p>}
          <VotingAndComments entityType="homeowner_request" entityId={detailData.id} />
        </div>
      );
    }

    if (selectedItem?.source_type === "registration_request") {
      const ownerName = detailData.owners ? `${detailData.owners.first_name || ""} ${detailData.owners.last_name || ""}`.trim() : detailData.last_name;
      return (
        <div className="space-y-3">
          <h4 className="text-sm font-semibold">Homeowner Registration Request</h4>
          <div className="divide-y divide-border rounded-md border">
            <div className="flex justify-between px-3 py-2 text-sm"><span className="text-muted-foreground">Homeowner</span><span className="font-medium text-right">{ownerName || "—"}</span></div>
            <div className="flex justify-between px-3 py-2 text-sm"><span className="text-muted-foreground">Email</span><span className="font-medium text-right">{detailData.email}</span></div>
            <div className="flex justify-between px-3 py-2 text-sm"><span className="text-muted-foreground">Unit</span><span className="font-medium text-right">{detailData.units?.unit_number || detailData.unit_identifier || "—"}</span></div>
            <div className="flex justify-between px-3 py-2 text-sm"><span className="text-muted-foreground">Property</span><span className="font-medium text-right">{detailData.units?.address || detailData.owners?.property_address || "—"}</span></div>
            <div className="flex justify-between px-3 py-2 text-sm"><span className="text-muted-foreground">Association</span><span className="font-medium text-right">{detailData.associations?.name || "—"}</span></div>
            <div className="flex justify-between px-3 py-2 text-sm"><span className="text-muted-foreground">Status</span><Badge variant="outline" className="text-2xs capitalize">{detailData.status}</Badge></div>
          </div>
          {detailData.notes && <div className="rounded-md border p-3 text-sm whitespace-pre-wrap">{detailData.notes}</div>}

          {detailData.status === "pending" && (
            <div className="space-y-3 rounded-md border border-dashed p-3">
              <div className="flex items-center justify-between gap-2">
                <p className="text-xs font-medium text-foreground flex items-center gap-1.5">
                  <LinkIcon className="h-3.5 w-3.5 text-primary" />
                  {detailData.owner_id ? "Confirm owner to link" : "Select owner to link this account to"}
                </p>
                <div className="flex items-center gap-1.5">
                  <ShieldCheck className={`h-3.5 w-3.5 ${overrideMode ? "text-primary" : "text-muted-foreground"}`} />
                  <Label htmlFor="override-toggle" className="text-2xs cursor-pointer">Override</Label>
                  <Switch id="override-toggle" checked={overrideMode} onCheckedChange={setOverrideMode} />
                </div>
              </div>

              {!overrideMode && (
                candidateOwners.length === 0 ? (
                  <p className="text-2xs text-muted-foreground">
                    No matching active owners found for this unit. Enable Override to search any owner, or create the owner record first.
                  </p>
                ) : (
                  <Select value={selectedOwnerId} onValueChange={setSelectedOwnerId}>
                    <SelectTrigger className="h-8 text-xs">
                      <SelectValue placeholder="Choose an owner…" />
                    </SelectTrigger>
                    <SelectContent>
                      {candidateOwners.map((o) => {
                        const name = `${o.first_name || ""} ${o.last_name || ""}`.trim() || "(no name)";
                        const unit = o.units?.unit_number || o.units?.address || o.property_address || "";
                        const linked = o.user_id ? " · already linked" : "";
                        const excluded = o.exclude_from_signin ? " · excluded" : "";
                        return (
                          <SelectItem key={o.id} value={o.id} disabled={!!o.user_id || o.exclude_from_signin}>
                            {name}{unit ? ` — ${unit}` : ""}{o.email ? ` · ${o.email}` : ""}{linked}{excluded}
                          </SelectItem>
                        );
                      })}
                    </SelectContent>
                  </Select>
                )
              )}

              {overrideMode && (
                <div className="space-y-2 rounded-md bg-muted/40 p-2">
                  <p className="text-2xs text-muted-foreground">
                    Override the auto-match: edit the request details and pick any owner record across all associations.
                  </p>
                  <div className="grid grid-cols-2 gap-2">
                    <div className="space-y-1">
                      <Label className="text-2xs">Email</Label>
                      <Input value={editEmail} onChange={(e) => setEditEmail(e.target.value)} className="h-8 text-xs" placeholder="email@example.com" />
                    </div>
                    <div className="space-y-1">
                      <Label className="text-2xs">Unit identifier</Label>
                      <Input value={editUnitIdentifier} onChange={(e) => setEditUnitIdentifier(e.target.value)} className="h-8 text-xs" placeholder="e.g. 12 or 4B" />
                    </div>
                  </div>
                  <div className="space-y-1">
                    <Label className="text-2xs">Search any owner</Label>
                    <div className="relative">
                      <Search className="h-3.5 w-3.5 text-muted-foreground absolute left-2 top-1/2 -translate-y-1/2" />
                      <Input
                        value={overrideSearch}
                        onChange={(e) => setOverrideSearch(e.target.value)}
                        className="h-8 text-xs pl-7"
                        placeholder="Search by name, email, or address…"
                      />
                    </div>
                    {overrideSearching && <p className="text-2xs text-muted-foreground flex items-center gap-1"><Loader2 className="h-3 w-3 animate-spin" /> Searching…</p>}
                    {!overrideSearching && overrideSearch.trim().length >= 2 && overrideOwners.length === 0 && (
                      <p className="text-2xs text-muted-foreground">No active owners match.</p>
                    )}
                    {overrideOwners.length > 0 && (
                      <div className="max-h-48 overflow-y-auto rounded border bg-background divide-y">
                        {overrideOwners.map((o) => {
                          const name = `${o.first_name || ""} ${o.last_name || ""}`.trim() || "(no name)";
                          const unit = o.units?.unit_number || o.units?.address || o.property_address || "";
                          const assoc = o.associations?.name || "";
                          const isSelected = selectedOwnerId === o.id;
                          const disabled = !!o.user_id || o.exclude_from_signin;
                          return (
                            <button
                              type="button"
                              key={o.id}
                              disabled={disabled}
                              onClick={() => setSelectedOwnerId(o.id)}
                              className={`w-full text-left px-2 py-1.5 text-2xs hover:bg-muted disabled:opacity-50 disabled:cursor-not-allowed ${isSelected ? "bg-primary/10" : ""}`}
                            >
                              <div className="font-medium">{name}{o.email ? ` · ${o.email}` : ""}</div>
                              <div className="text-muted-foreground">
                                {assoc ? `${assoc}` : ""}{unit ? ` — ${unit}` : ""}
                                {o.user_id ? " · already linked" : ""}{o.exclude_from_signin ? " · excluded" : ""}
                              </div>
                            </button>
                          );
                        })}
                      </div>
                    )}
                  </div>
                </div>
              )}

              <p className="text-2xs text-muted-foreground">
                Approving will link the homeowner account, mark the request approved, and email <span className="font-medium">{overrideMode && editEmail ? editEmail : detailData.email}</span> a link to choose their password.
              </p>
            </div>
          )}

          {detailData.status === "approved" && (
            <div className="rounded-md border border-success/30 bg-success/5 p-3 text-xs text-foreground flex items-center gap-2">
              <CheckCircle className="h-4 w-4 text-success" />
              Approved {detailData.reviewed_at ? `on ${format(new Date(detailData.reviewed_at), "MMM d, yyyy h:mm a")}` : ""}.
              Password setup email was sent to {detailData.email}.
            </div>
          )}
          {detailData.status === "rejected" && (
            <div className="rounded-md border border-destructive/30 bg-destructive/5 p-3 text-xs text-foreground flex items-center gap-2">
              <XCircle className="h-4 w-4 text-destructive" />
              Rejected {detailData.reviewed_at ? `on ${format(new Date(detailData.reviewed_at), "MMM d, yyyy h:mm a")}` : ""}.
            </div>
          )}
        </div>
      );
    }

    if (selectedItem?.source_type === "reservation") {
      const notes = (() => {
        try { return typeof detailData.notes === "string" ? JSON.parse(detailData.notes) : detailData.notes || {}; }
        catch { return {}; }
      })();
      const formData = notes.form_data || {};
      const hasSignature = !!notes.signature;
      const amenityName = (detailData.amenities as any)?.name || "Amenity";

      return (
        <div className="space-y-3">
          <h4 className="text-sm font-semibold">Reservation: {amenityName}</h4>
          <div className="divide-y divide-border rounded-md border">
            <div className="flex justify-between px-3 py-2 text-sm">
              <span className="text-muted-foreground">Guest Name</span>
              <span className="font-medium">{detailData.guest_name}</span>
            </div>
            {detailData.guest_email && (
              <div className="flex justify-between px-3 py-2 text-sm">
                <span className="text-muted-foreground">Email</span>
                <span className="font-medium">{detailData.guest_email}</span>
              </div>
            )}
            {detailData.guest_phone && (
              <div className="flex justify-between px-3 py-2 text-sm">
                <span className="text-muted-foreground">Phone</span>
                <span className="font-medium">{detailData.guest_phone}</span>
              </div>
            )}
            <div className="flex justify-between px-3 py-2 text-sm">
              <span className="text-muted-foreground">Booking Date</span>
              <span className="font-medium">{detailData.booking_date ? format(new Date(detailData.booking_date + "T12:00:00"), "MMM d, yyyy") : "—"}</span>
            </div>
            {notes.pin_label && (
              <div className="flex justify-between px-3 py-2 text-sm">
                <span className="text-muted-foreground">Location/Spot</span>
                <span className="font-medium">{notes.pin_label}</span>
              </div>
            )}
            <div className="flex justify-between px-3 py-2 text-sm">
              <span className="text-muted-foreground">Status</span>
              <Badge variant="outline" className="text-2xs">{detailData.status}</Badge>
            </div>
            {Object.entries(formData).filter(([k]) => !k.startsWith("guest_") && k !== "booking_date").map(([key, val]) => (
              <div key={key} className="flex justify-between px-3 py-2 text-sm">
                <span className="text-muted-foreground capitalize">{key.replace(/_/g, " ")}</span>
                <span className="font-medium text-right max-w-[60%] truncate">
                  {typeof val === "string" && val.startsWith("data:image") ? "✓ Signed" : String(val ?? "—")}
                </span>
              </div>
            ))}
          </div>
          {hasSignature && (
            <div className="space-y-1">
              <p className="text-xs font-medium text-muted-foreground">Signature</p>
              <img src={notes.signature} alt="Signature" className="border rounded h-16 bg-white" />
            </div>
          )}
          <Button
            variant="outline"
            size="sm"
            className="text-xs gap-1.5 mt-2"
            onClick={() => generateReservationPdf(detailData, notes, amenityName)}
          >
            <Download className="h-3.5 w-3.5" /> Download PDF
          </Button>
        </div>
      );
    }

    return <pre className="text-xs whitespace-pre-wrap">{JSON.stringify(detailData, null, 2)}</pre>;
  };

  const generateReservationPdf = (booking: any, notes: any, amenityName: string) => {
    const doc = new jsPDF();
    const margin = 36;
    const pageWidth = doc.internal.pageSize.getWidth();
    let y = margin;

    // Title
    doc.setFontSize(16);
    doc.setFont("helvetica", "bold");
    doc.text(`Reservation Application`, margin, y);
    y += 10;

    doc.setFontSize(11);
    doc.setFont("helvetica", "normal");
    doc.text(amenityName, margin, y);
    y += 8;

    doc.setDrawColor(200);
    doc.line(margin, y, pageWidth - margin, y);
    y += 10;

    // Helper to add a field row
    const addField = (label: string, value: string) => {
      if (y > 270) { doc.addPage(); y = margin; }
      doc.setFont("helvetica", "bold");
      doc.setFontSize(10);
      doc.text(label + ":", margin, y);
      doc.setFont("helvetica", "normal");
      const textLines = doc.splitTextToSize(value || "—", pageWidth - margin * 2 - 60);
      doc.text(textLines, margin + 60, y);
      y += Math.max(textLines.length * 5, 7);
    };

    addField("Guest Name", booking.guest_name || "");
    addField("Email", booking.guest_email || "");
    addField("Phone", booking.guest_phone || "");
    addField("Booking Date", booking.booking_date ? format(new Date(booking.booking_date + "T12:00:00"), "MMM d, yyyy") : "");
    if (notes.pin_label) addField("Location/Spot", notes.pin_label);
    addField("Status", booking.status || "");

    // Custom form data
    const formData = notes.form_data || {};
    const formEntries = Object.entries(formData).filter(
      ([k]) => !k.startsWith("guest_") && k !== "booking_date"
    );

    if (formEntries.length > 0) {
      y += 5;
      doc.setDrawColor(200);
      doc.line(margin, y, pageWidth - margin, y);
      y += 8;
      doc.setFont("helvetica", "bold");
      doc.setFontSize(11);
      doc.text("Additional Information", margin, y);
      y += 8;

      for (const [key, val] of formEntries) {
        const label = key.replace(/_/g, " ").replace(/\b\w/g, c => c.toUpperCase());
        const isSignature = typeof val === "string" && (val as string).startsWith("data:image");
        if (isSignature) {
          addField(label, "See signature below");
        } else {
          addField(label, String(val ?? ""));
        }
      }
    }

    // Signature
    if (notes.signature) {
      y += 8;
      if (y > 230) { doc.addPage(); y = margin; }
      doc.setFont("helvetica", "bold");
      doc.setFontSize(10);
      doc.text("Signature:", margin, y);
      y += 5;
      try {
        doc.addImage(notes.signature, "PNG", margin, y, 80, 25);
        y += 30;
      } catch (e) {
        doc.setFont("helvetica", "normal");
        doc.text("[Signature on file]", margin, y);
        y += 7;
      }
    }

    // Additional signatures from form_data
    for (const [key, val] of Object.entries(formData)) {
      if (typeof val === "string" && (val as string).startsWith("data:image")) {
        if (y > 230) { doc.addPage(); y = margin; }
        const label = key.replace(/_/g, " ").replace(/\b\w/g, c => c.toUpperCase());
        doc.setFont("helvetica", "bold");
        doc.setFontSize(10);
        doc.text(`${label}:`, margin, y);
        y += 5;
        try {
          doc.addImage(val as string, "PNG", margin, y, 80, 25);
          y += 30;
        } catch (e) {
          doc.setFont("helvetica", "normal");
          doc.text("[Signature on file]", margin, y);
          y += 7;
        }
      }
    }

    // Footer
    y += 5;
    doc.setDrawColor(200);
    doc.line(margin, y, pageWidth - margin, y);
    y += 6;
    doc.setFontSize(8);
    doc.setFont("helvetica", "normal");
    doc.setTextColor(130);
    doc.text(`Generated on ${format(new Date(), "MMM d, yyyy h:mm a")}`, margin, y);

    const safeName = (booking.guest_name || "reservation").replace(/[^a-z0-9]/gi, "_").toLowerCase();
    doc.save(`reservation-${safeName}-${booking.booking_date || "unknown"}.pdf`);
  };

  return (
    <div className="space-y-4">
      <div className="flex items-center justify-between">
        <div>
          <h1 className="text-xl font-bold text-foreground flex items-center gap-2">
            <Inbox className="h-5 w-5 text-primary" /> Form Inbox
          </h1>
          <p className="text-sm text-muted-foreground">Public form submissions, violation responses, reservations, and homeowner requests</p>
        </div>
      </div>

      <div className="flex items-center gap-3">
        <Select value={statusFilter} onValueChange={setStatusFilter}>
          <SelectTrigger className="w-[160px] h-8 text-[12px]">
            <SelectValue />
          </SelectTrigger>
          <SelectContent>
            <SelectItem value="active">Active (New / In Progress)</SelectItem>
            <SelectItem value="new">New Only</SelectItem>
            <SelectItem value="in_progress">In Progress</SelectItem>
            <SelectItem value="resolved">Resolved</SelectItem>
            <SelectItem value="archived">Archived</SelectItem>
            <SelectItem value="all">All</SelectItem>
          </SelectContent>
        </Select>

        <Select value={sourceFilter} onValueChange={setSourceFilter}>
          <SelectTrigger className="w-[180px] h-8 text-[12px]">
            <SelectValue />
          </SelectTrigger>
          <SelectContent>
            <SelectItem value="all">All Sources</SelectItem>
            <SelectItem value="public_form">Public Forms</SelectItem>
            <SelectItem value="violation_response">Violation Responses</SelectItem>
            <SelectItem value="client_request">Homeowner Requests</SelectItem>
            <SelectItem value="homeowner_ticket">Homeowner Tickets</SelectItem>
            <SelectItem value="registration_request">Registration Requests</SelectItem>
            <SelectItem value="reservation">Reservations</SelectItem>
            <SelectItem value="avriacam_contact">Avriacam.com Contact</SelectItem>
          </SelectContent>
        </Select>
      </div>

      <Card className="border shadow-sm">
        <CardContent className="p-0">
          {loading ? (
            <div className="flex items-center justify-center py-12">
              <Loader2 className="h-5 w-5 animate-spin text-muted-foreground" />
            </div>
          ) : items.length === 0 ? (
            <div className="text-center py-12">
              <Inbox className="h-8 w-8 text-muted-foreground/20 mx-auto mb-2" />
              <p className="text-sm text-muted-foreground">No items match your filters</p>
            </div>
          ) : (
            <div className="divide-y divide-border">
              {items.map((item) => {
                const Icon = sourceIcons[item.source_type] || FileText;
                return (
                  <div
                    key={item.id}
                    className="flex items-center gap-3 px-4 py-3 hover:bg-muted/50 transition-colors cursor-pointer group"
                    onClick={() => openDetail(item)}
                  >
                    <div className="h-8 w-8 rounded-full bg-primary/10 flex items-center justify-center shrink-0">
                      <Icon className="h-4 w-4 text-primary" />
                    </div>
                    <div className="min-w-0 flex-1">
                      <div className="flex items-center gap-2">
                        <p className="text-[13px] font-medium text-foreground truncate">{item.title}</p>
                        {item.status === "new" && <span className="h-2 w-2 rounded-full bg-destructive shrink-0" />}
                      </div>
                      <div className="flex items-center gap-2 mt-0.5">
                        <span className={`inline-flex items-center rounded-full px-2 py-0.5 text-2xs font-medium border ${statusStyles[item.status] || "cc-badge-neutral"}`}>
                          {item.status === "in_progress" ? "In Progress" : item.status.charAt(0).toUpperCase() + item.status.slice(1)}
                        </span>
                        <span className="text-2xs text-muted-foreground">
                          {sourceLabels[item.source_type] || item.source_type}
                        </span>
                        <span className="text-2xs text-muted-foreground">
                          · {item.submitter_name || item.submitter_email || "Anonymous"}
                        </span>
                      </div>
                    </div>
                    <div className="text-right shrink-0">
                      <p className="text-2xs text-muted-foreground">{formatDistanceToNow(new Date(item.created_at), { addSuffix: true })}</p>
                    </div>
                    <div className="flex items-center gap-1 opacity-0 group-hover:opacity-100 transition-opacity shrink-0">
                      {item.status !== "archived" && (
                        <Button
                          variant="ghost"
                          size="icon"
                          className="h-7 w-7"
                          title="Archive"
                          onClick={(e) => { e.stopPropagation(); updateStatus(item.id, "archived"); }}
                        >
                          <Archive className="h-3.5 w-3.5" />
                        </Button>
                      )}
                      {item.status !== "resolved" && item.status !== "archived" && (
                        <Button
                          variant="ghost"
                          size="icon"
                          className="h-7 w-7"
                          title="Mark Resolved"
                          onClick={(e) => { e.stopPropagation(); updateStatus(item.id, "resolved"); }}
                        >
                          <CheckCircle className="h-3.5 w-3.5" />
                        </Button>
                      )}
                      <Button
                        variant="ghost"
                        size="icon"
                        className="h-7 w-7 text-destructive hover:text-destructive"
                        title="Delete"
                        onClick={(e) => { e.stopPropagation(); deleteItem(item.id); }}
                      >
                        <Trash2 className="h-3.5 w-3.5" />
                      </Button>
                    </div>
                  </div>
                );
              })}
            </div>
          )}
        </CardContent>
      </Card>

      {/* Detail dialog */}
      <Dialog open={!!selectedItem} onOpenChange={(open) => { if (!open) setSelectedItem(null); }}>
        <DialogContent className="max-w-lg">
          <DialogHeader>
            <DialogTitle className="flex items-center gap-2 text-base">
              {selectedItem && (() => { const Icon = sourceIcons[selectedItem.source_type] || FileText; return <Icon className="h-4 w-4 text-primary" />; })()}
              {selectedItem?.title}
            </DialogTitle>
          </DialogHeader>

          <div className="flex items-center gap-2 mb-3">
            <span className={`inline-flex items-center rounded-full px-2 py-0.5 text-2xs font-medium border ${statusStyles[selectedItem?.status || "new"]}`}>
              {selectedItem?.status === "in_progress" ? "In Progress" : (selectedItem?.status || "").charAt(0).toUpperCase() + (selectedItem?.status || "").slice(1)}
            </span>
            <span className="text-2xs text-muted-foreground">{sourceLabels[selectedItem?.source_type || ""]}</span>
            {selectedItem?.created_at && (
              <span className="text-2xs text-muted-foreground">· {format(new Date(selectedItem.created_at), "MMM d, yyyy h:mm a")}</span>
            )}
          </div>

          {renderDetailContent()}

          <div className="flex items-center flex-wrap gap-2 mt-4 pt-3 border-t">
            {selectedItem?.source_type === "registration_request" && detailData?.status === "pending" && (
              <>
                <Button
                  size="sm"
                  className="text-xs gap-1"
                  disabled={approving || rejecting || (!detailData.owner_id && !selectedOwnerId)}
                  onClick={approveRegistration}
                >
                  {approving ? <Loader2 className="h-3.5 w-3.5 animate-spin" /> : <Mail className="h-3.5 w-3.5" />}
                  Approve & Send Password Email
                </Button>
                <Button
                  variant="outline"
                  size="sm"
                  className="text-xs gap-1 text-destructive hover:text-destructive border-destructive/30"
                  disabled={approving || rejecting}
                  onClick={rejectRegistration}
                >
                  {rejecting ? <Loader2 className="h-3.5 w-3.5 animate-spin" /> : <XCircle className="h-3.5 w-3.5" />}
                  Reject
                </Button>
              </>
            )}
            {selectedItem?.status !== "in_progress" && selectedItem?.status !== "archived" && (
              <Button variant="outline" size="sm" className="text-xs gap-1" onClick={() => selectedItem && updateStatus(selectedItem.id, "in_progress")}>
                <Clock className="h-3.5 w-3.5" /> In Progress
              </Button>
            )}
            {selectedItem?.status !== "resolved" && selectedItem?.status !== "archived" && (
              <Button variant="outline" size="sm" className="text-xs gap-1" onClick={() => selectedItem && updateStatus(selectedItem.id, "resolved")}>
                <CheckCircle className="h-3.5 w-3.5" /> Resolved
              </Button>
            )}
            {selectedItem?.status !== "archived" && (
              <Button variant="outline" size="sm" className="text-xs gap-1" onClick={() => selectedItem && updateStatus(selectedItem.id, "archived")}>
                <Archive className="h-3.5 w-3.5" /> Archive
              </Button>
            )}
            {selectedItem?.status === "archived" && (
              <Button variant="outline" size="sm" className="text-xs gap-1" onClick={() => selectedItem && updateStatus(selectedItem.id, "new")}>
                <RotateCcw className="h-3.5 w-3.5" /> Restore
              </Button>
            )}
            <div className="ml-auto">
              <Button variant="outline" size="sm" className="text-xs gap-1 text-destructive hover:text-destructive border-destructive/30" onClick={() => selectedItem && deleteItem(selectedItem.id)}>
                <Trash2 className="h-3.5 w-3.5" /> Delete
              </Button>
            </div>
          </div>
        </DialogContent>
      </Dialog>
    </div>
  );
}
