'use client';
import { ErrorState } from '@/components/ui/feedback/ErrorState';

import { useMemo } from 'react';
import { useUrlFilterState } from '@/lib/url/useUrlFilterState';
import { makeShareLinksCodec } from '@/lib/url/codecs/shareLinksCodec';
import { HISTORY } from '@/lib/url/historyPolicy';
import { useQuery, useQueryClient } from '@tanstack/react-query';
import { useT } from '@/lib/i18n/react';
import { getCsrfToken } from '@/lib/csrf';
import { Button } from '@/components/ui/primitives/Button';
import { Badge } from '@/components/ui/primitives/Badge/Badge';
import { Table } from '@/components/ui/primitives/Table/Table';
import { TableSkeleton } from '@/components/ui/feedback/Skeleton';
import { QueryBoundary } from '@platform-modules/ui-primitives';
import { createOptimisticMutation } from '@/lib/query/optimistic';

type LinkRow = {
  id: string;
  slug: string;
  shortUrl: string;
  channel: string;
  dealTitle: string | null;
  isActive: boolean;
  createdAt: string;
  stats: { clicks: number };
};

async function fetchLinks(params: { limit: number; offset: number }) {
  const url = new URL('/api/admin/share/links', window.location.origin);
  url.searchParams.set('limit', String(params.limit));
  url.searchParams.set('offset', String(params.offset));
  const res = await fetch(url.toString());
  if (!res.ok) throw new Error('fetch failed');
  const json = (await res.json()) as { data: { links: LinkRow[]; total: number } };
  return json.data;
}

async function patchLink(id: string, patch: { isActive?: boolean }) {
  const res = await fetch(`/api/admin/share/links/${id}`, {
    method: 'PATCH',
    headers: { 'Content-Type': 'application/json', 'x-csrf-token': getCsrfToken() },
    body: JSON.stringify(patch),
  });
  if (!res.ok) throw new Error('patch failed');
}

export function ShareLinksTable() {
  const t = useT('admin_sharing');
  const tCommon = useT('common');
  const qc = useQueryClient();
  const codec = useMemo(() => makeShareLinksCodec('/admin/sharing'), []);
  const { state: urlState, setUrlState } = useUrlFilterState({
    initial: { page: 0 },
    codec,
  });
  const page = urlState.page;
  const PAGE_SIZE = 25;

  const linksQuery = useQuery({
    queryKey: ['admin', 'share', 'links', page],
    queryFn: () => fetchLinks({ limit: PAGE_SIZE, offset: page * PAGE_SIZE }),
  });

  const useToggleLink = createOptimisticMutation<
    void,
    { id: string; isActive: boolean },
    { links: LinkRow[]; total: number }
  >({
    mutationFn: ({ id, isActive }) => patchLink(id, { isActive }),
    queryKey: ['admin', 'share', 'links', page],
    optimisticUpdate: (prev, vars) => ({
      links: (prev?.links ?? []).map((link) =>
        link.id === vars.id ? { ...link, isActive: vars.isActive } : link,
      ),
      total: prev?.total ?? 0,
    }),
    afterSuccess: () => void qc.invalidateQueries({ queryKey: ['admin', 'share', 'links'] }),
    broadcast: true,
  });
  const toggleMutation = useToggleLink();

  return (
    <QueryBoundary
      query={linksQuery}
      skeleton={<TableSkeleton rows={5} cols={6} />}
      errorFallback={(retry) => (
        <ErrorState
          title={tCommon('error_loading')}
          action={
            <Button variant="secondary" size="sm" onClick={() => retry()}>
              {tCommon('retry')}
            </Button>
          }
        />
      )}
    >
      {(data) => (
        <div className="space-y-2">
          <Table>
            <Table.Head>
              <Table.Row>
                <Table.HeadCell>{t('col_slug')}</Table.HeadCell>
                <Table.HeadCell>{t('col_channel')}</Table.HeadCell>
                <Table.HeadCell>{t('col_deal')}</Table.HeadCell>
                <Table.HeadCell>{t('clicks_col')}</Table.HeadCell>
                <Table.HeadCell>{t('col_status')}</Table.HeadCell>
                <Table.HeadCell>{t('col_actions')}</Table.HeadCell>
              </Table.Row>
            </Table.Head>
            <Table.Body>
              {data.links.length === 0 ? (
                <Table.Row>
                  <Table.Cell colSpan={6} className="text-text-muted p-4 text-center">
                    {t('links_empty')}
                  </Table.Cell>
                </Table.Row>
              ) : (
                data.links.map((link) => (
                  <Table.Row key={link.id}>
                    <Table.Cell className="font-mono text-xs">{link.slug}</Table.Cell>
                    <Table.Cell>{t(`channel_${link.channel}` as never)}</Table.Cell>
                    <Table.Cell className="max-w-48 truncate">{link.dealTitle ?? '—'}</Table.Cell>
                    <Table.Cell className="tabular-nums">{link.stats.clicks}</Table.Cell>
                    <Table.Cell>
                      <Badge tone={link.isActive ? 'success' : 'neutral'}>
                        {link.isActive ? t('link_active') : t('link_inactive')}
                      </Badge>
                    </Table.Cell>
                    <Table.Cell>
                      <Button
                        size="sm"
                        variant="ghost"
                        onClick={() =>
                          toggleMutation.mutate({ id: link.id, isActive: !link.isActive })
                        }
                        disabled={toggleMutation.isPending}
                      >
                        {link.isActive ? t('deactivate') : t('activate')}
                      </Button>
                    </Table.Cell>
                  </Table.Row>
                ))
              )}
            </Table.Body>
          </Table>
          <div className="flex justify-end gap-2 pt-2">
            <Button
              size="sm"
              variant="secondary"
              onClick={() => setUrlState({ page: Math.max(0, page - 1) }, HISTORY.nav)}
              disabled={page === 0}
            >
              {t('pagination_prev')}
            </Button>
            <Button
              size="sm"
              variant="secondary"
              onClick={() => setUrlState({ page: page + 1 }, HISTORY.nav)}
              disabled={(page + 1) * PAGE_SIZE >= data.total}
            >
              {t('pagination_next')}
            </Button>
          </div>
        </div>
      )}
    </QueryBoundary>
  );
}
