"use client";

import { useEffect, useMemo, useRef, useState } from "react";
import Image from "next/image";
import { useSearchParams } from "next/navigation";
import { useDispatch, useSelector } from "react-redux";
import type { AppDispatch, RootState } from "@/state/store";
import {
  fetchQuotes,
  fetchQuoteById,
  updateQuotesStatus,
  deleteQuotes,
  clearSelectedQuote,
  setSelectedQuote,
} from "@/state/quote/quoteSlice";
import type { Quote, QuoteStatus } from "@/types/quote";
import { useClickOutside } from "@/hooks/useClickOutside";
import DataTable, { type Column } from "../common/DataTable";
import ExportDropdown from "../common/ExportDropdown";
import FiltersDropdown from "../common/FiltersDropdown";
import type { ExportColumn } from "../common/export-utils";
import {
  CheckCircleIcon,
  EyeViewIcon,
  KebabIcon,
  LensThumb,
  TrashIcon,
} from "../dashboard/icons";
import QuoteDetailsDrawer from "./QuoteDetailsDrawer";
import QuoteStatusBadge from "./QuoteStatusBadge";
import { getImageUrl } from "@/lib/imageUrl";
import { formatListingNo } from "@/lib/listingNo";
import ProductImage from "../common/ProductImage";
import RemoveQuoteModal from "./RemoveQuoteModal";

const exportColumns: ExportColumn<Quote>[] = [
  { key: "listingNo", label: "Product No.", getValue: (q: Quote) => formatListingNo(q.product?.listingNo) },
  { key: "product", label: "Product", getValue: (q: Quote) => q.product?.title || "" },
  {
    key: "buyerName",
    label: "Buyer",
    getValue: (q: Quote) =>
      `${q.buyer?.firstName || ""} ${q.buyer?.lastName || ""}`.trim(),
  },
  { key: "phone", label: "Phone", text: true, getValue: (q: Quote) => q.buyer?.phone || "" },
  {
    key: "date",
    label: "Date",
    getValue: (q: Quote) => (q.createdAt ? new Date(q.createdAt).toLocaleDateString() : ""),
  },
  { key: "status", label: "Status", getValue: (q: Quote) => q.status },
];

