import type { Metadata } from 'next';
import Link from 'next/link';
import { getDb, isUuid } from '@pintrush/db';
import { ConfirmActionButton } from '@/components/host/client';
import { formatBusinessDate, formatDateTime, formatNumber } from '@/components/host/format';
import { EmptyState, linkStyles, Notice, PageHeader, Panel, StatusBadge, TableWrap, td, th } from '@/components/host/ui';
import { requireAdmin } from '@/lib/auth/session';
import { ADMIN_TZ } from '../../_lib/constants';
import { adminResetTvLink } from '../venues/actions';

export const metadata: Metadata = { title: 'Support' };

const AUDIT_LIMIT = 200;
const PAYLOAD_PREVIEW = 4000;

function one(v: string | string[] | undefined): string {
  return (Array.isArray(v) ? v[0] : v)?.trim() ?? '';
}

export default async function AdminSupportPage({ searchParams }: { searchParams: Promise<Record<string, string | string[] | undefined>> }) {
  await requireAdmin('/admin/support');
  const sp = await searchParams;
  const q = one(sp.q).slice(0, 80);
  const venueId = one(sp.venue);
  const sessionId = one(sp.session);
  const db = getDb();

  const [venueHits, eventHits] = q
    ? await Promise.all([
        db.venue.findMany({
          where: {
            OR: [
              { name: { contains: q, mode: 'insensitive' } },
              { slug: { contains: q, mode: 'insensitive' } },
              { joinCode: { contains: q.toUpperCase() } },
              ...(isUuid(q) ? [{ id: q }] : []),
            ],
          },
          select: { id: true, name: true, joinCode: true, status: true },
          take: 20,
        }),
        db.event.findMany({
          where: { OR: [{ name: { contains: q, mode: 'insensitive' } }, ...(isUuid(q) ? [{ id: q }] : [])] },
          select: { id: true, name: true, kind: true, status: true, venueId: true, venue: { select: { name: true } }, gameSession: { select: { id: true } } },
          orderBy: { createdAt: 'desc' },
          take: 20,
        }),
      ])
    : [[], []];

  const venue = isUuid(venueId)
    ? await db.venue.findUnique({
        where: { id: venueId },
        select: {
          id: true,
          name: true,
          timezone: true,
          rooms: { orderBy: { createdAt: 'asc' }, select: { id: true, name: true, tvTokenVersion: true, status: true } },
          events: {
            orderBy: { createdAt: 'desc' },
            take: 25,
            select: { id: true, name: true, kind: true, status: true, businessDate: true, scheduledAt: true, gameSession: { select: { id: true, status: true } } },
          },
        },
      })
    : null;

  const session = isUuid(sessionId)
    ? await db.gameSession.findUnique({
        where: { id: sessionId },
        select: { id: true, status: true, seq: true, venueId: true, event: { select: { id: true, name: true, kind: true } }, room: { select: { name: true, venue: { select: { name: true } } } } },
      })
    : null;
  const audit = session
    ? (await db.auditEvent.findMany({ where: { gameSessionId: session.id }, orderBy: { ordinal: 'desc' }, take: AUDIT_LIMIT })).reverse()
    : [];
  const auditTotal = session ? await db.auditEvent.count({ where: { gameSessionId: session.id } }) : 0;

  return (
    <div className="flex flex-col gap-8">
      <PageHeader title="Support" description="Find a venue or event, check a session’s audit log, regenerate TV links." />
      <Panel>
        <form method="get" className="flex flex-wrap items-end gap-3">
          <label className="flex min-w-64 flex-1 flex-col gap-2 text-sm font-semibold">
            Venue name, join code, event name or id
            <input
              name="q"
              type="search"
              defaultValue={q}
              maxLength={80}
              className="min-h-12 rounded-xl border border-line-strong bg-night/70 px-4 text-base font-normal text-fg focus-visible:border-cyan"
            />
          </label>
          <button type="submit" className="min-h-12 rounded-xl bg-violet-strong px-6 font-semibold text-white hover:bg-violet-deep">
            Search
          </button>
        </form>
      </Panel>

      {q && (
        <div className="grid gap-8 lg:grid-cols-2">
          <Panel title={`Venues (${venueHits.length})`}>
            {venueHits.length === 0 ? (
              <p className="text-sm text-muted">No venues match “{q}”.</p>
            ) : (
              <ul className="divide-y divide-line/60">
                {venueHits.map((v) => (
                  <li key={v.id} className="flex flex-wrap items-center justify-between gap-3 py-3 first:pt-0 last:pb-0">
                    <span>
                      <Link href={`/admin/support?venue=${v.id}`} className={linkStyles}>
                        {v.name}
                      </Link>
                      <span className="ml-2 text-sm text-subtle">{v.joinCode}</span>
                    </span>
                    <StatusBadge status={v.status} />
                  </li>
                ))}
              </ul>
            )}
          </Panel>
          <Panel title={`Events (${eventHits.length})`}>
            {eventHits.length === 0 ? (
              <p className="text-sm text-muted">No events match “{q}”.</p>
            ) : (
              <ul className="divide-y divide-line/60">
                {eventHits.map((e) => (
                  <li key={e.id} className="flex flex-wrap items-center justify-between gap-3 py-3 first:pt-0 last:pb-0">
                    <span className="min-w-0">
                      <span className="font-semibold">{e.name}</span>
                      <span className="block text-sm text-subtle">
                        {e.venue.name} · {e.kind === 'CHAMPIONSHIP' ? 'Championship' : 'Always-on'}
                      </span>
                    </span>
                    <span className="flex items-center gap-3">
                      <StatusBadge status={e.status} />
                      {e.gameSession && (
                        <Link href={`/admin/support?session=${e.gameSession.id}`} className={linkStyles}>
                          Audit log
                        </Link>
                      )}
                      <Link href={`/admin/venues/${e.venueId}/events/${e.id}`} className={linkStyles}>
                        Control
                      </Link>
                    </span>
                  </li>
                ))}
              </ul>
            )}
          </Panel>
        </div>
      )}

      {venue && (
        <Panel title={`${venue.name}: rooms & sessions`} actions={<Link href={`/admin/venues/${venue.id}`} className={`${linkStyles} text-sm`}>Venue page</Link>}>
          <div className="flex flex-col gap-6">
            <ul className="flex flex-col gap-3">
              {venue.rooms.map((r) => (
                <li key={r.id} className="flex flex-wrap items-center justify-between gap-3 rounded-xl border border-line/70 p-3">
                  <span>
                    <span className="font-semibold">{r.name}</span>
                    <span className="ml-2 text-sm text-subtle">TV link version {r.tvTokenVersion}</span>
                  </span>
                  <ConfirmActionButton
                    action={adminResetTvLink}
                    fields={{ venueId: venue.id, roomId: r.id }}
                    label="Regenerate TV link"
                    title={`Regenerate the TV link for ${r.name}?`}
                    description="TVs using the old link are signed out when they next reconnect. The venue opens the new link from its dashboard."
                    confirmLabel="Regenerate"
                  />
                </li>
              ))}
            </ul>
            <ul className="divide-y divide-line/60">
              {venue.events.map((e) => (
                <li key={e.id} className="flex flex-wrap items-center justify-between gap-3 py-3">
                  <span className="min-w-0">
                    <span className="font-semibold">{e.name}</span>
                    <span className="block text-sm text-subtle">
                      {e.kind === 'ALWAYS_ON' && e.businessDate ? formatBusinessDate(e.businessDate) : formatDateTime(e.scheduledAt, venue.timezone)}
                    </span>
                  </span>
                  <span className="flex items-center gap-3">
                    <StatusBadge status={e.status} />
                    {e.gameSession ? (
                      <Link href={`/admin/support?session=${e.gameSession.id}`} className={linkStyles}>
                        Audit log
                      </Link>
                    ) : (
                      <span className="text-sm text-subtle">never opened</span>
                    )}
                  </span>
                </li>
              ))}
            </ul>
          </div>
        </Panel>
      )}

      {sessionId && !session && <Notice tone="warning">No game session with id {sessionId}.</Notice>}
      {session && (
        <Panel
          title={`Audit log · ${session.event.name}`}
          description={`${session.room.venue.name} · ${session.room.name} · session ${session.status.toLowerCase()} · seq ${session.seq} · showing the last ${Math.min(AUDIT_LIMIT, auditTotal)} of ${formatNumber(auditTotal)} entries, oldest first`}
          actions={
            <Link href={`/admin/venues/${session.venueId}/events/${session.event.id}`} className={`${linkStyles} text-sm`}>
              Control
            </Link>
          }
          padded={audit.length === 0}
        >
          {audit.length === 0 ? (
            <EmptyState title="No audit entries yet" />
          ) : (
            <div className="px-5 sm:px-6">
              <TableWrap label="Audit log">
                <thead>
                  <tr>
                    <th scope="col" className={th}>
                      #
                    </th>
                    <th scope="col" className={th}>
                      Time
                    </th>
                    <th scope="col" className={th}>
                      Actor
                    </th>
                    <th scope="col" className={th}>
                      Type
                    </th>
                    <th scope="col" className={th}>
                      Payload
                    </th>
                  </tr>
                </thead>
                <tbody>
                  {audit.map((a) => {
                    const json = JSON.stringify(a.payload, null, 2);
                    return (
                      <tr key={a.id}>
                        <td className={`${td} num align-top text-subtle`}>{a.ordinal.toString()}</td>
                        <td className={`${td} align-top whitespace-nowrap text-muted`}>
                          {formatDateTime(a.createdAt, ADMIN_TZ)}
                          {a.seq !== null && <span className="block text-xs text-subtle">seq {a.seq}</span>}
                        </td>
                        <td className={`${td} align-top`}>
                          {a.actorType.toLowerCase()}
                          {a.actorId && <span className="block max-w-40 truncate text-xs text-subtle">{a.actorId}</span>}
                        </td>
                        <td className={`${td} align-top font-mono text-xs`}>{a.type}</td>
                        <td className={`${td} align-top`}>
                          <details>
                            <summary className="inline-flex min-h-11 items-center text-xs font-semibold text-violet-soft">{json.length > 2 ? `${json.length} chars` : 'empty'}</summary>
                            <pre className="mt-2 max-h-80 max-w-xl overflow-auto rounded-lg bg-night p-3 text-xs text-muted">
                              {json.length > PAYLOAD_PREVIEW ? `${json.slice(0, PAYLOAD_PREVIEW)}\n… (truncated)` : json}
                            </pre>
                          </details>
                        </td>
                      </tr>
                    );
                  })}
                </tbody>
              </TableWrap>
            </div>
          )}
        </Panel>
      )}
    </div>
  );
}
