"use client";

import Link from "next/link";
import { useCallback, useEffect, useState } from "react";
import { PlusIcon } from "@heroicons/react/24/outline";
import { Button } from "@/components/Button";
import { DashboardPageContainer } from "@/components/dashboard/DashboardPageContainer";
import { DashboardShell } from "@/components/dashboard/DashboardShell";
import { EmptyState } from "@/components/ui/EmptyState";
import { ErrorState } from "@/components/ui/ErrorState";
import { PageHeader } from "@/components/ui/PageHeader";
import { Skeleton } from "@/components/ui/Skeleton";
import { StatusBadge } from "@/components/ui/StatusBadge";
import { ApiError } from "@/lib/api";
import { campaignApi } from "@/lib/api/campaigns";
import { campaignStatusBadgeVariant, campaignStatusLabel } from "@/lib/campaigns";
import { formatDateRange, formatMoneyMinor, formatRelativeTime } from "@/lib/format";
import type { CampaignListItem, CampaignListMeta } from "@/types/campaign";

const BRAND_ONLY = ["brand"] as const;
const PER_PAGE = 20;

function CampaignTableSkeleton() {
  return (
    <div className="overflow-hidden rounded-pv border border-line bg-surface">
      <div className="hidden border-b border-line px-3 py-2 md:grid md:grid-cols-[minmax(0,1.4fr)_7rem_7rem_9rem_6rem_4rem] md:gap-3">
        {Array.from({ length: 6 }).map((_, index) => (
          <Skeleton key={index} className="h-3 w-16" />
        ))}
      </div>
      {Array.from({ length: 4 }).map((_, index) => (
        <div
          key={index}
          className="border-b border-line px-3 py-3 last:border-b-0 md:grid md:grid-cols-[minmax(0,1.4fr)_7rem_7rem_9rem_6rem_4rem] md:items-center md:gap-3"
        >
          <Skeleton className="h-4 w-40" />
          <Skeleton className="mt-2 h-4 w-16 md:mt-0" />
          <Skeleton className="mt-2 h-4 w-16 md:mt-0" />
          <Skeleton className="mt-2 h-4 w-28 md:mt-0" />
          <Skeleton className="mt-2 h-4 w-12 md:mt-0" />
          <Skeleton className="mt-2 h-4 w-10 md:mt-0" />
        </div>
      ))}
    </div>
  );
}

function CampaignMobileCard({ campaign }: { campaign: CampaignListItem }) {
  return (
    <li className="rounded-pv border border-line bg-surface px-3 py-3">
      <div className="flex items-start justify-between gap-3">
        <div className="min-w-0">
          <p className="truncate text-[0.875rem] font-medium text-primary">{campaign.name}</p>
          <div className="mt-1.5 flex flex-wrap items-center gap-2">
            <StatusBadge variant={campaignStatusBadgeVariant(campaign.status)}>
              {campaignStatusLabel(campaign.status)}
            </StatusBadge>
            <span className="text-[0.8125rem] tabular-nums text-ink-60">
              {formatMoneyMinor(campaign.budget_amount, campaign.currency)}
            </span>
          </div>
          <p className="mt-1.5 text-[0.75rem] text-ink-40">
            {formatDateRange(campaign.start_date, campaign.end_date)} ·{" "}
            {formatRelativeTime(campaign.updated_at)}
          </p>
        </div>
        <Link
          href={`/dashboard/campaigns/${campaign.id}`}
          className="shrink-0 text-[0.8125rem] font-medium text-accent hover:text-accent-hover"
        >
          View
        </Link>
      </div>
    </li>
  );
}

