Description
In the useDataGrid hook, the onDataUpdate function sizes newData from rows.length (via table.getRowModel().rows), but when search or column filters are active, that row count is smaller than currentData.length. This causes data beyond the filtered slice to be silently dropped when onDataChange is called.
Steps to Reproduce
- Create a data grid with 50+ rows
- Enable search (
enableSearch: true)
- Search for a term that filters down to ~5 rows
- Edit a cell in one of the filtered rows
- Observe that
onDataChange receives an array of only 5 items instead of 50
Root Cause
In use-data-grid.ts, the onDataUpdate callback:
const tableRowCount = rows?.length ?? currentData.length;
const newData: TData[] = new Array(tableRowCount);
rows comes from table.getRowModel().rows which returns filtered/sorted rows. When filters are active, rows.length < currentData.length, so the new array is undersized. The loop then only iterates up to the filtered count, dropping all rows beyond that index.
Meanwhile, the rowUpdatesMap correctly maps updates to original data indices (via currentData.indexOf(originalData)), but those indices may exceed the truncated array size and are never visited.
Suggested Fix
Replace:
const tableRowCount = rows?.length ?? currentData.length;
With:
const tableRowCount = currentData.length;
This ensures the full dataset is always preserved, and updates are applied at their correct original indices regardless of active filters.
Environment
@diceui/data-grid installed via npx shadcn@3.8.4 add "@diceui/data-grid"
- Next.js 16, React 19
Description
In the
useDataGridhook, theonDataUpdatefunction sizesnewDatafromrows.length(viatable.getRowModel().rows), but when search or column filters are active, that row count is smaller thancurrentData.length. This causes data beyond the filtered slice to be silently dropped whenonDataChangeis called.Steps to Reproduce
enableSearch: true)onDataChangereceives an array of only 5 items instead of 50Root Cause
In
use-data-grid.ts, theonDataUpdatecallback:rowscomes fromtable.getRowModel().rowswhich returns filtered/sorted rows. When filters are active,rows.length < currentData.length, so the new array is undersized. The loop then only iterates up to the filtered count, dropping all rows beyond that index.Meanwhile, the
rowUpdatesMapcorrectly maps updates to original data indices (viacurrentData.indexOf(originalData)), but those indices may exceed the truncated array size and are never visited.Suggested Fix
Replace:
With:
This ensures the full dataset is always preserved, and updates are applied at their correct original indices regardless of active filters.
Environment
@diceui/data-gridinstalled vianpx shadcn@3.8.4 add "@diceui/data-grid"