"use client";

import { useCallback, useEffect, useState } from "react";
import { api, Customer, CustomerDetail } from "@/lib/api";
import { useLocale } from "@/i18n/LocaleProvider";
import {
  Button,
  Card,
  Dialog,
  EmptyState,
  ErrorState,
  Field,
  IconChip,
  MoneyText,
  Numeric,
  PageHeader,
  Sheet,
  SkeletonTable,
  StatusBadge,
  Tone,
} from "@/components/ui";

const statusTone: Record<Customer["status"], Tone> = {
  ACTIVE: "success",
  PENDING: "warning",
  BANNED: "danger",
};

export default function Page() {
  const { t } = useLocale();
  const [phone, setPhone] = useState("");
  const [query, setQuery] = useState("");
  const [rows, setRows] = useState<Customer[] | null>(null);
  const [error, setError] = useState(false);
  const [selected, setSelected] = useState<string | null>(null);

  const load = useCallback(async () => {
    setRows(null);
    setError(false);
    try {
      setRows(await api.listCustomers(query || undefined));
    } catch {
      setError(true);
    }
  }, [query]);

  useEffect(() => {
    load();
  }, [load]);

  return (
    <div>
      <PageHeader titleKey="nav.customers" />

      <Card className="mb-4">
        <form
          className="flex flex-wrap items-end gap-3"
          onSubmit={(e) => {
            e.preventDefault();
            setQuery(phone.trim());
          }}
        >
          <Field
            label={t("customers.searchLabel")}
            value={phone}
            onChange={(e) => setPhone(e.target.value)}
            placeholder="+9665…"
            className="min-w-[240px] flex-1"
          />
          <Button variant="primary" type="submit">
            {t("customers.search")}
          </Button>
          {query && (
            <Button
              type="button"
              onClick={() => {
                setPhone("");
                setQuery("");
              }}
            >
              {t("customers.clear")}
            </Button>
          )}
        </form>
      </Card>

      {error ? (
        <ErrorState onRetry={load} />
      ) : rows === null ? (
        <SkeletonTable rows={8} />
      ) : rows.length === 0 ? (
        <EmptyState
          icon={<span className="text-xl">👤</span>}
          title={t("customers.emptyTitle")}
          description={query ? t("customers.noMatch") : t("customers.emptyBody")}
        />
      ) : (
        <div className="card overflow-x-auto">
          <table className="w-full min-w-[640px] text-sm">
            <thead>
              <tr className="border-b border-line">
                <Th>{t("customers.colPhone")}</Th>
                <Th>{t("customers.colStatus")}</Th>
                <Th>{t("customers.colJoined")}</Th>
                <Th>{t("customers.colLastSeen")}</Th>
              </tr>
            </thead>
            <tbody>
              {rows.map((c) => (
                <tr
                  key={c.id}
                  onClick={() => setSelected(c.id)}
                  className="cursor-pointer border-b border-line transition last:border-b-0 hover:bg-surface-raised"
                >
                  <td className="px-4 py-3">
                    {/* Phone is LTR-isolated so +966… never flips under Arabic. */}
                    <Numeric className="font-medium">{c.phone}</Numeric>
                  </td>
                  <td className="px-4 py-3">
                    <StatusBadge tone={statusTone[c.status]}>
                      {t(`customers.status${c.status}`)}
                    </StatusBadge>
                  </td>
                  <td className="px-4 py-3 text-xs text-muted">
                    {new Date(c.createdAt).toLocaleDateString()}
                  </td>
                  <td className="px-4 py-3 text-xs text-muted">
                    {c.lastLoginAt
                      ? new Date(c.lastLoginAt).toLocaleString()
                      : t("customers.never")}
                  </td>
                </tr>
              ))}
            </tbody>
          </table>
        </div>
      )}

      {selected && (
        <CustomerSheet
          id={selected}
          onClose={() => setSelected(null)}
          onChanged={load}
        />
      )}
    </div>
  );
}

function Th({ children }: { children: React.ReactNode }) {
  return (
    <th className="px-4 py-3 text-start text-[11px] font-semibold uppercase tracking-wider text-muted">
      {children}
    </th>
  );
}

/* ------------------------------------------------------------------- detail */