function BrandCampaignsContent() {
  const [campaigns, setCampaigns] = useState<CampaignListItem[]>([]);
  const [meta, setMeta] = useState<CampaignListMeta | null>(null);
  const [page, setPage] = useState(1);
  const [isLoading, setIsLoading] = useState(true);
  const [error, setError] = useState<string | null>(null);

  const load = useCallback(async (nextPage: number) => {
    setIsLoading(true);
    setError(null);

    try {
      const result = await campaignApi.list({ page: nextPage, per_page: PER_PAGE });
      setCampaigns(result.campaigns);
      setMeta(result.meta);
      setPage(result.meta.current_page);
    } catch (err) {
      const message =
        err instanceof ApiError ? err.message : "Unable to load campaigns.";
      setError(message);
      setCampaigns([]);
      setMeta(null);
    } finally {
      setIsLoading(false);
    }
  }, []);

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

  return (
    <DashboardPageContainer>
      <PageHeader
        description="Create and manage your creator campaigns."
        actions={
          <Button href="/dashboard/campaigns/new" size="sm">
            <PlusIcon className="size-4" aria-hidden="true" />
            <span>Create campaign</span>
          </Button>
        }
      />

      {error ? (
        <ErrorState
          title="Couldn’t load campaigns"
          message={error}
          action={
            <Button size="sm" onClick={() => void load(page)}>
              Try again
            </Button>
          }
        />
      ) : null}

      {isLoading ? <CampaignTableSkeleton /> : null}

      {!isLoading && !error && campaigns.length === 0 ? (
        <EmptyState
          title="No campaigns yet"
          description="Create your first campaign to start working with creators."
          action={
            <Button href="/dashboard/campaigns/new" size="sm">
              <PlusIcon className="size-4" aria-hidden="true" />
              <span>Create campaign</span>
            </Button>
          }
        />
      ) : null}

      {!isLoading && !error && campaigns.length > 0 ? (
        <>
          <div className="hidden overflow-x-auto rounded-pv border border-line bg-surface md:block">
            <table className="min-w-full text-left">
              <thead>
                <tr className="border-b border-line text-[0.6875rem] uppercase tracking-[0.06em] text-ink-40">
                  <th className="px-3 py-2.5 font-medium">Campaign</th>
                  <th className="px-3 py-2.5 font-medium">Status</th>
                  <th className="px-3 py-2.5 font-medium">Budget</th>
                  <th className="px-3 py-2.5 font-medium">Timeline</th>
                  <th className="px-3 py-2.5 font-medium">Updated</th>
                  <th className="px-3 py-2.5 font-medium">Action</th>
                </tr>
              </thead>
              <tbody>
                {campaigns.map((campaign) => (
                  <tr key={campaign.id} className="border-b border-line last:border-b-0 hover:bg-bg/80">
                    <td className="px-3 py-2.5 text-[0.8125rem] font-medium text-primary">
                      <Link
                        href={`/dashboard/campaigns/${campaign.id}`}
                        className="hover:text-accent"
                      >
                        {campaign.name}
                      </Link>
                    </td>
                    <td className="px-3 py-2.5">
                      <StatusBadge variant={campaignStatusBadgeVariant(campaign.status)}>
                        {campaignStatusLabel(campaign.status)}
                      </StatusBadge>
                    </td>
                    <td className="px-3 py-2.5 text-[0.8125rem] tabular-nums text-ink-60">
                      {formatMoneyMinor(campaign.budget_amount, campaign.currency)}
                    </td>
                    <td className="px-3 py-2.5 text-[0.8125rem] text-ink-60">
                      {formatDateRange(campaign.start_date, campaign.end_date)}
                    </td>
                    <td className="px-3 py-2.5 text-[0.8125rem] text-ink-40">
                      {formatRelativeTime(campaign.updated_at)}
                    </td>
                    <td className="px-3 py-2.5">
                      <Link
                        href={`/dashboard/campaigns/${campaign.id}`}
                        className="text-[0.8125rem] font-medium text-accent hover:text-accent-hover"
                      >
                        View
                      </Link>
                    </td>
                  </tr>
                ))}
              </tbody>
            </table>
          </div>

          <ul className="space-y-2 md:hidden">
            {campaigns.map((campaign) => (
              <CampaignMobileCard key={campaign.id} campaign={campaign} />
            ))}
          </ul>

          {meta && meta.last_page > 1 ? (
            <div className="flex items-center justify-between gap-3">
              <p className="text-[0.75rem] text-ink-40">
                Page {meta.current_page} of {meta.last_page}
              </p>
              <div className="flex gap-2">
                <Button
                  size="sm"
                  variant="secondary"
                  disabled={meta.current_page <= 1 || isLoading}
                  onClick={() => void load(meta.current_page - 1)}
                >
                  Previous
                </Button>
                <Button
                  size="sm"
                  variant="secondary"
                  disabled={meta.current_page >= meta.last_page || isLoading}
                  onClick={() => void load(meta.current_page + 1)}
                >
                  Next
                </Button>
              </div>
            </div>
          ) : null}
        </>
      ) : null}
    </DashboardPageContainer>
  );
}

export function BrandCampaignsPage() {
  return (
    <DashboardShell title="Campaigns" allowedAccountTypes={BRAND_ONLY}>
      {() => <BrandCampaignsContent />}
    </DashboardShell>
  );
}
