"use client";

import {
  ActionIcon,
  Anchor,
  Badge,
  Group,
  Loader,
  Modal,
  Pagination,
  Select,
  SimpleGrid,
  Stack,
  Switch,
  Tabs,
  Text,
  Textarea,
  TextInput,
  ThemeIcon,
} from "@mantine/core";
import { useForm } from "@mantine/form";
import { notifications } from "@mantine/notifications";
import { useMutation, useQuery, useQueryClient } from "@tanstack/react-query";
import {
  ExternalLink,
  Globe,
  MapPin,
  Pencil,
  RefreshCw,
  Search,
  Sparkles,
  ToggleLeft,
  Trash2,
} from "lucide-react";
import Link from "next/link";
import { useMemo, useState } from "react";
import { DashboardPage } from "@/components/dashboard/DashboardPage";
import { DataTable, type Column } from "@/components/dashboard/DataTable";
import { PageHeader } from "@/components/dashboard/PageHeader";
import { GlassCard } from "@/components/ui/GlassCard";
import { PrimaryButton } from "@/components/ui/PrimaryButton";
import { seoCities } from "@/data/seo/cities";
import { seoSegments } from "@/data/seo/segments";
import { seoServices } from "@/data/seo/services";
import { seoStates } from "@/data/seo/states";
import { buildPriorityPagesForDb } from "@/lib/seo/export-for-db";
import { estimatePageCount } from "@/lib/seo/registry";
import { adminSeoService } from "@/services/adminSeoService";
import { useAuthStore } from "@/store/authStore";
import { colors } from "@/styles/tokens";
import {
  SeoGooglePreview,
  SeoLengthBar,
  seoDescriptionScore,
  seoTitleScore,
} from "@/components/admin/seo/SeoGooglePreview";
import { SEO_KEYWORDS_POOL_COUNT } from "@/data/seo/keywords-pool";
import { suggestKeywordsForAdminSlug } from "@/lib/seo/keyword-assignment";
import { APP_NAME, SITE_URL } from "@/utils/constants";
import type { SeoPageRecord } from "@/types/seoPage";

const SITE_HOST = (() => {
  try {
    return new URL(SITE_URL).host;
  } catch {
    return "localhost:3000";
  }
})();

const EXAMPLE_SLUGS = [
  "criacao-de-app-em-sao-paulo",
  "app-para-restaurante",
  "sistema-delivery-no-parana",
  "cardapio-digital-para-pizzaria-em-belo-horizonte",
];

function StatCard({
  label,
  value,
  hint,
}: {
  label: string;
  value: string | number;
  hint?: string;
}) {
  return (
    <GlassCard>
      <Text size="xs" tt="uppercase" c="dimmed" mb={4} style={{ letterSpacing: "0.08em" }}>
        {label}
      </Text>
      <Text size="xl" fw={800} c={colors.white}>
        {value}
      </Text>
      {hint && (
        <Text size="xs" c="dimmed" mt={4}>
          {hint}
        </Text>
      )}
    </GlassCard>
  );
}

