import { Users, XCircle } from 'lucide-react';

import { useState } from 'react';

import { Head, Link, router, usePage } from '@inertiajs/react';

import { AdminDataTable } from '@/Components/admin/AdminDataTable';
import { AdminStatsGrid, type StatCard } from '@/Components/admin/AdminStatsGrid';
import { SortHeader } from '@/Components/admin/SortHeader';
import PageHeader from '@/Components/layout/PageHeader';
import { Alert, AlertDescription, AlertTitle } from '@/Components/ui/alert';
import {
  Breadcrumb,
  BreadcrumbItem,
  BreadcrumbLink,
  BreadcrumbList,
  BreadcrumbPage,
  BreadcrumbSeparator,
} from '@/Components/ui/breadcrumb';
import { Button } from '@/Components/ui/button';
import { ConfirmDialog } from '@/Components/ui/confirm-dialog';
import { ExportButton } from '@/Components/ui/export-button';
import { Input } from '@/Components/ui/input';
import {
  Table,
  TableBody,
  TableCell,
  TableHead,
  TableHeader,
  TableRow,
} from '@/Components/ui/table';
import { useAdminFilters } from '@/hooks/useAdminFilters';
import { useAdminKeyboardShortcuts } from '@/hooks/useAdminKeyboardShortcuts';
import { useNavigationState } from '@/hooks/useNavigationState';
import AdminLayout from '@/Layouts/AdminLayout';
import { formatRelativeTime } from '@/lib/format';
import type { PageProps, PaginatedResponse } from '@/types';

interface SessionRow {
  session_id: string;
  user_id: number;
  user_name: string;
  user_email: string;
  ip_address: string | null;
  last_activity: string;
}

interface Props {
  stats: {
    driver: string;
    total: number;
    active_users: number;
  };
  sessions: PaginatedResponse<SessionRow> | null;
  filters: {
    search: string;
    sort: string;
    dir: string;
  };
}

export default function SessionsIndex({ stats, sessions, filters }: Props) {
  const { auth } = usePage<PageProps>().props;
  const canMutate = auth.user?.admin_role != null && auth.user.admin_role !== 'viewer';
  const [invalidateId, setInvalidateId] = useState<string | null>(null);
  const { search, setSearch, handleSort, handlePage } = useAdminFilters({
    route: '/admin/sessions',
    filters,
  });
  const isNavigating = useNavigationState();

  const isDatabase = stats.driver === 'database';

  useAdminKeyboardShortcuts({
    onSearch: () => {
      document.querySelector<HTMLInputElement>('[data-search-input]')?.focus();
    },
    onNextPage:
      sessions && sessions.current_page < sessions.last_page
        ? () => handlePage(sessions.current_page + 1)
        : undefined,
    onPrevPage:
      sessions && sessions.current_page > 1
        ? () => handlePage(sessions.current_page - 1)
        : undefined,
  });

  const statCards: StatCard[] = [
    { title: 'Total Sessions', value: stats.total, icon: Users },
    { title: 'Active Users', value: stats.active_users, icon: Users },
  ];

  return (
    <AdminLayout>
      <Head title="Session Manager" />
      <div className="container py-6 space-y-6">
        <Breadcrumb>
          <BreadcrumbList>
            <BreadcrumbItem>
              <BreadcrumbLink asChild>
                <Link href="/admin">Admin</Link>
              </BreadcrumbLink>
            </BreadcrumbItem>
            <BreadcrumbSeparator />
            <BreadcrumbItem>
              <BreadcrumbPage>Sessions</BreadcrumbPage>
            </BreadcrumbItem>
          </BreadcrumbList>
        </Breadcrumb>
        <PageHeader title="Session Manager" description={`Session driver: ${stats.driver}`} />

        {!isDatabase && (
          <Alert>
            <AlertTitle>Database driver required</AlertTitle>
            <AlertDescription>
              Session manager requires <code>SESSION_DRIVER=database</code>. Current driver:{' '}
              <strong>{stats.driver}</strong>. Session listing and invalidation are unavailable.
            </AlertDescription>
          </Alert>
        )}

        {isDatabase && sessions && (
          <>
            <AdminStatsGrid stats={statCards} />

            <div className="flex gap-2">
              <Input
                data-search-input
                placeholder="Search by name, email, or IP…"
                value={search}
                onChange={(e) => setSearch(e.target.value)}
                className="w-72"
              />
              <ExportButton
                href={route('admin.sessions.export')}
                params={filters.search ? { search: filters.search } : {}}
              />
            </div>

            <AdminDataTable
              isEmpty={sessions.data.length === 0}
              isNavigating={isNavigating}
              pagination={sessions}
              onPage={handlePage}
              paginationLabel="sessions"
              emptyIcon={Users}
              emptyTitle="No sessions found"
              emptyDescription="No authenticated user sessions match your search."
            >
              <Table>
                <TableHeader>
                  <TableRow>
                    <SortHeader
                      column="name"
                      label="User"
                      currentSort={filters.sort}
                      currentDir={filters.dir}
                      onSort={handleSort}
                    />
                    <SortHeader
                      column="email"
                      label="Email"
                      currentSort={filters.sort}
                      currentDir={filters.dir}
                      onSort={handleSort}
                    />
                    <SortHeader
                      column="ip_address"
                      label="IP Address"
                      currentSort={filters.sort}
                      currentDir={filters.dir}
                      onSort={handleSort}
                    />
                    <SortHeader
                      column="last_activity"
                      label="Last Activity"
                      currentSort={filters.sort}
                      currentDir={filters.dir}
                      onSort={handleSort}
                    />
                    <TableHead className="w-20" />
                  </TableRow>
                </TableHeader>
                <TableBody>
                  {sessions.data.map((session) => (
                    <TableRow key={session.session_id}>
                      <TableCell>
                        <Link
                          href={route('admin.users.show', session.user_id)}
                          className="text-sm font-medium hover:underline"
                        >
                          {session.user_name}
                        </Link>
                      </TableCell>
                      <TableCell className="text-sm text-muted-foreground">
                        {session.user_email}
                      </TableCell>
                      <TableCell className="text-sm font-mono text-muted-foreground">
                        {session.ip_address ?? '—'}
                      </TableCell>
                      <TableCell className="text-sm text-muted-foreground">
                        {formatRelativeTime(session.last_activity)}
                      </TableCell>
                      <TableCell>
                        {canMutate && (
                          <Button
                            size="sm"
                            variant="ghost"
                            className="text-destructive hover:text-destructive"
                            onClick={() => setInvalidateId(session.session_id)}
                          >
                            <XCircle className="h-3.5 w-3.5" />
                          </Button>
                        )}
                      </TableCell>
                    </TableRow>
                  ))}
                </TableBody>
              </Table>
            </AdminDataTable>
          </>
        )}
      </div>

      <ConfirmDialog
        open={invalidateId !== null}
        onOpenChange={() => setInvalidateId(null)}
        title="Invalidate session?"
        description="This will log the user out immediately. They will need to log in again."
        confirmLabel="Invalidate"
        variant="destructive"
        onConfirm={() => {
          if (invalidateId) {
            router.delete(route('admin.sessions.destroy', invalidateId));
            setInvalidateId(null);
          }
        }}
      />
    </AdminLayout>
  );
}
