"use client";

import type { Domain } from "@domainops/shared-types";
import { App, Button, Input, Popconfirm, Table, Tooltip, Typography } from "antd";
import { DeleteOutlined, UndoOutlined } from "@ant-design/icons";
import type { ColumnsType } from "antd/es/table";
import { useCallback, useEffect, useState } from "react";
import { deleteDomain, listDomains, restoreDomain } from "@/lib/api/domains";
import { ApiError } from "@/lib/api/client";
import { SORT_DIRECTIONS } from "@/lib/utils/sort";
import { DEFAULT_PAGE_SIZE, serverPaginationConfig, useServerPagination } from "@/lib/hooks/useServerPagination";
import { useAuth } from "@/lib/auth/AuthProvider";
import { formatDate } from "@/lib/utils/date";
import { titleCase } from "@/lib/utils/text";
import { DomainStatusTag } from "@/components/features/DomainStatusTag";
import { PageGuide } from "@/components/features/PageGuide";
import { ARCHIVED_DOMAINS_GUIDES } from "@/lib/guides/domains";

export default function ArchivedDomainsPage() {
  const { message } = App.useApp();
  const { user: currentUser } = useAuth();
  const [domains, setDomains] = useState<Domain[]>([]);
  const [total, setTotal] = useState(0);
  const { page, pageSize, setPage, onChange: onPageChange } = useServerPagination(DEFAULT_PAGE_SIZE, "domains-archived");
  const [sortOrder, setSortOrder] = useState<"ascend" | "descend" | undefined>();
  const [search, setSearch] = useState("");
  const [isLoading, setIsLoading] = useState(true);

  const load = useCallback(async () => {
    setIsLoading(true);
    try {
      const result = await listDomains({ archived: true, search, page, per_page: pageSize, sort: sortOrder ? "fqdn" : undefined, order: sortOrder });
      setDomains(result.data);
      setTotal(result.meta.total);
    } catch (err) {
      message.error(err instanceof ApiError ? err.message : "Couldn't load archived domains.");
    } finally {
      setIsLoading(false);
    }
  }, [search, sortOrder, page, pageSize, message]);

  useEffect(() => {
    // eslint-disable-next-line react-hooks/set-state-in-effect
    void load();
  }, [load]);

  async function handleRestore(domain: Domain) {
    try {
      await restoreDomain(domain.id);
      message.success(`${domain.fqdn} restored to Domain Inventory.`);
      void load();
    } catch (err) {
      message.error(err instanceof ApiError ? err.message : "Couldn't restore that domain.");
    }
  }

  async function handleDelete(domain: Domain) {
    try {
      await deleteDomain(domain.id);
      message.success(`${domain.fqdn} permanently deleted.`);
      void load();
    } catch (err) {
      message.error(err instanceof ApiError ? err.message : "Couldn't delete that domain.");
    }
  }

  const columns: ColumnsType<Domain> = [
    { title: "Domain", dataIndex: "fqdn", sorter: true, sortOrder: sortOrder ?? null, sortDirections: SORT_DIRECTIONS, render: (v: string) => <span className="font-mono">{v}</span> },
    { title: "Project", render: (_, domain) => domain.brand?.name ?? "—" },
    { title: "Status", dataIndex: "status", render: (v: Domain["status"]) => <DomainStatusTag status={v} /> },
    { title: "Expires", dataIndex: "expires_at", render: (v: string | null) => formatDate(v) },
    {
      title: "Reason",
      dataIndex: "archived_reason",
      render: (v: string | null | undefined) => (v ? titleCase(v) : "—"),
    },
    { title: "Notes", dataIndex: "archived_notes", render: (v: string | null | undefined) => v ?? "—" },
    { title: "Archived On", dataIndex: "deleted_at", render: (v: string | null | undefined) => formatDate(v) },
    {
      title: "Actions",
      render: (_, domain) => (
        <div className="flex gap-2">
          <Popconfirm title="Restore this domain to Domain Inventory?" onConfirm={() => handleRestore(domain)}>
            <Tooltip title="Restore">
              <Button size="small" icon={<UndoOutlined />} className="dms_archived_domains_restore_btn" />
            </Tooltip>
          </Popconfirm>
          {currentUser?.is_crowned_or_above && (
            <Popconfirm
              title="Permanently delete this domain?"
              description="This cannot be undone. Its subdomains and redirect history are deleted too."
              okText="Delete"
              okButtonProps={{ danger: true }}
              onConfirm={() => handleDelete(domain)}
            >
              <Tooltip title="Delete permanently">
                <Button size="small" danger icon={<DeleteOutlined />} className="dms_archived_domains_delete_btn" />
              </Tooltip>
            </Popconfirm>
          )}
        </div>
      ),
    },
  ];

  return (
    <div className="flex flex-col gap-4 page page-domains-archived">
      <div className="flex items-center gap-3">
        <Typography.Title level={4} style={{ margin: 0 }}>
          Archived Domains
        </Typography.Title>
        <PageGuide guides={ARCHIVED_DOMAINS_GUIDES} label="Archived Domains guide" />
        <Typography.Text type="secondary">{total} archived</Typography.Text>
      </div>
      <Input.Search
        allowClear
        placeholder="Search archived domains…"
        onSearch={(value) => {
          setPage(1);
          setSearch(value);
        }}
        style={{ width: 280 }}
        className="dms_archived_domains_search"
      />
      <Table<Domain>
        rowKey="id"
        columns={columns}
        dataSource={domains}
        loading={isLoading}
        onChange={(_pagination, _filters, sorter, extra) => {
          if (extra.action !== "sort") return;
          const active = Array.isArray(sorter) ? sorter[0] : sorter;
          setPage(1);
          setSortOrder(active?.order ?? undefined);
        }}
        pagination={serverPaginationConfig(total, page, pageSize, onPageChange, "archived")}
        className="dms_archived_domains_table"
      />
    </div>
  );
}