export default function SeoDashboardPage() {
  const token = useAuthStore((s) => s.token);
  const user = useAuthStore((s) => s.user);
  const queryClient = useQueryClient();

  const [search, setSearch] = useState("");
  const [serviceFilter, setServiceFilter] = useState<string | null>(null);
  const [page, setPage] = useState(1);
  const [editing, setEditing] = useState<SeoPageRecord | null>(null);

  const programmaticTotal = useMemo(() => estimatePageCount(), []);

  const { data: statsRes, isLoading: statsLoading } = useQuery({
    queryKey: ["admin", "seo", "stats"],
    queryFn: () => adminSeoService.stats(token!),
    enabled: Boolean(token) && user?.role === "admin",
  });

  const { data: listRes, isLoading: listLoading } = useQuery({
    queryKey: ["admin", "seo", "pages", search, serviceFilter, page],
    queryFn: () =>
      adminSeoService.list(token!, {
        search: search || undefined,
        service: serviceFilter ?? undefined,
        page,
        per_page: 15,
      }),
    enabled: Boolean(token) && user?.role === "admin",
  });

  const stats = statsRes?.data;
  const pages = listRes?.data ?? [];
  const meta = listRes?.meta;

  const form = useForm({
    initialValues: {
      title: "",
      metaDescription: "",
      keywords: "",
      canonicalUrl: "",
      active: true,
    },
  });

  const openEdit = (row: SeoPageRecord) => {
    form.setValues({
      title: row.title,
      metaDescription: row.metaDescription,
      keywords: row.keywords ?? "",
      canonicalUrl: row.canonicalUrl,
      active: row.active,
    });
    setEditing(row);
  };

  const saveMutation = useMutation({
    mutationFn: () =>
      adminSeoService.update(token!, editing!.id, {
        title: form.values.title,
        metaDescription: form.values.metaDescription,
        keywords: form.values.keywords,
        canonicalUrl: form.values.canonicalUrl,
        active: form.values.active,
      }),
    onSuccess: () => {
      queryClient.invalidateQueries({ queryKey: ["admin", "seo"] });
      setEditing(null);
      notifications.show({ message: "Página SEO salva.", color: "green" });
    },
    onError: (e: Error) => {
      notifications.show({ message: e.message, color: "red" });
    },
  });

  const syncMutation = useMutation({
    mutationFn: async () => {
      const batch = buildPriorityPagesForDb(200);
      const chunkSize = 100;
      let total = 0;
      for (let i = 0; i < batch.length; i += chunkSize) {
        const chunk = batch.slice(i, i + chunkSize);
        const res = await adminSeoService.bulkUpsert(token!, chunk);
        total += res.data?.upserted ?? chunk.length;
      }
      return total;
    },
    onSuccess: (total) => {
      queryClient.invalidateQueries({ queryKey: ["admin", "seo"] });
      notifications.show({
        message: `${total} páginas prioritárias sincronizadas no banco.`,
        color: "green",
      });
    },
    onError: (e: Error) => {
      notifications.show({
        message: e.message || "Erro ao sincronizar. Rode a migration seo_pages?",
        color: "red",
      });
    },
  });

  const toggleMutation = useMutation({
    mutationFn: (id: number) => adminSeoService.toggle(token!, id),
    onSuccess: () => queryClient.invalidateQueries({ queryKey: ["admin", "seo"] }),
  });

  const deleteMutation = useMutation({
    mutationFn: (id: number) => adminSeoService.remove(token!, id),
    onSuccess: () => {
      queryClient.invalidateQueries({ queryKey: ["admin", "seo"] });
      notifications.show({ message: "Página removida.", color: "green" });
    },
  });

  const columns: Column<SeoPageRecord>[] = [
    {
      key: "slug",
      label: "Slug / URL",
      render: (row) => (
        <Stack gap={2}>
          <Text size="sm" fw={600} c={colors.grayLight}>
            {row.slug}
          </Text>
          <Anchor
            component={Link}
            href={`/${row.slug}`}
            target="_blank"
            size="xs"
            c={colors.primary}
          >
            Ver página <ExternalLink size={12} style={{ verticalAlign: "middle" }} />
          </Anchor>
        </Stack>
      ),
    },
    { key: "title", label: "Título" },
    {
      key: "city",
      label: "Local",
      render: (row) => (
        <Text size="sm">
          {[row.city, row.state].filter(Boolean).join(" · ") || "—"}
        </Text>
      ),
    },
    {
      key: "active",
      label: "Status",
      render: (row) => (
        <Badge color={row.active ? "green" : "gray"} variant="light">
          {row.active ? "Ativa" : "Inativa"}
        </Badge>
      ),
    },
    {
      key: "actions",
      label: "",
      render: (row) => (
        <Group gap="xs" wrap="nowrap">
          <ActionIcon variant="subtle" onClick={() => openEdit(row)} aria-label="Editar">
            <Pencil size={16} />
          </ActionIcon>
          <ActionIcon
            variant="subtle"
            onClick={() => toggleMutation.mutate(row.id)}
            aria-label="Ativar/desativar"
          >
            <ToggleLeft size={16} />
          </ActionIcon>
          <ActionIcon
            variant="subtle"
            color="red"
            onClick={() => deleteMutation.mutate(row.id)}
            aria-label="Excluir"
          >
            <Trash2 size={16} />
          </ActionIcon>
        </Group>
      ),
    },
  ];

  if (user?.role !== "admin") {
    return (
      <DashboardPage title="SEO Local">
        <Text c="dimmed">Acesso restrito a administradores.</Text>
      </DashboardPage>
    );
  }

  return (
    <DashboardPage title="SEO Local">
      <PageHeader
        title="SEO Local & Programático"
        description="Milhares de landing pages por cidade, estado e segmento — gestão, indexação e banco."
        actions={
          <Group>
            <PrimaryButton
              leftSection={<RefreshCw size={16} />}
              loading={syncMutation.isPending}
              onClick={() => syncMutation.mutate()}
            >
              Sincronizar prioritárias
            </PrimaryButton>
          </Group>
        }
      />

      <Tabs defaultValue="overview" mb="xl">
        <Tabs.List>
          <Tabs.Tab value="overview" leftSection={<Globe size={14} />}>
            Visão geral
          </Tabs.Tab>
          <Tabs.Tab value="pages" leftSection={<MapPin size={14} />}>
            Páginas no banco
          </Tabs.Tab>
        </Tabs.List>

        <Tabs.Panel value="overview" pt="lg">
          <SimpleGrid cols={{ base: 1, sm: 2, lg: 4 }} mb="lg">
            <StatCard
              label="Páginas programáticas"
              value={programmaticTotal.toLocaleString("pt-BR")}
              hint="Combinações serviço × segmento × local"
            />
            <StatCard
              label="Serviços"
              value={seoServices.length}
            />
            <StatCard
              label="Segmentos"
              value={seoSegments.length}
            />
            <StatCard
              label="Cidades"
              value={seoCities.length}
              hint={`${seoStates.length} estados`}
            />
          </SimpleGrid>

          <SimpleGrid cols={{ base: 1, md: 2 }} mb="lg">
            <StatCard
              label="No banco (total)"
              value={statsLoading ? "…" : (stats?.dbTotal ?? 0)}
            />
            <StatCard
              label="Ativas no banco"
              value={statsLoading ? "…" : (stats?.dbActive ?? 0)}
              hint="Use sincronizar para popular páginas prioritárias"
            />
          </SimpleGrid>

          <GlassCard mb="lg">
            <Group gap="sm" mb="md">
              <ThemeIcon size="lg" radius="md" variant="light" color="blue">
                <Sparkles size={18} />
              </ThemeIcon>
              <Stack gap={0}>
                <Text fw={700}>Como funciona</Text>
                <Text size="sm" c="dimmed">
                  O site gera páginas automaticamente via Next.js (ISR). O banco{" "}
                  <code>seo_pages</code> guarda overrides e metadados para gestão futura.
                </Text>
              </Stack>
            </Group>
            <Text size="sm" c="dimmed" mb="sm">
              Meta tags globais do site:{" "}
              <Anchor component={Link} href="/dashboard/conteudo">
                Conteúdo → grupo SEO
              </Anchor>
            </Text>
            <Text size="sm" c="dimmed" mb="md">
              Sitemap:{" "}
              <Anchor href={`${SITE_URL}/sitemap.xml`} target="_blank">
                {SITE_URL}/sitemap.xml
              </Anchor>
            </Text>
            <Text size="xs" tt="uppercase" c="dimmed" mb="xs">
              Exemplos ao vivo
            </Text>
            <Group gap="xs">
              {EXAMPLE_SLUGS.map((slug) => (
                <Badge
                  key={slug}
                  component={Link}
                  href={`/${slug}`}
                  target="_blank"
                  variant="outline"
                  style={{ cursor: "pointer" }}
                >
                  /{slug}
                </Badge>
              ))}
            </Group>
          </GlassCard>
        </Tabs.Panel>

        <Tabs.Panel value="pages" pt="lg">
          <GlassCard mb="lg">
            <Group align="flex-end" wrap="wrap">
              <TextInput
                label="Buscar"
                placeholder="slug, título, cidade…"
                leftSection={<Search size={16} />}
                value={search}
                onChange={(e) => {
                  setSearch(e.currentTarget.value);
                  setPage(1);
                }}
                style={{ flex: 1, minWidth: 200 }}
              />
              <Select
                label="Serviço"
                placeholder="Todos"
                clearable
                data={seoServices.map((s) => ({ value: s.slug, label: s.name }))}
                value={serviceFilter}
                onChange={(v) => {
                  setServiceFilter(v);
                  setPage(1);
                }}
                w={220}
              />
            </Group>
          </GlassCard>

          {listLoading ? (
            <Loader color="nogahost" />
          ) : pages.length === 0 ? (
            <GlassCard>
              <Stack gap="md" align="center" py="xl">
                <Text c="dimmed" ta="center">
                  Nenhuma página no banco ainda. Clique em &quot;Sincronizar prioritárias&quot; para
                  importar até 200 landing pages ou rode{" "}
                  <code>php artisan migrate</code> se a tabela não existir.
                </Text>
                <PrimaryButton
                  loading={syncMutation.isPending}
                  onClick={() => syncMutation.mutate()}
                >
                  Sincronizar agora
                </PrimaryButton>
              </Stack>
            </GlassCard>
          ) : (
            <>
              <DataTable columns={columns} data={pages} />
              {meta && meta.lastPage > 1 && (
                <Group justify="center" mt="lg">
                  <Pagination
                    total={meta.lastPage}
                    value={page}
                    onChange={setPage}
                    color="blue"
                  />
                </Group>
              )}
            </>
          )}
        </Tabs.Panel>
      </Tabs>

      <Modal
        opened={Boolean(editing)}
        onClose={() => setEditing(null)}
        title="Editar página SEO"
        size="lg"
        classNames={{ content: "noga-seo-edit-modal" }}
      >
        <Stack gap="lg">
          <Text size="sm" c="dimmed">
            Slug: <strong>{editing?.slug}</strong>
          </Text>

          <SeoGooglePreview
            title={form.values.title}
            metaDescription={form.values.metaDescription}
            slug={editing?.slug ?? ""}
            siteName={APP_NAME}
            siteHost={SITE_HOST}
            updatedAt={editing?.updatedAt}
          />

          <Stack gap="xs">
            <TextInput label="Título SEO" {...form.getInputProps("title")} />
            <SeoLengthBar
              length={form.values.title.length}
              score={seoTitleScore(form.values.title.length)}
            />
          </Stack>

          <TextInput
            label="Slug (URL)"
            value={editing?.slug ?? ""}
            readOnly
            description={`${SITE_HOST}/${editing?.slug ?? ""}`}
          />

          <Stack gap="xs">
            <Textarea
              label="Metadescrição"
              minRows={3}
              {...form.getInputProps("metaDescription")}
            />
            <SeoLengthBar
              length={form.values.metaDescription.length}
              score={seoDescriptionScore(form.values.metaDescription.length)}
            />
          </Stack>

          <Stack gap="xs">
            <Group justify="space-between" align="flex-end" wrap="wrap" gap="xs">
              <Text size="sm" fw={600}>
                Keywords
              </Text>
              <Button
                variant="light"
                color="violet"
                size="xs"
                leftSection={<Sparkles size={14} />}
                onClick={() => {
                  if (!editing) return;
                  form.setFieldValue(
                    "keywords",
                    suggestKeywordsForAdminSlug(
                      editing.slug,
                      editing.service,
                      editing.segment,
                    ),
                  );
                }}
              >
                Sugerir do catálogo ({SEO_KEYWORDS_POOL_COUNT})
              </Button>
            </Group>
            <TextInput
              placeholder="Separadas por vírgula — uma intenção principal por página"
              {...form.getInputProps("keywords")}
            />
            <Text size="xs" c="dimmed">
              O catálogo de {SEO_KEYWORDS_POOL_COUNT} termos é distribuído automaticamente nas
              landing pages programáticas para evitar canibalização. Use termos específicos desta
              URL ao editar manualmente.
            </Text>
          </Stack>
          <TextInput label="URL canônica" {...form.getInputProps("canonicalUrl")} />
          <Switch label="Página ativa" {...form.getInputProps("active", { type: "checkbox" })} />
          <PrimaryButton loading={saveMutation.isPending} onClick={() => saveMutation.mutate()}>
            Salvar
          </PrimaryButton>
        </Stack>
      </Modal>
    </DashboardPage>
  );
}
