100 lines
2.5 KiB
TypeScript

'use client';
import {
type ColumnDef,
flexRender,
getCoreRowModel,
useReactTable,
} from '@tanstack/react-table';
import { Loader } from 'lucide-react';
import { useTranslations } from 'next-intl';
import { Card } from '../common/Card';
import {
Table,
TableBody,
TableCell,
TableHead,
TableHeader,
TableRow,
} from '../common/Table';
type DataTableProps<TData, TValue> = {
columns: ColumnDef<TData, TValue>[];
data: TData[];
};
export const DataTable = <TData, TValue>({
columns,
data,
}: DataTableProps<TData, TValue>) => {
const t = useTranslations('components.dataTable');
const table = useReactTable({
data,
columns,
getCoreRowModel: getCoreRowModel(),
});
return (
<div className="rounded-lg border">
<Table>
<TableHeader>
{table.getHeaderGroups().map((headerGroup) => (
<TableRow key={headerGroup.id}>
{headerGroup.headers.map((header) => (
<TableHead key={header.id}>
{header.isPlaceholder
? null
: flexRender(
header.column.columnDef
.header,
header.getContext(),
)}
</TableHead>
))}
</TableRow>
))}
</TableHeader>
<TableBody>
{table.getRowModel().rows?.length
? table.getRowModel().rows.map((row) => (
<TableRow
key={row.id}
data-state={row.getIsSelected() && 'selected'}
>
{row.getVisibleCells().map((cell) => (
<TableCell key={cell.id}>
{flexRender(
cell.column.columnDef.cell,
cell.getContext(),
)}
</TableCell>
))}
</TableRow>
))
: (
<TableRow>
<TableCell
className="h-24 text-center"
colSpan={columns.length}
>
{t('notFound')}
</TableCell>
</TableRow>
)}
</TableBody>
</Table>
</div>
);
};
export const DataTableSkeleton = () => (
<div className="mx-auto mb-10 w-full max-w-(--breakpoint-2xl)">
<Card className="mt-6 flex h-[500px] w-full items-center justify-center">
<Loader className="size-8 animate-spin text-muted-foreground" />
</Card>
</div>
);