// src/components/keywords/planning/planning-table.tsx
// Planning table (replaces BriefingContainer). Columns: select · Terme · Pays ·
// Vol · KD · SERP · On-page · Brief · Sources · ✕. Row click opens the centered
// KeywordOverviewModal. Adapted from the "Planning & Overview" mockup, rendered
// with this app's tokens + shadcn primitives.
"use client";

import { SparklesIcon, XIcon } from "lucide-react";
import { useRouter } from "next/navigation";
import { useMemo, useState } from "react";
import { toast } from "sonner";
import { FacetRow, FiltersPanel } from "@/components/keywords/filters-panel";
import { ImportBriefDialog } from "@/components/keywords/import-brief-dialog";
import { INTENT_LABELS } from "@/components/keywords/intent-badge";
import { KeywordsToolbar } from "@/components/keywords/keywords-toolbar";
import { PromoteToContentDialog } from "@/components/keywords/promote-content-dialog";
import { useSerankingSync } from "@/components/keywords/seranking-sync-dialog";
import { SourceDots } from "@/components/keywords/source-dots";
import { SourcesModal } from "@/components/keywords/sources/sources-modal";
import { SyncMenu } from "@/components/keywords/sync-menu";
import { TargetPageCell } from "@/components/keywords/target-page-cell";
import { Button } from "@/components/ui/button";
import { Checkbox } from "@/components/ui/checkbox";
import {
  FacetMenuContent,
  ToolbarDivider,
  ToolbarPanel,
  ToolbarRow,
  ToolbarSearch,
} from "@/components/ui/design-toolbar";
import { Flag } from "@/components/ui/flag";
import {
  FloatingBulkBar,
  FloatingBulkBarSeparator,
} from "@/components/ui/floating-bulk-bar";
import { useMangoolsSync } from "@/hooks/use-mangools-sync";
import type { ContentAnalysis } from "@/lib/content/types";
import {
  addKeywordsToStageAction,
  removeKeywordFromStageAction,
} from "@/lib/keywords/actions";
import type { ReadyState } from "@/lib/keywords/prompt/types";
import type { PlanningRow } from "@/lib/keywords/queries";
import { cn } from "@/lib/utils";
import { KeywordOverviewModal } from "./keyword-overview-modal";
import { ReadinessDot, ReadinessLegend } from "./readiness-dot";

/** French compact volume: 1 300 → « 1,3 k ». */
function formatVolume(v: number | null): string {
  if (v == null) return "—";
  return v >= 1000
    ? `${(v / 1000).toLocaleString("fr-FR", { maximumFractionDigits: 1 })} k`
    : v.toLocaleString("fr-FR");
}

function kdClasses(kd: number): string {
  if (kd < 30)
    return "bg-emerald-500/14 text-emerald-600 dark:text-emerald-300";
  if (kd < 45) return "bg-amber-500/14 text-amber-600 dark:text-amber-300";
  return "bg-red-500/14 text-red-600 dark:text-red-300";
}

function serpReady(a: ContentAnalysis): ReadyState {
  return a.serp.state === "ok" ? "ready" : "missing";
}
function onpageReady(a: ContentAnalysis): ReadyState {
  if (a.onpage.state === "ok") return "ready";
  if (a.onpage.state === "partial") return "progress";
  return "missing";
}
function briefReady(a: ContentAnalysis): ReadyState {
  if (a.brief.state === "ok") return "ready";
  if (a.brief.state === "other-locale") return "progress";
  return "missing";
}

/** Primary-source reference metrics for the keyword (vol/kd from primarySource). */
function primaryMetrics(row: PlanningRow) {
  const k = row.keyword;
  return k.metrics[k.primarySource] ?? null;
}

