'use client';

import { useMemo, useState } from 'react';
import Link from 'next/link';
import { Search, X } from 'lucide-react';
import type { LucideIcon } from 'lucide-react';

import { Card, CardContent, CardDescription, CardHeader, CardTitle } from '@/components/ui/card';
import { Input } from '@/components/ui/input';
import { Button } from '@/components/ui/button';
import { cn } from '@/lib/utils';

export interface AdminSection {
  href: string;
  label: string;
  description: string;
  icon: LucideIcon;
}

export interface AdminGroup {
  title: string;
  description: string;
  sections: AdminSection[];
}

interface AdminSectionsBrowserProps {
  portSlug: string;
  groups: AdminGroup[];
}

/**
 * Searchable index of admin settings cards. The unfiltered view renders the
 * grouped grid (Access / Configuration / Content / …); typing in the search
 * input collapses every section into a flat result list of matching cards.
 *
 * Match is substring against label + description + group title so a search
 * for "tax" finds Document Templates (description mentions tax-id mergefield)
 * as well as ID fields, without needing perfect spelling of the label.
 */
export function AdminSectionsBrowser({ portSlug, groups }: AdminSectionsBrowserProps) {
  const [query, setQuery] = useState('');
  const q = query.trim().toLowerCase();

  // Flatten + filter when there's an active query; otherwise let the grouped
  // view render. The grouped view is also memoised because the section count
  // is large (30+) and the JSX otherwise rebuilds on every keystroke.
  const filteredMatches = useMemo(() => {
    if (!q) return null;
    const matches: Array<AdminSection & { groupTitle: string }> = [];
    for (const g of groups) {
      for (const s of g.sections) {
        const hay = `${s.label} ${s.description} ${g.title}`.toLowerCase();
        if (hay.includes(q)) matches.push({ ...s, groupTitle: g.title });
      }
    }
    return matches;
  }, [q, groups]);

  return (
    <div className="space-y-6">
      <div className="relative max-w-md">
        <Search className="pointer-events-none absolute left-3 top-1/2 h-4 w-4 -translate-y-1/2 text-muted-foreground" />
        <Input
          type="search"
          inputMode="search"
          placeholder="Search settings…"
          aria-label="Search admin settings"
          value={query}
          onChange={(e) => setQuery(e.target.value)}
          className="h-9 pl-9 pr-9"
        />
        {query ? (
          <Button
            type="button"
            variant="ghost"
            size="icon"
            onClick={() => setQuery('')}
            className="absolute right-1 top-1 h-7 w-7"
            aria-label="Clear search"
          >
            <X className="h-3.5 w-3.5" />
          </Button>
        ) : null}
      </div>

      {filteredMatches ? (
        filteredMatches.length === 0 ? (
          <p className="rounded-md border border-dashed py-8 text-center text-sm text-muted-foreground">
            No settings match &quot;{query}&quot;.
          </p>
        ) : (
          <div className="space-y-3">
            <p className="text-xs uppercase tracking-wider text-muted-foreground">
              {filteredMatches.length} match{filteredMatches.length === 1 ? '' : 'es'}
            </p>
            <div className="grid grid-cols-1 gap-4 sm:grid-cols-2 lg:grid-cols-3">
              {filteredMatches.map((s) => (
                <SectionCard
                  key={`${s.href}-${s.groupTitle}`}
                  portSlug={portSlug}
                  section={s}
                  groupTitle={s.groupTitle}
                />
              ))}
            </div>
          </div>
        )
      ) : (
        groups.map((group) => (
          <section key={group.title} className="space-y-3">
            <div>
              <h2 className="text-xs font-semibold uppercase tracking-wider text-muted-foreground">
                {group.title}
              </h2>
              <p className="text-xs text-muted-foreground/80">{group.description}</p>
            </div>
            <div className="grid grid-cols-1 gap-4 sm:grid-cols-2 lg:grid-cols-3">
              {group.sections.map((s) => (
                <SectionCard key={s.href} portSlug={portSlug} section={s} />
              ))}
            </div>
          </section>
        ))
      )}
    </div>
  );
}

function SectionCard({
  portSlug,
  section,
  groupTitle,
}: {
  portSlug: string;
  section: AdminSection;
  /** Optional "from group X" tag for search-result mode. */
  groupTitle?: string;
}) {
  const Icon = section.icon;
  return (
    <Link
      // eslint-disable-next-line @typescript-eslint/no-explicit-any
      href={`/${portSlug}/admin/${section.href}` as any}
      className="block group"
    >
      <Card
        className={cn(
          'h-full transition-colors group-hover:border-primary/50 group-hover:bg-muted/30',
        )}
      >
        <CardHeader className="flex flex-row items-start gap-3 space-y-0 pb-2">
          <Icon className="h-5 w-5 mt-0.5 text-muted-foreground group-hover:text-primary" />
          <div className="flex-1">
            <CardTitle className="text-base">{section.label}</CardTitle>
            {groupTitle ? (
              <p className="text-[10px] uppercase tracking-wider text-muted-foreground">
                {groupTitle}
              </p>
            ) : null}
          </div>
        </CardHeader>
        <CardContent>
          <CardDescription>{section.description}</CardDescription>
        </CardContent>
      </Card>
    </Link>
  );
}
