Open ahkhanjani opened 1 year ago
Do you know if this "Type instantiation is excessively deep and possibly infinite" related to columnHelper has already been fixed?
https://github.com/TanStack/table/issues/4224#issuecomment-1423946421 https://github.com/TanStack/table/issues/4387 https://github.com/TanStack/table/issues/4241
Yes, I am trying to make this work... I've done everything, but I can't get the DataTable component columns prop to accept my columns generated by createColumnHelper.
Here's what I mean:
A you can see in the image, I can send columns
to the normal useReactTable hook, but not to the DataTable component columns prop....
I'm trying to make this work. Does anyone know the solution?
I kind of 'fixed it' by removing TValue generic in the any
for ColumnDef<TData, TValue>[];
instead of TValue
Do you know if this "Type instantiation is excessively deep and possibly infinite" related to columnHelper has already been fixed?
Hi. I didn't know that issue existed. I will look into it.
I kind of 'fixed it' by removing TValue generic in the component,a nd placing
any
forColumnDef<TData, TValue>[];
instead of TValue
I'm just ts-ignore'ing where I pass the columns prop for now.
Here's what I got. I'm new to typescript but I bashed my way through it by trying to understand the IDE errors and looking up expected values. Probably lots to improve here.
One trick is defining the object returned from columnHelper.accessor() as ColumnDef<Task>
.
Without this, it complains:
Type 'ColumnDef<{ id: string; title: string; status: string; label: string; priority: string; }, string>' is not assignable to type 'ColumnDef<{ id: string; title: string; status: string; label: string; priority: string; }>'.
Alternatively, you can declare the column array definition as ColumnDef<Task, string>
and remove as ColumnDef<Task>
from each column.
I couldn't figure out how to do this with just the exported constant, so I added a createColumns() function that the constant calls to get values. Is there a better way to do this?
function createColumns(): ColumnDef<Task>[] {
const columnHelper = createColumnHelper<Task>()
return [
columnHelper.display({
id: "select",
header: ({ table }) => (
<Checkbox
checked={table.getIsAllPageRowsSelected()}
onCheckedChange={(value) => table.toggleAllPageRowsSelected(!!value)}
aria-label="Select all"
className="translate-y-[2px]"
/>
),
cell: ({ row }) => (
<Checkbox
checked={row.getIsSelected()}
onCheckedChange={(value) => row.toggleSelected(!!value)}
aria-label="Select row"
className="translate-y-[2px]"
/>
),
enableSorting: false,
enableHiding: false,
}),
columnHelper.accessor('id', {
header: ({ column }) => (
<DataTableColumnHeader column={column} title="Task" />
),
cell: ({ row }) => <div className="w-[80px]">{row.getValue("id")}</div>,
enableSorting: false,
enableHiding: false,
}) as ColumnDef<Task>,
columnHelper.accessor('title', {
header: ({ column }) => (
<DataTableColumnHeader column={column} title="Title" />
),
cell: ({ row }) => {
const label = labels.find((label) => label.value === row.original.label)
return (
<div className="flex space-x-2">
{label && <Badge variant="outline">{label.label}</Badge>}
<span className="max-w-[500px] truncate font-medium">
{row.getValue("title")}
</span>
</div>
)
},
}) as ColumnDef<Task>,
columnHelper.accessor('priority', {
header: ({ column }) => (
<DataTableColumnHeader column={column} title="Status" />
),
cell: ({ row }) => {
const status = statuses.find(
(status) => status.value === row.getValue("status")
)
if (!status) {
return null
}
return (
<div className="flex w-[100px] items-center">
{status.icon && (
<status.icon className="mr-2 h-4 w-4 text-muted-foreground" />
)}
<span>{status.label}</span>
</div>
)
},
filterFn: (row, id, value) => {
return value.includes(row.getValue(id))
},
}) as ColumnDef<Task>,
columnHelper.accessor('status', {
header: ({ column }) => (
<DataTableColumnHeader column={column} title="Priority" />
),
cell: ({ row }) => {
const priority = priorities.find(
(priority) => priority.value === row.getValue("priority")
)
if (!priority) {
return null
}
return (
<div className="flex items-center">
{priority.icon && (
<priority.icon className="mr-2 h-4 w-4 text-muted-foreground" />
)}
<span>{priority.label}</span>
</div>
)
},
filterFn: (row, id, value) => {
return value.includes(row.getValue(id))
},
}) as ColumnDef<Task>,
columnHelper.display({
id: 'actions',
cell: ({ row }) => <DataTableRowActions row={row} />,
})
]
}
export const columns: ColumnDef<Task>[] = createColumns()
I kind of 'fixed it' by removing TValue generic in the component,a nd placing
any
forColumnDef<TData, TValue>[];
instead of TValue
This fixed the error.. Bit of a hack..
interface DataTableProps<TData> {
columns: any;
data: TData[];
}
I still don't get it, why don't the docs use column helper @shadcn ?
I still don't get it, why don't the docs use column helper @shadcn ?
agreed, using column helper for better type safety @shadcn, thanks for all your works..
This seems to work for me
const columnHelper = createColumnHelper<Contact>()
export const columns: ColumnDef<Contact>[] = [
columnHelper.accessor('firstName', {
header: 'First Name',
cell: (info) => info.getValue(),
}),
columnHelper.accessor('lastName', {
id: 'lastName',
header: 'Last Name',
cell: (info) => info.getValue(),
})
] as Array<ColumnDef<Contact, unknown>>
interface DataTableProps<TData, TValue> {
columns: ColumnDef<TData, TValue>[]
data: TData[]
}
This seems to work for me
const columnHelper = createColumnHelper<Contact>() export const columns: ColumnDef<Contact>[] = [ columnHelper.accessor('firstName', { header: 'First Name', cell: (info) => info.getValue(), }), columnHelper.accessor('lastName', { id: 'lastName', header: 'Last Name', cell: (info) => info.getValue(), }) ] as Array<ColumnDef<Contact, unknown>>
interface DataTableProps<TData, TValue> { columns: ColumnDef<TData, TValue>[] data: TData[] }
You actually just need the last part as Array<ColumnDef<Contact, unknown>>. Thanks for the solution.
createColumnHelper
function in my opinion makes the TypeScript experience much better. It would be great to have it in the docs. The current example works at run time but gives a type error