chs-real-data-grid
v0.0.7
Published
A lightweight, customizable React data grid with MUI integration, fast virtualization, sorting, filtering, pagination, selection, and XLSX/PDF export.
Readme
chs-real-data-grid
A customizable React Data Grid built with Material UI. Designed for real-world apps with controlled state, async workflows, and TypeScript. Supports sorting, filtering, pagination, row selection, column search, and export helpers (XLSX/PDF).
Features
- Sorting: global and per-column sorting.
- Filtering: column and global filtering with enum and range filters.
- Pagination: client-side and server-side support.
- Row Selection: select/deselect rows and bulk delete.
- Column Search: per-column search toggles.
- Export Helpers: Excel (XLSX) and PDF export helpers.
- Material UI theming and responsive layout using
Box,Typography. - TypeScript types for data and grid configuration.
- Server-side pagination and actions supported.
Installation
Install peer dependencies and the grid package. Material UI packages are peer dependencies — ensure compatible versions are installed.
npm install chs-real-data-gridMinimal usage
import DataTable from "chs-real-data-grid";
<DataTable data={myRows} gridMaster={myGridMaster} />data: array of rows (objects).gridMaster: configuration object (GridMaster) with columns, flags, andcallBacks(handlers).- Optional:
childrencan be used as a fallback forgridMaster. - Optional:
onStatusMessageChange— callback to receive status messages.
Quick Start
- Define your data types (e.g.
Customer). - Create a
GridMasterconfiguration (columns, paging, flags, callbacks). You can reuse the providedcustomerGriddefault object. - Render
DataTableinside a Material UI container and passdata+gridMasterprops.
Usage example
import React, { useEffect, useState } from "react";
import { Box } from "@mui/material";
import DataTable from "chs-real-data-grid";
import { Customer } from "./models/customer";
import { GridMaster } from "./models/gridMaster";
import { dumpData, validateInput } from "./data/validateInput";
import { customerGrid as customerGridDefault } from "./screens/data/data";
const Customers: React.FC = () => {
const [customData, setCustomData] = useState<Customer[]>(dumpData);
const [customerGrid, setCustomerGrid] = useState<GridMaster>({
...validateInput,
...customerGridDefault,
callBacks: {
onSelect: (row) => console.log("Selected:", row),
onDelete: (row) => console.log("Deleted:", row),
onRowView: (row) => console.log("View:", row),
onRowEdit: (row) => console.log("Edit:", row),
onRowDelete: (row) => console.log("Delete Cell:", row),
onSearch: (query) => console.log("Search:", query),
onSort: (sort) => console.log("Sort:", sort),
onColumnSearch: (col) => console.log("Column Search:", col),
onFilter: (filter) => console.log("Filter:", filter),
onClearSort: () => console.log("Clear Sort"),
onClearFilter: () => console.log("Clear Filter"),
onClearAll: () => console.log("Clear All"),
onColumnSort: (col) => console.log("Column Sort:", col),
onDownload: (format) => console.log("Download:", format),
onPagination: (page) => console.log("Pagination:", page),
},
});
useEffect(() => {
// fetch initial data if needed
setCustomData(dumpData);
}, []);
return (
<Box sx={{ width: "100%", p: 2 }}>
<DataTable data={customData} gridMaster={customerGrid} />
</Box>
);
};
export default Customers;Default customerGrid (example)
import { DataType } from "../models/dataType";
import { GridMaster } from "../models/gridMaster";
import { PageState } from "../models/pageState";
export const customerGrid: GridMaster = {
id: 1,
targetObject: "customer",
title: "Customer List",
filterReqd: true,
searchReqd: true,
sortReqd: true,
paginationReqd: true,
primaryColour: "#1E90FF",
secondaryColour: "#F0F8FF",
actionReqd: true,
actionCheckboxReqd: true,
actionEditReqd: true,
actionViewReqd: true,
actionDeleteReqd: true,
actionAddReqd: true,
indexReqd: true,
dynamicLoad: true,
recordsPerPage: 10,
actionKey: "firstName",
sortActionKey: "code",
gridPagination: {
reqd: true,
pageCount: 10,
recordPerPage: [5, 10, 25, 50],
dynamicLoad: true,
},
gridColumns: [
{ id: 2, code: "firstName", title: "First Name", sortable: true, searchReqd: true, filterable: true, displayable: true, formElementType: "text", type: DataType.STRING },
{ id: 3, code: "middleName", title: "Middle Name", sortable: false, searchReqd: false, filterable: false, displayable: true, formElementType: "image", type: DataType.STRING },
{ id: 4, code: "lastName", title: "Last Name", sortable: true, searchReqd: true, filterable: false, displayable: true, formElementType: "text", type: DataType.STRING },
{ id: 5, code: "username", title: "Username", sortable: true, searchReqd: true, filterable: false, displayable: true, formElementType: "text", type: DataType.STRING },
{ id: 6, code: "gender", title: "Gender", sortable: false, searchReqd: false, filterable: true, displayable: true, enumValues: ["MALE", "FEMALE"], formElementType: "radio", type: DataType.STRING },
{ id: 7, code: "dob", title: "Date of Birth", sortable: false, searchReqd: false, filterable: false, displayable: true, formElementType: "range", type: DataType.INTEGER },
{ id: 8, code: "anniversary", title: "Anniversary", sortable: false, searchReqd: false, filterable: false, displayable: false, formElementType: "text", type: DataType.INTEGER },
{ id: 9, code: "mobileNumber", title: "Mobile Number", sortable: false, searchReqd: true, filterable: false, displayable: true, formElementType: "phone", type: DataType.STRING },
{ id: 10, code: "emailId", title: "Email ID", sortable: false, searchReqd: true, filterable: false, displayable: true, formElementType: "email", type: DataType.STRING },
{ id: 11, code: "referredBy", title: "Referred By", sortable: true, searchReqd: false, filterable: false, displayable: false, formElementType: "text", type: DataType.LONG },
{ id: 12, code: "prefLang", title: "Preferred Lang.", sortable: false, searchReqd: true, filterable: true, displayable: true, enumValues: ["Telugu", "English"], formElementType: "checkbox", type: DataType.STRING },
{ id: 13, code: "registeredOn", title: "Registered On", sortable: true, searchReqd: false, filterable: true, displayable: true, formElementType: "range", type: DataType.DATE_AND_TIME },
{ id: 14, code: "currency", title: "Currency", sortable: true, searchReqd: false, filterable: true, displayable: false, enumValues: ["SUCCESS", "FAILED", "PENDING"], formElementType: "radio", type: DataType.STRING },
],
callBacks: {
onSelect: (row) => console.log("Selected row:", row),
onDelete: (row) => console.log("Deleted row:", row),
onSearch: (key) => console.log("Searching with key:", key),
onRowView: (key) => console.log("Viewing row with key:", key),
onRowEdit: (key) => console.log("Editing row with key:", key),
onRowDelete: (key) => console.log("Deleting row with key:", key),
onSort: (key) => console.log("Sorting by key:", key),
onClearSort: (key) => console.log("Clear sort for key:", key),
onFilter: (key) => console.log("Filtering by key:", key),
onClearFilter: (key) => console.log("Clear filter for key:", key),
onColumnSort: (key) => console.log("Column sort by key:", key),
onDownload: (key) => console.log("Download for key:", key),
onPagination: (value) => console.log("Pagination:", value),
},
serverSide: true,
serverSidePagination: true,
pageState: PageState.IDLE,
gridActions: {
ep_data: { uri: "/customer/get", method: "GET" },
ep_update: { uri: "/customer/update", method: "PUT" },
ep_delete: { uri: "/customer/delete", method: "DELETE" },
ep_toggle: { uri: "/customer/status", method: "PUT" },
},
};Props
data: An array of row objects matching the consumer's model (e.g.,Customer[]).gridMaster: The grid configuration object, containing columns, paging, sorting, filter state, UI options, and callback handlers.children: OptionalReactNodefor advanced composition; can pass grid state for debugging or developer tools.
Callbacks / Grid Event Callbacks
These functions are triggered by user interactions within the grid and allow you to implement custom logic for data manipulation and state updates.
Row Actions
onSelect: Triggered on row select/deselect.onRowView: Triggered on a single row “view” action.onRowEdit: Triggered on a single row “edit” action.onRowDelete: Triggered on a single row “delete” action.onDelete: Triggered for bulk delete actions.
Search and Filter
onSearch: Triggered for global search / filter submit; implement server or local filtering here.onColumnSearch: Triggered for per-column search; receives{ column, searchText }.onFilter: Triggered when filter UI is applied.onClearFilter: Clears current filter state.
Sorting
onSort: Triggered for global sort; receives{ column, direction }.onColumnSort: Triggered when sorting is invoked from a header context.onClearSort: Clears current sort state.
Pagination
onPagination: Triggered on page change; receives{ page, rowsPerPage, isFilter, filteredData }.
Other Actions
onClearAll: Clears all grid state.onDownload: Triggered for export; receives"xlsx"or"pdf".
Grid Types
Customer
Customer: The consumer's record shape; must at least include a uniqueid.
GridMaster
GridMaster: Configuration object for the grid.gridColumns: Columns configuration.paging: Paging info, includingcurrentPage,currentPageSize,totalPages.sortBy,sortDirection.pageState: Current UI state (seePageState).callBacks: Event callbacks likeonSelect,onDelete, etc.
PageState
PageStateenum values:LOADINGSUCCESSERROR
Column Configuration
Each entry in gridColumns can include:
code:string— field key in data.title:string— header label.displayable:boolean— controls visibility/export.width,align,sortable,filterable,searchable: optional flags.renderCell: optional custom renderer.formElementType: e.g.,"text","radio","range".type: e.g.,DataType.STRING,DataType.INTEGER,DataType.DATE_AND_TIME.enumValues: predefined options for the column (e.g.,"MALE","FEMALE").
Export Helpers
exportToExcel(data, columns, fileName): Exports selected columns to XLSX.exportToPDF(data, columns, fileName): Exports selected columns to PDF.
Tip: Map displayable columns and exclude internal fields before export.
Styling & Theming
- The component uses MUI theming. Wrap your app with
ThemeProviderandcreateThemeto customize palette, typography, and shape. - Layout is responsive via
Boxprops — adjust container width/height based on your use case.
Best practices
- Keep data immutable: create new arrays on sort/filter to avoid stale renders.
- Prefer server-side operations for large datasets. Wire network calls inside
onSearch/onPaginationand usepageStateto control loaders and errors. - Keep
gridColumnsstable (memoize) to avoid re-mounting cells.
Error handling
- Use
pageStateto show loading spinners and error banners. - In callbacks, wrap async calls with
try/catchand updatepageStateaccordingly.
Accessibility
- Keyboard navigation and focus rely on MUI/X Grid behavior — ensure row
idis stable and unique. - Provide clear header names and adequate contrast via theme.
Versioning & peer requirements
- React 18+
- Material UI v5 (
@mui/material,@emotion/react,@emotion/styled) @mui/x-data-gridfor base grid primitives- Icons via
@mui/icons-material
Contributing
- Open issues with minimal reproductions.
- Propose API sketches for new features before submitting PRs.
- Run type checks and linting before submitting.
License
ISC