function CustomerSheet({
  id,
  onClose,
  onChanged,
}: {
  id: string;
  onClose: () => void;
  onChanged: () => void;
}) {
  const { t } = useLocale();
  const [detail, setDetail] = useState<CustomerDetail | null>(null);
  const [ridesPage, setRidesPage] = useState(0);
  const [error, setError] = useState(false);
  const [confirmBan, setConfirmBan] = useState(false);
  const [busy, setBusy] = useState(false);

  const load = useCallback(async () => {
    setError(false);
    try {
      setDetail(await api.customerDetail(id));
    } catch {
      setError(true);
    }
  }, [id]);

  useEffect(() => {
    load();
  }, [load]);

  const toggleBan = async (banned: boolean) => {
    setBusy(true);
    try {
      await api.setCustomerBanned(id, banned);
      setConfirmBan(false);
      await load();
      onChanged();
    } finally {
      setBusy(false);
    }
  };

  const c = detail?.customer;
  // The server sends every ride this customer ever took, so the page size only controls what is
  // rendered. Server-side paging is the real fix; this at least stops the UI hiding the rest.
  const RIDES_PER_PAGE = 8;
  const allRides = detail?.rides ?? [];
  const ridePages = Math.max(1, Math.ceil(allRides.length / RIDES_PER_PAGE));
  const ridePage = allRides.slice(
    ridesPage * RIDES_PER_PAGE,
    ridesPage * RIDES_PER_PAGE + RIDES_PER_PAGE,
  );

  const banned = c?.status === "BANNED";

  return (
    <Sheet open onClose={onClose} title={c ? c.phone : t("common.loading")}>
      {error ? (
        <ErrorState onRetry={load} />
      ) : !detail ? (
        <SkeletonTable rows={4} />
      ) : (
        <div className="space-y-5">
          <div className="flex items-center gap-3">
            <IconChip tone={statusTone[detail.customer.status]} className="h-11 w-11">
              👤
            </IconChip>
            <div>
              <Numeric className="text-lg font-semibold">{detail.customer.phone}</Numeric>
              <div className="mt-0.5">
                <StatusBadge tone={statusTone[detail.customer.status]}>
                  {t(`customers.status${detail.customer.status}`)}
                </StatusBadge>
              </div>
            </div>
          </div>

          {/* Wallet, joined from wallet-service; null when it's unreachable. */}
          <div>
            <SectionLabel>{t("customers.wallet")}</SectionLabel>
            {detail.wallet ? (
              <Card className="flex items-center justify-between">
                <span className="text-sm text-muted">{t("customers.balance")}</span>
                <span className="text-2xl font-bold text-brand">
                  <Numeric>{detail.wallet.balance.toFixed(2)}</Numeric>{" "}
                  <span className="text-sm font-normal text-muted">
                    {detail.wallet.currency}
                  </span>
                </span>
              </Card>
            ) : (
              <Card className="text-sm text-muted">{t("customers.walletUnavailable")}</Card>
            )}
          </div>

          {/* Rides, from booking-service. */}
          <div>
            <SectionLabel>{t("customers.recentRides")}</SectionLabel>
            {detail.rides.length === 0 ? (
              <Card className="text-sm text-muted">{t("customers.noRides")}</Card>
            ) : (
              <Card className="!p-0">
                <div className="divide-y divide-line">
                  {ridePage.map((r) => (
                    <div key={r.id} className="flex items-center justify-between px-4 py-3">
                      <div>
                        <div className="text-sm font-medium">
                          {r.startedAt
                            ? new Date(r.startedAt).toLocaleDateString()
                            : t("customers.never")}
                        </div>
                        <div className="text-xs text-muted">{r.status}</div>
                      </div>
                      {r.fareAmount != null && (
                        <MoneyText amount={r.fareAmount} currency={r.currency} />
                      )}
                    </div>
                  ))}
                </div>
                  {/* Paged rather than silently cut at eight: an operator could not otherwise
                      tell that a rider with 300 rides had any beyond the first few. */}
                  {ridePages > 1 && (
                    <div className="flex items-center justify-between gap-3 border-t border-line px-4 py-3">
                      <button
                        type="button"
                        onClick={() => setRidesPage((n) => Math.max(0, n - 1))}
                        disabled={ridesPage === 0}
                        className="rounded-field border border-line px-3 py-1.5 text-sm disabled:opacity-40"
                      >
                        {t("common.prev")}
                      </button>
                      <span className="text-xs text-muted">
                        {ridesPage * RIDES_PER_PAGE + 1}-
                        {Math.min((ridesPage + 1) * RIDES_PER_PAGE, detail.rides.length)} /{" "}
                        {detail.rides.length}
                      </span>
                      <button
                        type="button"
                        onClick={() => setRidesPage((n) => Math.min(ridePages - 1, n + 1))}
                        disabled={ridesPage >= ridePages - 1}
                        className="rounded-field border border-line px-3 py-1.5 text-sm disabled:opacity-40"
                      >
                        {t("common.next")}
                      </button>
                    </div>
                  )}
              </Card>
            )}
          </div>

          {banned ? (
            <Button
              variant="primary"
              className="w-full"
              disabled={busy}
              onClick={() => toggleBan(false)}
            >
              {t("customers.reinstate")}
            </Button>
          ) : (
            <Button
              variant="danger"
              className="w-full"
              disabled={busy}
              onClick={() => setConfirmBan(true)}
            >
              {t("customers.ban")}
            </Button>
          )}
        </div>
      )}

      <Dialog
        open={confirmBan}
        onClose={() => setConfirmBan(false)}
        icon="🚫"
        tone="danger"
        title={t("customers.banConfirmTitle")}
        description={t("customers.banConfirmBody")}
        actions={
          <>
            <Button
              variant="danger"
              className="flex-1"
              disabled={busy}
              onClick={() => toggleBan(true)}
            >
              {t("customers.banYes")}
            </Button>
            <Button onClick={() => setConfirmBan(false)}>{t("common.cancel")}</Button>
          </>
        }
      />
    </Sheet>
  );
}

function SectionLabel({ children }: { children: React.ReactNode }) {
  return (
    <div className="mb-2 text-[11px] font-semibold uppercase tracking-wider text-muted">
      {children}
    </div>
  );
}