export default function QuotesTable() {
  const searchParams = useSearchParams();
  const dispatch = useDispatch<AppDispatch>();
  const { quotes, totalPages, currentPage, limit, loading, selectedQuote } =
    useSelector((state: RootState) => state.quote);

  const [selected, setSelected] = useState<Set<string>>(new Set());
  const [openMenu, setOpenMenu] = useState<string | null>(null);
  const [page, setPage] = useState(1);
  const [pageSize, setPageSize] = useState(12);
  const [searchQuery, setSearchQuery] = useState("");
  const [statusFilter, setStatusFilter] = useState<string>("All");
  const [exportOpen, setExportOpen] = useState(false);
  const [bulkExportOpen, setBulkExportOpen] = useState(false);
  const [filtersOpen, setFiltersOpen] = useState(false);
  const [deleteIds, setDeleteIds] = useState<string[] | null>(null);

  // Fetch quotes whenever pagination or filter parameters change
  useEffect(() => {
    const statusParam: QuoteStatus | "all" | undefined =
      statusFilter === "Pending"
        ? "pending"
        : statusFilter === "Quote Sent"
        ? "quote_sent"
        : statusFilter === "Sold"
        ? "sold"
        : undefined;

    dispatch(
      fetchQuotes({
        page,
        limit: pageSize,
        search: searchQuery.trim() || undefined,
        status: statusParam,
        sortBy: "createdAt:desc",
      })
    );
  }, [dispatch, page, pageSize, searchQuery, statusFilter]);

  // Handle direct navigation via URL: ?id=<quoteId>
  useEffect(() => {
    const urlQuoteId = searchParams.get("id");
    if (urlQuoteId) {
      dispatch(fetchQuoteById(urlQuoteId));
    }
  }, [searchParams, dispatch]);

  const selectedQuotes = useMemo(
    () => quotes.filter((q) => selected.has(q.id)),
    [quotes, selected]
  );

  const handleStatusChange = (ids: string[], status: QuoteStatus) => {
    dispatch(updateQuotesStatus({ ids, status }));
  };

  const handleDeleteConfirm = () => {
    if (deleteIds && deleteIds.length > 0) {
      dispatch(deleteQuotes(deleteIds));
      setSelected((prev) => {
        const next = new Set(prev);
        deleteIds.forEach((id) => next.delete(id));
        return next;
      });
      setDeleteIds(null);
    }
  };

  const columns: Column<Quote>[] = [
    {
      key: "id",
      label: "ID",
      sortable: true,
      sortValue: (quote) => quote.product?.listingNo ?? 0,
      render: (quote) => (
        <span className="text-[14px] font-medium text-[var(--color-blue)]">
          {formatListingNo(quote.product?.listingNo)}
        </span>
      ),
    },
    {
      key: "product",
      label: "Product",
      sortable: true,
      render: (quote) => {
        const productTitle = quote.product?.title || "Unknown Product";
        return (
          <div className="flex items-center gap-2.5">
            <ProductImage
              src={quote.product?.images?.[0]}
              alt={productTitle}
            />
            <span className="max-w-[220px] truncate text-[14px] text-[#101828]">
              {productTitle}
            </span>
          </div>
        );
      },
    },
    {
      key: "buyerName",
      label: "Buyer",
      sortable: true,
      render: (quote) => {
        const buyerName = quote.buyer
          ? `${quote.buyer.firstName || ""} ${quote.buyer.lastName || ""}`.trim() || "Unknown"
          : "Unknown";
        const buyerEmail = quote.buyer?.email || "—";
        return (
          <>
            <p className="whitespace-nowrap text-[13px] font-medium text-[#101828]">
              {buyerName}
            </p>
            <p className="whitespace-nowrap text-[12px] text-[var(--color-blue)]">
              {buyerEmail}
            </p>
          </>
        );
      },
    },
    {
      key: "phone",
      label: "Phone",
      render: (quote) => (
        <span className="whitespace-nowrap text-[13px] text-[var(--color-blue)]">
          {quote.buyer?.phone || "—"}
        </span>
      ),
    },
    {
      key: "date",
      label: "Date",
      sortable: true,
      render: (quote) => (
        <span className="whitespace-nowrap text-[13px] text-[#475467]">
          {quote.createdAt
            ? new Date(quote.createdAt).toLocaleDateString()
            : "—"}
        </span>
      ),
    },
    {
      key: "status",
      label: "Status",
      sortable: true,
      render: (quote) => <QuoteStatusBadge status={quote.status} />,
    },
  ];

  return (
    <div className="min-w-0">
      <div>
        <h1 className="text-[20px] font-bold text-[#101828]">Request a Quote</h1>
        <p className="mt-1 text-[13px] text-[#667085]">
          Manage quote requests from buyers on new products
        </p>
      </div>

      <div className="mt-6">
        <DataTable<Quote>
          columns={columns}
          data={quotes}
          rowKey={(quote) => quote.id}
          searchPlaceholder="Search quotes..."
          searchValue={searchQuery}
          onSearchChange={(q) => {
            setSearchQuery(q);
            setPage(1);
          }}
          showFilters
          onFiltersClick={() => setFiltersOpen((prev) => !prev)}
          filtersSlot={
            <FiltersDropdown
              open={filtersOpen}
              onClose={() => setFiltersOpen(false)}
              statusOptions={["All", "Pending", "Quote Sent", "Sold"]}
              ranges={[]}
              initialStatus={new Set([statusFilter])}
              onApply={(selectedStatus) => {
                const arr = Array.from(selectedStatus);
                const active = arr.find((s) => s !== "All") || "All";
                setStatusFilter(active);
                setPage(1);
              }}
              onClear={() => {
                setStatusFilter("All");
                setPage(1);
              }}
            />
          }
          showExport
          onExportClick={() => setExportOpen((prev) => !prev)}
          exportSlot={
            <ExportDropdown<Quote>
              open={exportOpen}
              onClose={() => setExportOpen(false)}
              allRows={quotes}
              selectedRows={selectedQuotes}
              columns={exportColumns}
              fileName="quotes"
              title="Request a Quote"
            />
          }
          selectedIds={selected}
          onSelectionChange={setSelected}
          pageSize={pageSize}
          onPageSizeChange={(size) => {
            setPageSize(size);
            setPage(1);
          }}
          externalPagination={{
            currentPage: page,
            totalPages: Math.max(1, totalPages),
            onPageChange: setPage,
          }}
          renderRowActions={(quote) => (
            <RowActionMenu
              open={openMenu === quote.id}
              status={quote.status}
              onToggle={() =>
                setOpenMenu(openMenu === quote.id ? null : quote.id)
              }
              onClose={() => setOpenMenu(null)}
              onViewDetails={() => {
                setOpenMenu(null);
                dispatch(setSelectedQuote(quote));
              }}
              onMarkSent={() => {
                setOpenMenu(null);
                handleStatusChange([quote.id], "quote_sent");
              }}
              onMarkSold={() => {
                setOpenMenu(null);
                handleStatusChange([quote.id], "sold");
              }}
              onDelete={() => {
                setOpenMenu(null);
                setDeleteIds([quote.id]);
              }}
            />
          )}
          renderBulkActionBar={() => {
            const hasPending = selectedQuotes.some((q) => q.status === "pending");
            const hasNonSold = selectedQuotes.some((q) => q.status !== "sold");
            return (
              <>
                <button
                  type="button"
                  onClick={() => setDeleteIds(Array.from(selected))}
                  className="flex h-9 items-center gap-2 rounded-lg border border-[var(--color-red)] bg-white px-4 text-[13px] font-medium text-[var(--color-red)] transition-colors hover:bg-red-50 cursor-pointer"
                >
                  <TrashIcon />
                  Delete Quote
                </button>
                {hasNonSold && (
                  <button
                    type="button"
                    onClick={() => handleStatusChange(Array.from(selected), "sold")}
                    className="flex h-9 items-center gap-2 rounded-lg border border-[var(--color-green)] bg-white px-4 text-[13px] font-medium text-[var(--color-green)] transition-colors hover:bg-green-50 cursor-pointer"
                  >
                    <CheckCircleIcon />
                    Mark as Sold
                  </button>
                )}
                {hasPending && (
                  <button
                    type="button"
                    onClick={() =>
                      handleStatusChange(Array.from(selected), "quote_sent")
                    }
                    className="flex h-9 items-center gap-2 rounded-lg border border-[var(--color-blue)] bg-white px-4 text-[13px] font-medium text-[var(--color-blue)] transition-colors hover:bg-blue-50 cursor-pointer"
                  >
                    <CheckCircleIcon />
                    Mark as Sent
                  </button>
                )}
                <div className="relative">
                  <button
                    type="button"
                    onClick={() => setBulkExportOpen((prev) => !prev)}
                    className="flex h-9 items-center gap-2 rounded-lg border border-[var(--color-blue)] bg-white px-4 text-[13px] font-medium text-[var(--color-blue)] transition-colors hover:bg-blue-50 cursor-pointer"
                  >
                    <Image src="/assets/export.svg" alt="" width={18} height={18} aria-hidden="true" />
                    Export Selection
                  </button>
                  <ExportDropdown<Quote>
                    open={bulkExportOpen}
                    onClose={() => setBulkExportOpen(false)}
                    allRows={quotes}
                    selectedRows={selectedQuotes}
                    columns={exportColumns}
                    fileName="quotes-selection"
                    title="Request a Quote"
                  />
                </div>
              </>
            );
          }}
        />
      </div>

      <QuoteDetailsDrawer
        quote={selectedQuote}
        open={selectedQuote !== null}
        onClose={() => dispatch(clearSelectedQuote())}
        onDelete={() => {
          if (selectedQuote) {
            setDeleteIds([selectedQuote.id]);
          }
        }}
        onMarkSent={() => {
          if (selectedQuote) {
            handleStatusChange([selectedQuote.id], "quote_sent");
          }
        }}
        onMarkSold={() => {
          if (selectedQuote) {
            handleStatusChange([selectedQuote.id], "sold");
          }
        }}
      />

      <RemoveQuoteModal
        open={deleteIds !== null}
        count={deleteIds?.length ?? 0}
        onClose={() => setDeleteIds(null)}
        onConfirm={handleDeleteConfirm}
      />
    </div>
  );
}

