"use client";
import { useEffect, useRef, useState, useTransition } from "react";
import { useRouter, useSearchParams } from "next/navigation";
import { ChevronLeft, ChevronRight, Plus, RefreshCw, Search, Trash2, Users } from "lucide-react";
import { Button } from "@/components/ui/button";
import { Input } from "@/components/ui/input";
import { Dialog, DialogContent, DialogDescription, DialogFooter, DialogHeader, DialogTitle } from "@/components/ui/dialog";
import { EmptyState } from "@/components/shared/panel";
import { useQueryUpdate } from "@/components/shared/query-controls";
import { StatusBadge } from "@/components/shared/status-badge";
import type { Chargepoint } from "../types";
import { AddAuthorizationDialog } from "./add-dialog";
import { AuthorizationSettings } from "./settings";
import { mutateAuthorization } from "./client-api";
import type { AuthorizationPage, AuthorizationUser } from "./contract";

export function AuthorizationApiPanel({ chargepoint, data, loadError }: { chargepoint: Chargepoint; data?: AuthorizationPage; loadError?: string }) {
  const router = useRouter();
  const params = useSearchParams();
  const update = useQueryUpdate();
  const currentQuery = params.get("auth_query") ?? "";
  const [searchState, setSearchState] = useState({ source: currentQuery, value: currentQuery });
  const searchValue = searchState.source === currentQuery ? searchState.value : currentQuery;
  const searchTimer = useRef<ReturnType<typeof setTimeout> | null>(null);
  useEffect(() => () => { if (searchTimer.current) clearTimeout(searchTimer.current); }, []);
  const [adding, setAdding] = useState(false);
  const [removing, setRemoving] = useState<AuthorizationUser | null>(null);
  const [saving, setSaving] = useState(false);
  const busy = useRef(false);
  const [error, setError] = useState("");
  const [notice, setNotice] = useState("");
  const [refreshAttempted, setRefreshAttempted] = useState(false);
  const [refreshing, startRefresh] = useTransition();
  const users = data?.users ?? [];
  const items = users.filter(user => `${user.name} ${user.email} ${user.phone} ${user.id}`.toLowerCase().includes(searchValue.trim().toLowerCase()));
  const pagination = data?.pagination;

  function reload(message = "") {
    setNotice(message);
    setRefreshAttempted(!message);
    startRefresh(() => router.refresh());
  }
  async function remove() {
    if (!removing || busy.current) return;
    busy.current = true;
    setSaving(true);
    setError("");
    try {
      await mutateAuthorization({ chargepointId: chargepoint.id, userId: removing.id, action: "remove" });
      setRemoving(null);
      reload("Authorization removed successfully.");
    } catch (error) {
      setError(error instanceof Error ? error.message : "Unable to remove authorization. Try again.");
    } finally { busy.current = false; setSaving(false); }
  }
  function changePage(page: number) {
    setNotice("");
    setRefreshAttempted(false);
    startRefresh(() => update({ paginate_page: String(page) }));
  }
  function changeSearch(value: string) {
    setSearchState({ source: currentQuery, value });
    if (searchTimer.current) clearTimeout(searchTimer.current);
    searchTimer.current = setTimeout(() => {
      const url = new URL(window.location.href);
      if (value.trim()) url.searchParams.set("auth_query", value.trim());
      else url.searchParams.delete("auth_query");
      window.history.replaceState(null, "", `${url.pathname}${url.search}${url.hash}`);
      searchTimer.current = null;
    }, 300);
  }
  return (
    <div className="space-y-5">
      <AuthorizationSettings chargepoint={chargepoint} refreshing={refreshing} userCount={data?.totalDocs} onChanged={reload} />
      <section className="panel overflow-hidden" aria-label="Chargepoint authorizations" aria-busy={refreshing}>
        <div className="space-y-4 p-5 md:p-6">
          <div className="flex flex-wrap items-start justify-between gap-4">
            <div>
              <h2 className="text-lg font-semibold">Authorizations <span className="ml-1 text-sm font-normal text-muted-foreground">{data ? `(${data.totalDocs})` : ""}</span></h2>
              <p className="mt-1 text-sm text-muted-foreground">Manage users authorized for this chargepoint.</p>
            </div>
            <div className="flex w-full flex-wrap gap-2 sm:w-auto">
              <Button variant="outline" disabled={refreshing || saving} onClick={() => reload()}><RefreshCw aria-hidden="true" className={refreshing ? "animate-spin motion-reduce:animate-none" : undefined} />{refreshing ? "Refreshing…" : "Refresh"}</Button>
              <Button disabled={!data || refreshing || saving} onClick={() => setAdding(true)}><Plus aria-hidden="true" />Add Authorization</Button>
            </div>
          </div>
          <div className="relative w-full sm:max-w-sm">
            <Search aria-hidden="true" className="pointer-events-none absolute left-3 top-1/2 size-4 -translate-y-1/2 text-muted-foreground" />
            <Input aria-label="Search authorizations" className="pl-10" placeholder="Search this page by name, email, or ID…" value={searchValue} maxLength={200} onChange={event => changeSearch(event.target.value)} />
          </div>
          {!!data?.detailsUnavailable && <p role="status" className="text-sm text-muted-foreground">Some user details are unavailable. The authorization IDs remain visible; refresh to retry loading their profiles.</p>}
          {searchValue.trim() && <p className="text-xs text-muted-foreground">{items.length} matching users on this page.</p>}
          {notice && <p role="status" className="text-sm text-success">{notice}</p>}
          {refreshing ? <p role="status" className="text-sm text-muted-foreground">Refreshing authorizations…</p> : loadError ? <p role="alert" className="text-sm text-destructive">{refreshAttempted ? "Refresh failed. " : ""}{loadError}</p> : refreshAttempted && <p role="status" className="text-sm text-success">Authorizations refreshed successfully.</p>}
        </div>
        <div className="overflow-x-auto">
          <table className="data-table min-w-[680px]" aria-label="Authorized users">
            <thead><tr>{["User", "Email", "Phone", "Role", "Actions"].map(label => <th key={label} scope="col">{label}</th>)}</tr></thead>
            <tbody>{items.map(user => <tr key={user.id}>
              <td><p className="font-medium">{user.name || "User details unavailable"}</p><p className="mt-1 text-xs text-muted-foreground">{user.id}</p></td>
              <td>{user.email || "—"}</td><td className="whitespace-nowrap">{user.phone || "—"}</td>
              <td>{user.role ? <StatusBadge tone="neutral">{user.role}</StatusBadge> : "—"}</td>
              <td><Button size="sm" variant="ghost" className="text-destructive hover:bg-destructive/10 hover:text-destructive" disabled={saving || refreshing} aria-label={`Remove authorization for ${user.name || user.email || user.id}`} onClick={() => { setError(""); setRemoving(user); }}><Trash2 aria-hidden="true" />Remove</Button></td>
            </tr>)}</tbody>
          </table>
        </div>
        {!items.length && (loadError ? <EmptyState title="Authorizations unavailable" description="Refresh to retry loading the authorized users." /> : <div className="pt-8"><Users aria-hidden="true" className="mx-auto size-8 text-muted-foreground/60" /><EmptyState title={searchValue.trim() ? "No matching users on this page" : "No authorized users yet"} description={searchValue.trim() ? "Try a different name, email, or user ID." : "Add a user to prepare the authorization list for this chargepoint."} /></div>)}
        {pagination && <div className="flex flex-wrap items-center justify-between gap-3 border-t px-5 py-4 text-sm">
          <p className="text-muted-foreground">Showing {pagination.start} to {pagination.end} of {pagination.total} entries</p>
          <div className="flex items-center gap-2">
            <Button size="sm" variant="outline" aria-label="Previous authorizations page" disabled={pagination.page <= 1 || refreshing} onClick={() => changePage(pagination.page - 1)}><ChevronLeft aria-hidden="true" />Previous</Button>
            <span className="px-2 text-muted-foreground">{pagination.page} / {pagination.pages}</span>
            <Button size="sm" variant="outline" aria-label="Next authorizations page" disabled={pagination.page >= pagination.pages || refreshing} onClick={() => changePage(pagination.page + 1)}>Next<ChevronRight aria-hidden="true" /></Button>
          </div>
        </div>}
      </section>
      {adding && <AddAuthorizationDialog chargepointId={chargepoint.id} chargepointName={chargepoint.name} authorizedIds={data?.userIds ?? []} onOpenChange={setAdding} onAdded={() => { setAdding(false); reload("Authorization added successfully."); }} />}
      <Dialog open={removing !== null} onOpenChange={open => { if (!open && !busy.current) setRemoving(null); }}>
        <DialogContent showCloseButton={!saving} className="sm:max-w-lg" aria-busy={saving}>
          <DialogHeader>
            <DialogTitle>Remove Authorization?</DialogTitle>
            <DialogDescription>Remove this user from the authorization list for <span className="font-medium text-foreground">{chargepoint.name}</span>. The user account will be retained.</DialogDescription>
          </DialogHeader>
          <div className="rounded-xl border bg-muted/30 p-4"><p className="font-medium">{removing?.name || removing?.email || "Selected user"}</p><p className="mt-1 break-all text-sm text-muted-foreground">{removing?.email}</p><p className="mt-2 break-all text-xs text-muted-foreground">{removing?.id}</p></div>
          {error && <p role="alert" className="text-sm text-destructive">{error}</p>}
          <DialogFooter><Button variant="outline" disabled={saving} onClick={() => setRemoving(null)}>Cancel</Button><Button variant="destructive" disabled={saving} onClick={remove}>{saving ? "Removing…" : "Remove Authorization"}</Button></DialogFooter>
        </DialogContent>
      </Dialog>
    </div>
  );
}