export function PlanningTable({
  siteId,
  initialRows,
  serankingEnabled,
  mangoolsConnected,
  initialSyncStatus,
  canImportGsc,
  analyticsEnabled,
  defaultLang,
}: {
  siteId: string | null;
  initialRows: PlanningRow[];
  /** Feature SE-Ranking configurée (undefined/false → menu « Sync » absent). */
  serankingEnabled?: boolean;
  /** Connecteur Mangools branché (org active) → entrée « Enrichir via Mangools »
   *  dans le menu « Sync ». Résolu RSC via `getMangoolsStatus()`. */
  mangoolsConnected?: boolean;
  /** Horodatages de dernière sync (footer du menu « Sync »), fetch RSC. */
  initialSyncStatus: {
    lastGscSyncAt: string | null;
    lastSerankingSyncAt: string | null;
    lastMangoolsSyncAt: string | null;
  };
  /** Rôle owner/admin → entrée « Importer depuis GSC » dans la toolbar. */
  canImportGsc?: boolean;
  /** Feature analytics configurée → entrée « Importer un CSV » dans la toolbar. */
  analyticsEnabled?: boolean;
  /** Langue primaire du site — présélectionne le picker « Langue » de l'import CSV. */
  defaultLang?: string;
}) {
  const router = useRouter();
  const rows = initialRows;
  const [syncStatus, setSyncStatus] = useState(initialSyncStatus);

  const [query, setQuery] = useState("");
  const [country, setCountry] = useState<string>("all");
  const [status, setStatus] = useState<string>("all");
  const [serpFilter, setSerpFilter] = useState<string>("all");
  const [onpageFilter, setOnpageFilter] = useState<string>("all");
  const [briefFilter, setBriefFilter] = useState<string>("all");
  const [sel, setSel] = useState<Record<string, boolean>>({});

  const [overviewId, setOverviewId] = useState<string | null>(null);
  const [overviewOpen, setOverviewOpen] = useState(false);
  const [promoteOpen, setPromoteOpen] = useState(false);
  const [briefForId, setBriefForId] = useState<string | null>(null);
  const [sourcesOpen, setSourcesOpen] = useState(false);

  const countries = useMemo(() => {
    const set = new Set<string>();
    for (const r of rows) set.add(r.keyword.locale.country);
    return [...set].sort();
  }, [rows]);

  const filtered = useMemo(() => {
    const q = query.trim().toLowerCase();
    return rows.filter((r) => {
      if (q && !r.keyword.term.toLowerCase().includes(q)) return false;
      if (country !== "all" && r.keyword.locale.country !== country)
        return false;
      if (status !== "all") {
        const ready =
          r.analysis.serp.state === "ok" &&
          r.analysis.onpage.state === "ok" &&
          r.analysis.brief.state === "ok";
        if (status === "ready" && !ready) return false;
        if (status === "incomplete" && ready) return false;
      }
      if (serpFilter !== "all" && serpReady(r.analysis) !== serpFilter)
        return false;
      if (onpageFilter !== "all" && onpageReady(r.analysis) !== onpageFilter)
        return false;
      if (briefFilter !== "all" && briefReady(r.analysis) !== briefFilter)
        return false;
      return true;
    });
  }, [rows, query, country, status, serpFilter, onpageFilter, briefFilter]);

  const selectedKeywordObjs = useMemo(
    () =>
      rows
        .filter((r) => sel[r.keyword.id])
        .map((r) => ({ id: r.keyword.id, term: r.keyword.term })),
    [rows, sel],
  );

  function openOverview(id: string) {
    setOverviewId(id);
    setOverviewOpen(true);
  }

  // Position of the open keyword in the currently filtered/displayed order —
  // drives the panel's header "n / total" and its ↑/↓ navigation, which must
  // follow the same order the user sees in the table, not the raw `rows`.
  const overviewIndex = useMemo(
    () =>
      overviewId ? filtered.findIndex((r) => r.keyword.id === overviewId) : -1,
    [filtered, overviewId],
  );

  function navigateOverview(dir: -1 | 1) {
    if (overviewIndex < 0) return;
    const next = filtered[overviewIndex + dir];
    if (next) setOverviewId(next.keyword.id);
  }

  function remove(keywordId: string) {
    if (!siteId) return;
    void removeKeywordFromStageAction(siteId, keywordId, "planning")
      .then(() => {
        toast.success("Retiré du planning", {
          // Le défaut sonner (4 s) est trop court pour décider d'annuler.
          duration: 10_000,
          action: {
            label: "Annuler",
            onClick: () => {
              void addKeywordsToStageAction(siteId, [keywordId], "planning")
                .then(() => {
                  toast.success("Annulé");
                  router.refresh();
                })
                .catch(() => toast.error("Échec de l'annulation"));
            },
          },
        });
        router.refresh();
      })
      .catch(() => toast.error("Échec du retrait"));
  }

  const {
    open: openSerankingSync,
    dialog: serankingSyncDialog,
    syncing: serankingSyncing,
  } = useSerankingSync(siteId ?? "", {
    onDone: () => {
      setSyncStatus((s) => ({
        ...s,
        lastSerankingSyncAt: new Date().toISOString(),
      }));
      setSel({});
      router.refresh();
    },
  });
  function syncSeranking() {
    if (!siteId) return;
    const ids = Object.keys(sel).filter((k) => sel[k]);
    if (ids.length === 0) return;
    openSerankingSync({ mode: "ids", ids });
  }

  // Enrichissement Mangools — même mécanisme de sélection que SE-Ranking sur
  // cette surface (Planning n'a pas le mode « N filtrés » du réservoir : on
  // envoie les ids explicitement cochés). Optimiste : on avance l'horodatage du
  // footer dès la mise en file et on vide la sélection (le worker enrichit en
  // arrière-plan ; router.refresh remontera les métriques au prochain rendu).
  const { syncSelection: syncMangoolsSelection, syncing: mangoolsSyncing } =
    useMangoolsSync(siteId ?? "", {
      onQueued: () => {
        setSyncStatus((s) => ({
          ...s,
          lastMangoolsSyncAt: new Date().toISOString(),
        }));
        setSel({});
        router.refresh();
      },
    });
  function syncMangools() {
    if (!siteId) return;
    const ids = Object.keys(sel).filter((k) => sel[k]);
    if (ids.length === 0) return;
    syncMangoolsSelection({ mode: "ids", ids });
  }

  const allFilteredSelected =
    filtered.length > 0 && filtered.every((r) => sel[r.keyword.id]);

  const filtersActive =
    (country !== "all" ? 1 : 0) +
    (status !== "all" ? 1 : 0) +
    (serpFilter !== "all" ? 1 : 0) +
    (onpageFilter !== "all" ? 1 : 0) +
    (briefFilter !== "all" ? 1 : 0);

  return (
    <div className="p-4">
      {/* Design panel (finale-B, slice 3) : bande sticky (toolbar) + table. */}
      <ToolbarPanel>
        {/* Bande de pilotage sticky — même pattern que Recherche/Réservoir. */}
        <div className="sticky top-0 z-20 rounded-t-2xl border-b bg-background/95 backdrop-blur supports-[backdrop-filter]:bg-background/80">
          <ToolbarRow className="border-b-0">
            <div className="flex min-w-0 flex-1 flex-wrap items-center gap-2.5">
              <ToolbarSearch
                value={query}
                onChange={setQuery}
                placeholder="Rechercher un terme…"
                ariaLabel="Rechercher un terme"
              />
              <FiltersPanel
                activeCount={filtersActive}
                onResetAll={() => {
                  setCountry("all");
                  setStatus("all");
                  setSerpFilter("all");
                  setOnpageFilter("all");
                  setBriefFilter("all");
                }}
              >
                <FacetRow
                  label="Pays"
                  ariaLabel="Filtrer par pays"
                  value={
                    country === "all"
                      ? "Tous"
                      : // Résumé du filtre = texte (type string) : code seul, sans drapeau.
                        country.toUpperCase()
                  }
                  active={country !== "all"}
                >
                  <FacetMenuContent
                    allLabel="Tous pays"
                    value={country}
                    options={countries.map((c) => ({
                      value: c,
                      label: (
                        <span className="inline-flex items-center gap-1.5">
                          <Flag code={c} />
                          {c.toUpperCase()}
                        </span>
                      ),
                    }))}
                    onChange={setCountry}
                  />
                </FacetRow>
                <FacetRow
                  label="Préparation"
                  ariaLabel="Filtrer par état de préparation"
                  value={
                    status === "ready"
                      ? "Prêt"
                      : status === "incomplete"
                        ? "Incomplet"
                        : "Tous"
                  }
                  active={status !== "all"}
                >
                  <FacetMenuContent
                    allLabel="Tous statuts"
                    value={status}
                    options={[
                      { value: "ready", label: "Prêt" },
                      { value: "incomplete", label: "Incomplet" },
                    ]}
                    onChange={setStatus}
                  />
                </FacetRow>
                <FacetRow
                  label="SERP"
                  ariaLabel="Filtrer par état SERP"
                  value={
                    serpFilter === "ready"
                      ? "Prêt"
                      : serpFilter === "missing"
                        ? "Manquant"
                        : "Tous"
                  }
                  active={serpFilter !== "all"}
                >
                  <FacetMenuContent
                    allLabel="Tous"
                    value={serpFilter}
                    options={[
                      { value: "ready", label: "Prêt" },
                      { value: "missing", label: "Manquant" },
                    ]}
                    onChange={setSerpFilter}
                  />
                </FacetRow>
                <FacetRow
                  label="On-page"
                  ariaLabel="Filtrer par état on-page"
                  value={
                    onpageFilter === "ready"
                      ? "Prêt"
                      : onpageFilter === "progress"
                        ? "En cours"
                        : onpageFilter === "missing"
                          ? "Manquant"
                          : "Tous"
                  }
                  active={onpageFilter !== "all"}
                >
                  <FacetMenuContent
                    allLabel="Tous"
                    value={onpageFilter}
                    options={[
                      { value: "ready", label: "Prêt" },
                      { value: "progress", label: "En cours" },
                      { value: "missing", label: "Manquant" },
                    ]}
                    onChange={setOnpageFilter}
                  />
                </FacetRow>
                <FacetRow
                  label="Brief"
                  ariaLabel="Filtrer par état brief"
                  value={
                    briefFilter === "ready"
                      ? "Prêt"
                      : briefFilter === "progress"
                        ? "En cours"
                        : briefFilter === "missing"
                          ? "Manquant"
                          : "Tous"
                  }
                  active={briefFilter !== "all"}
                >
                  <FacetMenuContent
                    allLabel="Tous"
                    value={briefFilter}
                    options={[
                      { value: "ready", label: "Prêt" },
                      { value: "progress", label: "En cours" },
                      { value: "missing", label: "Manquant" },
                    ]}
                    onChange={setBriefFilter}
                  />
                </FacetRow>
              </FiltersPanel>
            </div>

            <div className="flex shrink-0 items-center gap-2.5">
              <ReadinessLegend />
              <ToolbarDivider />
              {/* Philosophie « toutes les capacités partout » : même toolbar bleue que
                  Réservoir/Recherche. NOTE : ça monte une 2ᵉ instance de SourcesModal
                  (celle interne à KeywordsToolbar), en plus de celle gardée plus bas
                  pour la ligne « métriques » de l'Overview (KeywordOverviewModal.onImport) —
                  une seule est ouverte à la fois, donc c'est acceptable ; l'instance
                  locale n'est pas supprimée, l'Overview en dépend. */}
              {siteId ? (
                <KeywordsToolbar
                  siteId={siteId}
                  onImported={() => router.refresh()}
                  canImportGsc={canImportGsc}
                  analyticsEnabled={analyticsEnabled}
                  defaultLang={defaultLang}
                />
              ) : null}
              <SyncMenu
                canSyncGsc={false}
                serankingEnabled={Boolean(serankingEnabled && siteId)}
                mangoolsConnected={Boolean(mangoolsConnected && siteId)}
                selectedCount={selectedKeywordObjs.length}
                syncingGsc={false}
                syncingSeranking={serankingSyncing}
                syncingMangools={mangoolsSyncing}
                onSyncGsc={() => {}}
                onSyncSeranking={syncSeranking}
                onSyncMangools={syncMangools}
                lastGscSyncAt={syncStatus.lastGscSyncAt}
                lastSerankingSyncAt={syncStatus.lastSerankingSyncAt}
                lastMangoolsSyncAt={syncStatus.lastMangoolsSyncAt}
              />
            </div>
          </ToolbarRow>
        </div>

        {/* Table. Ancre du tutoriel : `data-tour-has-content` n'est posé QU'À
            PARTIR d'une ligne affichée — sur un Planning vide (ou entièrement
            masqué par les filtres) l'attribut est ABSENT, et non "false", donc
            le moteur reporte le tour au lieu de commenter un tableau vide. */}
        <div
          className="overflow-x-auto"
          data-tour="planning-table"
          data-tour-has-content={filtered.length > 0 ? "true" : undefined}
        >
          <table className="w-full text-sm">
            <thead>
              <tr className="border-b text-left text-muted-foreground text-xs">
                <th className="w-10 px-4 py-3">
                  <Checkbox
                    checked={allFilteredSelected}
                    onCheckedChange={(v) =>
                      setSel((s) => {
                        const next = { ...s };
                        for (const r of filtered)
                          next[r.keyword.id] = v === true;
                        return next;
                      })
                    }
                    aria-label="Tout sélectionner"
                  />
                </th>
                <th className="px-4 py-3 font-medium">Terme</th>
                <th className="px-4 py-3 text-center font-medium">Pays</th>
                <th className="px-4 py-3 text-center font-medium">Vol</th>
                <th className="px-4 py-3 text-center font-medium">KD</th>
                <th className="px-4 py-3 text-center font-medium">SERP</th>
                {/* Ancre du tutoriel sur le MILIEU du trio SERP / On-page /
                    Brief. driver.js découpe la boîte du SEUL élément visé et ne
                    s'étend jamais à ses voisins : le halo éclaire cet en-tête,
                    pas les trois colonnes. Un tableau HTML n'offre d'ailleurs
                    aucun élément qui enveloppe exactement ces trois cellules —
                    le `<tr>` en contiendrait onze. Le texte du point (clé
                    `Tour.planning.readiness`) est donc écrit pour ce qui est
                    RÉELLEMENT éclairé : il prend cette colonne pour sujet et
                    situe les deux autres à sa gauche et à sa droite. Déplacer
                    cette ancre oblige à réécrire ce texte, dans les deux
                    catalogues. */}
                <th
                  className="px-4 py-3 text-center font-medium"
                  data-tour="planning-readiness"
                >
                  On-page
                </th>
                <th className="px-4 py-3 text-center font-medium">Brief</th>
                <th className="px-4 py-3 font-medium">Sources</th>
                <th className="px-4 py-3 font-medium">Page ciblée</th>
                <th className="w-10 px-4 py-3" />
              </tr>
            </thead>
            <tbody>
              {filtered.length === 0 ? (
                <tr>
                  <td
                    colSpan={11}
                    className="px-4 py-8 text-center text-muted-foreground"
                  >
                    {rows.length === 0
                      ? "Aucun mot-clé planifié. Cible un pays en « Planifié » dans Recherche."
                      : "Aucun résultat pour ces filtres."}
                  </td>
                </tr>
              ) : (
                filtered.map((row, rowIndex) => {
                  const k = row.keyword;
                  const a = row.analysis;
                  const m = primaryMetrics(row);
                  const intent = k.intent[0]
                    ? INTENT_LABELS[k.intent[0]]
                    : null;
                  const serpInfo =
                    a.serp.state === "ok" && a.serp.count
                      ? `SERP top ${a.serp.count}`
                      : "SERP —";

                  return (
                    <tr
                      key={k.id}
                      className="cursor-pointer border-b last:border-0 hover:bg-muted/40"
                      onClick={() => openOverview(k.id)}
                      // Ancre du tutoriel sur la LIGNE — c'est elle qui ouvre
                      // le détail. Jamais sur le contenu de la modale : celle-ci
                      // pose `pointer-events: none` sur le body et son overlay
                      // entrerait en conflit avec celui de driver.js.
                      data-tour={
                        rowIndex === 0 ? "planning-dispatch" : undefined
                      }
                    >
                      {/* biome-ignore lint/a11y/useKeyWithClickEvents: stop row-click bubbling only */}
                      <td
                        className="px-4 py-3"
                        onClick={(e) => e.stopPropagation()}
                      >
                        <Checkbox
                          checked={!!sel[k.id]}
                          onCheckedChange={(v) =>
                            setSel((s) => ({ ...s, [k.id]: v === true }))
                          }
                          aria-label={`Sélectionner ${k.term}`}
                        />
                      </td>
                      <td className="px-4 py-3">
                        <div className="flex flex-col">
                          <span className="font-medium">{k.term}</span>
                          <span className="text-muted-foreground text-xs">
                            {[intent, serpInfo].filter(Boolean).join(" · ")}
                          </span>
                        </div>
                      </td>
                      <td className="px-4 py-3 text-center">
                        <Flag
                          code={k.locale.country}
                          title={k.locale.country}
                        />
                      </td>
                      <td className="px-4 py-3 text-center tabular-nums">
                        {formatVolume(m?.volume ?? null)}
                      </td>
                      <td className="px-4 py-3 text-center">
                        {m ? (
                          <span
                            className={cn(
                              "inline-flex min-w-8 items-center justify-center rounded-md px-2 py-0.5 font-semibold text-xs tabular-nums",
                              kdClasses(m.kd),
                            )}
                          >
                            {Math.round(m.kd)}
                          </span>
                        ) : (
                          <span className="text-muted-foreground">—</span>
                        )}
                      </td>
                      <td className="px-4 py-3 text-center">
                        <ReadinessDot
                          state={serpReady(a)}
                          tooltip={
                            a.serp.state === "ok"
                              ? `SERP importée (${a.serp.count})`
                              : "Aucune SERP importée"
                          }
                        />
                      </td>
                      <td className="px-4 py-3 text-center">
                        <ReadinessDot
                          state={onpageReady(a)}
                          tooltip={
                            a.onpage.state === "ok"
                              ? "On-page crawlé"
                              : a.onpage.state === "partial"
                                ? "Crawl partiel"
                                : "On-page non crawlé"
                          }
                        />
                      </td>
                      <td className="px-4 py-3 text-center">
                        <ReadinessDot
                          state={briefReady(a)}
                          tooltip={
                            a.brief.state === "ok"
                              ? "Brief complet"
                              : a.brief.state === "other-locale"
                                ? "Brief autre locale"
                                : "Aucun brief"
                          }
                        />
                      </td>
                      <td className="px-4 py-3">
                        <SourceDots keyword={k} />
                      </td>
                      {/* biome-ignore lint/a11y/useKeyWithClickEvents: stop row-click bubbling only */}
                      <td
                        className="px-4 py-3"
                        onClick={(e) => e.stopPropagation()}
                      >
                        {siteId ? (
                          <TargetPageCell
                            keyword={k}
                            siteId={siteId}
                            onChanged={() => router.refresh()}
                          />
                        ) : null}
                      </td>
                      <td className="px-4 py-3 text-right">
                        {siteId ? (
                          <Button
                            size="icon"
                            variant="ghost"
                            className="size-7 text-muted-foreground hover:text-destructive"
                            aria-label={`Retirer ${k.term} du planning`}
                            onClick={(e) => {
                              e.stopPropagation();
                              remove(k.id);
                            }}
                          >
                            <XIcon className="size-4" aria-hidden />
                          </Button>
                        ) : null}
                      </td>
                    </tr>
                  );
                })
              )}
            </tbody>
          </table>
        </div>
      </ToolbarPanel>

      {/* Barre de sélection flottante — reste montée (show anime seulement). */}
      <FloatingBulkBar show={selectedKeywordObjs.length > 0}>
        <span className="whitespace-nowrap font-medium text-sm">
          {selectedKeywordObjs.length} sélectionné(s)
        </span>
        <FloatingBulkBarSeparator />
        <Button
          size="sm"
          variant="outline"
          className="h-8"
          onClick={() => setPromoteOpen(true)}
        >
          → Contenu…
        </Button>
        {serankingEnabled && siteId ? (
          <Button
            size="sm"
            variant="outline"
            className="h-8 border-violet-500/40 text-violet-500 hover:bg-violet-500/10 hover:text-violet-500"
            disabled={serankingSyncing}
            onClick={syncSeranking}
          >
            <SparklesIcon className="size-3.5" aria-hidden />
            Enrichir
          </Button>
        ) : null}
        <Button
          size="sm"
          variant="ghost"
          className="h-8"
          onClick={() => setSel({})}
        >
          Annuler
        </Button>
      </FloatingBulkBar>

      <KeywordOverviewModal
        keywordId={overviewId}
        open={overviewOpen}
        onOpenChange={setOverviewOpen}
        onImportBrief={(id) => setBriefForId(id)}
        onImport={() => setSourcesOpen(true)}
        onDataChanged={() => router.refresh()}
        position={
          overviewIndex >= 0
            ? { index: overviewIndex, total: filtered.length }
            : undefined
        }
        onNavigate={navigateOverview}
      />

      <SourcesModal
        open={sourcesOpen}
        onOpenChange={setSourcesOpen}
        siteId={siteId}
        onImported={() => router.refresh()}
      />

      {siteId && briefForId ? (
        <ImportBriefDialog
          open={briefForId !== null}
          onOpenChange={(o) => {
            if (!o) setBriefForId(null);
          }}
          siteId={siteId}
          keywordId={briefForId}
          onImported={() => router.refresh()}
        />
      ) : null}

      {siteId ? (
        <PromoteToContentDialog
          siteId={siteId}
          keywords={selectedKeywordObjs}
          open={promoteOpen}
          onOpenChange={setPromoteOpen}
          onDone={() => {
            setSel({});
            router.refresh();
          }}
        />
      ) : null}
      {serankingSyncDialog}
    </div>
  );
}