function RowActionMenu({
  open,
  status,
  onToggle,
  onClose,
  onViewDetails,
  onMarkSent,
  onMarkSold,
  onDelete,
}: {
  open: boolean;
  status: QuoteStatus;
  onToggle: () => void;
  onClose: () => void;
  onViewDetails: () => void;
  onMarkSent: () => void;
  onMarkSold: () => void;
  onDelete: () => void;
}) {
  const ref = useRef<HTMLDivElement | null>(null);
  const [openUpward, setOpenUpward] = useState(false);
  useClickOutside(ref, onClose, open);

  useEffect(() => {
    if (open && ref.current) {
      const rect = ref.current.getBoundingClientRect();
      const spaceBelow = window.innerHeight - rect.bottom;
      setOpenUpward(spaceBelow < 220);
    }
  }, [open]);

  const itemClass =
    "flex w-full items-center gap-2.5 whitespace-nowrap px-3.5 py-2 text-left text-[13px] font-medium hover:bg-[#F5F7F9] cursor-pointer";

  return (
    <div ref={ref} className={`relative ${open ? "z-50" : ""}`}>
      <button
        type="button"
        onClick={onToggle}
        className="flex h-7 w-7 items-center justify-center rounded-full text-[#667085] transition-colors hover:bg-[#F2F4F7] cursor-pointer"
      >
        <KebabIcon />
      </button>
      {open && (
        <div
          className={`absolute right-0 ${
            openUpward ? "bottom-[calc(100%+4px)]" : "top-[calc(100%+4px)]"
          } z-50 min-w-[170px] rounded-lg border border-[#E4E7EC] bg-white py-1.5 shadow-[0_10px_24px_rgba(15,23,42,0.12)]`}
        >
          <button
            type="button"
            onClick={onViewDetails}
            className={`${itemClass} text-[#344054]`}
          >
            <EyeViewIcon />
            View Details
          </button>
          {status === "pending" && (
            <button
              type="button"
              onClick={onMarkSent}
              className={`${itemClass} text-[#344054]`}
            >
              <CheckCircleIcon />
              Mark as Sent
            </button>
          )}
          {status !== "sold" && (
            <button
              type="button"
              onClick={onMarkSold}
              className={`${itemClass} text-[var(--color-green)]`}
            >
              <CheckCircleIcon />
              Mark as Sold
            </button>
          )}
          <button
            type="button"
            onClick={onDelete}
            className={`${itemClass} text-[var(--color-red)]`}
          >
            <TrashIcon />
            Remove Quote
          </button>
        </div>
      )}
    </div>
  );
}
