import { useMemo, useState, type ReactElement } from "react"; import type { SchemaTable } from "../api/types"; import { Dialog, DialogContent, DialogTitle } from "../components/ui/dialog"; export function SchemaColumnsDialog({ table, open, readOnly, selected, onToggle, onClose, }: { table: SchemaTable; open: boolean; readOnly: boolean; selected: Set; onToggle: (column: string) => void; onClose: () => void; }): ReactElement { const [query, setQuery] = useState(""); // Suggested-first, then catalog order. Sorting on the descriptor's `suggested` // flag (not the live selection) keeps the list stable: toggling a checkbox never // reorders rows. For excluded tables (all suggested=false) this leaves catalog order. const ordered = useMemo( () => table.columns .map((c, i) => ({ c, i })) .sort((a, b) => Number(!!b.c.suggested) - Number(!!a.c.suggested) || a.i - b.i) .map((x) => x.c), [table.columns], ); const q = query.trim().toLowerCase(); const displayed = q ? ordered.filter( (c) => c.name.toLowerCase().includes(q) || (c.description ?? "").toLowerCase().includes(q), ) : ordered; return ( { if (!o) onClose(); }}> {table.name}
setQuery(e.target.value)} aria-label="Filter columns" placeholder="Filter columns…" className="min-w-0 flex-1 rounded-md border border-input bg-card px-2.5 py-1.5 text-sm shadow-xs outline-none transition-[border-color,box-shadow] focus:border-primary/50 focus:ring-2 focus:ring-ring/20" /> {displayed.length}/{table.columns.length}
    {displayed.map((col) => { const on = selected.has(col.name); const strong = on && !readOnly; return (
  • {!readOnly && ( onToggle(col.name)} aria-label={col.name} /> )}
    {col.name}
    {col.description ? (

    {col.description}

    ) : null}
  • ); })} {displayed.length === 0 && (
  • No columns match the filter.
  • )}
); }