/** * Component: BlocklistTable * Documentation: documentation/admin-features/release-blocklist.md * * Desktop = sortable table, mobile = stacked cards. Sortable columns clickable * with explicit affordance (cursor + sort icon) — per zach.md UX rule on * intentional affordances. */ 'use client'; import { useBlocklistUrlState } from '../hooks/useBlocklistUrlState'; import { BlockedReleaseRow, SortField } from '../types'; import { BlocklistRow } from './BlocklistRow'; interface BlocklistTableProps { entries: BlockedReleaseRow[]; onUnblocked: (id: string) => void; onUnblockFailed: (entry: BlockedReleaseRow, error: string) => void; } interface SortableHeaderProps { field: SortField; label: string; className?: string; } function SortableHeader({ field, label, className = '' }: SortableHeaderProps) { const { filters, setFilters } = useBlocklistUrlState(); const isActive = filters.sortBy === field; const order = filters.sortOrder; const handleClick = () => { if (isActive) { setFilters({ sortOrder: order === 'asc' ? 'desc' : 'asc' }); } else { setFilters({ sortBy: field, sortOrder: 'desc' }); } }; return (
| Source | Associated request | Indexer | Actions |
|---|