"use client"; import { IconX, IconDeviceFloppy, IconBookmark } from "@tabler/icons-react"; import type { Icon } from "@tabler/icons-react"; import { useCallback } from "react"; import { cn } from "@/lib/utils"; import { PR_PRESETS, ISSUE_PRESETS, type PresetOption, type PresetGroup } from "./search-bar"; import type { SavedPreset } from "./saved-preset-model"; import { useTranslation } from "react-i18next"; import { SavedQueryDefaultButton } from "@/components/integrations/saved-query-default-button"; export type SidebarSelection = { kind: "pr" | "issue"; source: "preset" | "saved"; id: string; }; export type SidebarSelectionRequest = | SidebarSelection | { kind: SidebarSelection["kind"]; source: "kind-switch" }; type PresetsSidebarProps = { selected: SidebarSelection; onSelect: (request: SidebarSelectionRequest) => void; savedPresets: SavedPreset[]; onDeleteSaved: (id: string) => void; canSaveCurrent: boolean; onSaveCurrent: () => void; onToggleSavedDefault: (preset: SavedPreset) => void; defaultMutationPendingId: string | null; prPresets?: PresetOption[]; issuePresets?: PresetOption[]; }; function KindToggle({ kind, onChange, }: { kind: "pr" | "issue"; onChange: (k: "pr" | "issue") => void; }) { const { t } = useTranslation(); return (
{(["pr", "issue"] as const).map((value) => ( ))}
); } function SectionHeader({ title }: { title: string }) { return (
{title}
); } function PresetItem({ label, Icon, active, onClick, trailing, }: { label: string; Icon: Icon; active: boolean; onClick: () => void; trailing?: React.ReactNode; }) { return (
{trailing}
); } function PresetGroupList({ presets, group, selected, onSelect, kind, }: { presets: PresetOption[]; group: PresetGroup; selected: SidebarSelection; onSelect: (s: SidebarSelection) => void; kind: "pr" | "issue"; }) { const { t } = useTranslation(); const items = presets.filter((p) => p.group === group); if (items.length === 0) return null; return ( <> {items.map((p) => ( onSelect({ kind, source: "preset", id: p.value })} /> ))} ); } function SavedSection({ saved, selected, onSelect, onDelete, kind, canSaveCurrent, onSaveCurrent, onToggleSavedDefault, defaultMutationPendingId, }: { saved: SavedPreset[]; selected: SidebarSelection; onSelect: (s: SidebarSelection) => void; onDelete: (id: string) => void; kind: "pr" | "issue"; canSaveCurrent: boolean; onSaveCurrent: () => void; onToggleSavedDefault: (preset: SavedPreset) => void; defaultMutationPendingId: string | null; }) { const { t } = useTranslation(); const defaultMutationPending = defaultMutationPendingId !== null; return ( <> {saved.length === 0 && (
{t("github:noSavedQueriesYet")}
)} {saved.map((s) => { const deleteLabel = t("integrations:deleteSavedQueryNamed", { label: s.label }); const accessibleDeleteLabel = defaultMutationPending ? t("integrations:savedQueryDefaultUpdateInProgress", { action: deleteLabel }) : deleteLabel; return ( onSelect({ kind, source: "saved", id: s.id })} trailing={
void onToggleSavedDefault(s)} />
} /> ); })} ); } export function PresetsSidebar({ selected, onSelect, savedPresets, onDeleteSaved, canSaveCurrent, onSaveCurrent, onToggleSavedDefault, defaultMutationPendingId, prPresets = PR_PRESETS, issuePresets = ISSUE_PRESETS, }: PresetsSidebarProps) { const presets = selected.kind === "pr" ? prPresets : issuePresets; const saved = savedPresets.filter((p) => p.kind === selected.kind); const onKindChange = useCallback( (kind: "pr" | "issue") => { if (kind === selected.kind) return; onSelect({ kind, source: "kind-switch" }); }, [onSelect, selected.kind], ); return ( ); }