Introduction
On this article, we’ll present learn how to use Materials UI <DataGrid/>
part and refine’s useDataGrid
hook to render knowledge from a mock API server in tabular type utilizing a refine
software.
refine is a React-based framework for quickly growing data-driven purposes by a group of helper hooks
, parts
, and data-providers
. refine is a headless framework that does not embrace UI parts by default however has help and configurations to inject any UI libraries or a framework of selections akin to Materials UI or Tailwind CSS.
Materials UI is a React UI part library with a wealthy set of parts and instruments for bootstrapping elegant person interfaces. We’ll use the <DataGrid/>
part to render an inventory of workers from a mock server. We’ll additionally have a look at a few of the properties and customized configurations that can be utilized with the part.
Steps we’ll cowl:
Stipulations
refine is a react software shipped with TypeScript by default. Our tutorial software might be written in typescript-react, so a very good background in coding in React and TypeScript is important. Additionally, guarantee you will have the next variations of node and npm to keep away from working into errors with superplate:
- Node v16.14 or later
- Npm v8.3 or later
You’ll be able to run node -v
and npm -v
in your terminal to verify your put in variations earlier than continuing.
Establishing a refine
software
There are two attainable methods to arrange a refine software: utilizing superplate or including the refine module into an empty React software. We’ll go together with the previous methodology on this tutorial as it is the really useful method to get began.
Run the next command in your terminal to create a refine app with superplate:
npx superplate-cli -p refine-react datagrid
Within the command above, the -p
flag specifies the challenge kind which in our case, a refine-react challenge. datagrid
is the title I selected because the app title for brevity. You’ll be able to all the time select any title you are snug with.
You can be requested a number of questions by the installer. Choose the next choices to proceed:
After superplate has completed creating our app, run npm run dev
to start out the event server after which navigate to localhost:8000
within the browser to view the app. If every went easily, the next needs to be rendered on the browser:
Creating mock API with Mockaroo and My JSON Server
The faux worker knowledge we’ll render within the <DataGrid/>
part might be created with Mockaroo and My JSON Server. Mockaroo is a random faux knowledge generator for producing as much as 1,000 lifelike take a look at knowledge in JSON, CSV, and different codecs.
My JSON Server is a faux on-line REST Server for prototyping software APIs with out a backend. The REST Server for the JSON knowledge we’ll use on this tutorial is hosted right here, and the faux JSON knowledge created with Mockaroo is on GitHub.
Materials UI DataGrid part
The Materials UI DataGrid part is an extendable and feature-rich part used to show tabular knowledge in React purposes. A few of its highly effective options embrace automated pagination, desk knowledge filtering and sorting, and lots of different cool options.
The part is obtainable in two variations, the MIT <DataGrid/>
and Business <DataGridPro/>
(Professional and Premium) variations. The MIT model is free-to-use whereas the industrial model is paid and extends the options of the MIT model akin to the flexibility to filter and kind a number of columns on the similar time.
The <DataGrid/>
part requires two obligatory properties specifically: rows
and columns
. The columns
prop accepts an array of fields that are used because the desk header whereas the rows
prop accepts an array of objects (knowledge) to be rendered throughout the desk rows.
The next instance reveals a primary utilization of the DataGrid
part:
<DataGrid
columns={[{ field: 'name' }]}
rows={[
{ id: 1, name: 'React' },
{ id: 2, name: 'MUI' },
]}
/>
Though refine is a headless framework that can be utilized with any UI framework of alternative, it has built-in help for a number of UI frameworks, akin to Materials UI. The refine-mui
module, for instance ships with some frequent Materials UI parts akin to DataGrid
, GridColumn
, and so forth.
We’ll see learn how to leverage these parts with refine’s useDataGrid
hook in our refine app within the coming sections.
Including styled-components
We’ll use styled-components to fashion our app, as refine does not management how we select to fashion our purposes. So let’s go forward and set up it with its varieties definition as follows:
npm set up styled-components && npm set up --save-dev @varieties/styled-components
Subsequent, create two folders: parts
and pages
within the src
folder. We’ll be writing the majority of our code in these folders.
Then, create a Structure.tsx
file within the parts
folder and add the next code to it:
// src/parts/Structure.tsx
import React from 'react';
import { LayoutProps } from "@pankod/refine-core";
import styled from 'styled-components';
const Wrapper = styled.div`
width: 80%;
margin: 50px auto;
top: 100%;
`;
const Structure: React.FC<LayoutProps> = ({kids}) => {
return (
<>
<Wrapper>
{kids}
</Wrapper>
</>
);
}
export default Structure;
Above, we’re making a div to wrap our app content material by the kids
prop after which aligning it within the middle of the web page.
refine’s useDataGrid
hook
Along with integrating MUI parts, refine offers a clear interface by the useDataGrid
hook for implementing some properties that can be utilized with MUI <DataGrid/>
part. The hook simplifies working with options akin to pagination, sorting, and filtering which come as out-of-box.
As an example, if in case you have a web page part the place you need to render tabular knowledge, you would possibly do one thing just like the under:
// src/pages/instance.tsx
import React from'react'
import { useDataGrid, DataGrid, GridColumns } from "@pankod/refine-mui"
const Desk: React.FC = () => {
const { dataGridProps } = useDataGrid();
const columns: GridColumns = [
{
field: "id",
headerName: "ID",
},
{
field: "name",
headerName: "Name"
},
{
field: "Age",
headerName: "Age"
},
];
return (
<DataGrid
{...dataGridProps}
columns={columns}
autoHeight
/>
)
}
export default Desk;
It is necessary to notice that within the above instance, we’re not passing the rows
prop to the <DataGrid/>
part. It is because the dataGridProps
variable mechanically injects the rows
values into the <DataGrid>
part by the native <Refine/>
part’s dataProvider
prop out there within the src/App.tsx
file of your refine software.
The dataProvider
prop is used to learn knowledge from an API endpoint after which make the info out there in the whole software.
Consult with refine knowledge supplier documentation for detailed utilization
Rendering knowledge with the <DataGrid/>
part
We’ll use the mock API we created with Mockaroo and My JSON Server as the info supply for our DataGrid part.
To get began, create a folder within the pages
folder named workers
, after which on this folder, create a file named workers.tsx
.
Add the next code to the workers.tsx
file:
// src/pages/workers.tsx
import React from 'react';
import { useDataGrid, DataGrid, GridColumns, Record } from '@pankod/refine-mui';
const EmployeeList: React.FC = () => {
const { dataGridProps } = useDataGrid();
const columns = React.useMemo<GridColumns>(
() => [
{ field: 'id', headerName: 'ID', Width: 30 },
{
field: 'full_name',
headerName: 'Full Name',
minWidth: 150,
flex: 1,
valueGetter: (params) =>
`$ '' $`,
},
{
field: 'email',
headerName: 'Email',
minWidth: 250,
},
{
field: 'department',
headerName: 'Department',
minWidth: 150,
},
{
field: 'role',
headerName: 'Role',
minWidth: 150,
},
{
field: 'level',
headerName: 'Level',
Width: 30,
},
],
[]
);
return (
<Record>
<DataGrid
{...dataGridProps}
checkboxSelection
disableSelectionOnClick
columns={columns}
autoHeight
/>
</Record>
);
};
export default EmployeeList;
Let’s perceive what is going on on above.
The columns
variable defines the column fields for our knowledge. We additionally wrapped the fields in a React.Memo
greater order part for memoizing the values after which created fields for every of the properties from our useful resource endpoint. We additionally used the valueGetter
attribute to compose a worth from two totally different fields.
Subsequent, edit App.tsx
within the src
folder to the next:
// src/App.tsx
import { Refine } from '@pankod/refine-core';
import {
CssBaseline,
GlobalStyles,
ThemeProvider,
LightTheme,
} from '@pankod/refine-mui';
import routerProvider from '@pankod/refine-react-router-v6';
import dataProvider from '@pankod/refine-simple-rest';
import Structure from './parts/Structure';
import EmployeeList from './pages/workers';
operate App() {
return (
<ThemeProvider theme={LightTheme}>
<CssBaseline />
<GlobalStyles types={{ html: { WebkitFontSmoothing: 'auto' } }} />
<Refine
Structure={Structure}
routerProvider={routerProvider}
dataProvider={dataProvider(
'https://my-json-server.typicode.com/Mich45/employee-data'
)}
sources={[{ name: 'employees', list: EmployeeList }]}
/>
</ThemeProvider>
);
}
export default App;
This is a breakdown of what’s going on above:
The native <Refine/>
part accepts a dataProvider
prop which specifies the supply of our knowledge (the faux REST API we created earlier), and a sources
prop which takes an array of object properties:
- The
title
property is the title of the useful resource we predict from the REST API – this worth should match the useful resource we created within the REST API. In our case,workers
. - The
listing
property takes a web page part to render the info. That is theEmployeeList
part we’re importing from thepages/workers
folder.
We additionally added a format part (Structure.tsx
) to the Structure
prop. That is to customise the appear and feel of our app.
Now, when you navigate to localhost:8000/workers
, it is best to see the next:
Voila! We have efficiently displayed our knowledge from a REST API in a MUI DataGrid part. Within the subsequent part we’ll have a look at how we are able to use the useDataGrid
hook to simplify operations akin to pagination, sorting, and filtering.
Pagination, Filtering, and Sorting utilizing the useDataGrid
hook
The useDataGrid
hook simplifies operations akin to pagination, sorting, and filtering on the <DataGrid/>
part by a versatile API. On this half, we’ll leverage the hook so as to add pagination, sorting, and filter options to our workers desk knowledge.
Pagination
Pagination lets us show a sure variety of rows on a DataGrid at a time and is enabled by default. It can’t be disabled both. It’s out there on the backside of the DataGrid part like so:
For instance, our workers listing has a complete of 28 rows, however we might need to render simply 10 rows per web page. Right here’s a demo displaying how we are able to render 10 rows of things on the preliminary web page render with the initialPageSize property (defaults to 25).
That is much like utilizing the initialState
prop on the DataGrid part. We are able to additionally outline what number of rows the person can select to view per web page utilizing the rowsPerPageOptions
prop.
Replace the workers.tsx
with the next codes:
// src/pages/workers.tsx
import React from 'react';
import { useDataGrid, DataGrid, GridColumns, Record } from '@pankod/refine-mui';
...
// ====>
const { dataGridProps } = useDataGrid({initialPageSize: 10});
const {
pageSize,
onPageSizeChange,
...restDataGridProps
} = dataGridProps;
// <====
...
return (
<Record>
// ====>
<DataGrid
{...restDataGridProps}
checkboxSelection
disableSelectionOnClick
columns={columns}
pageSize={10}
onPageSizeChange={onPageSizeChange}
rowsPerPageOptions={[10, 15]}
autoHeight
/>
// <====
</Record>
);
export default EmployeeList;
Which renders our grid like this:
You’ll be able to seek advice from the pagination documentation for extra props on pagination.
Sorting
The DataGrid part lets us kind the info within the rows based mostly on one criterion at a time. Sorting is enabled for all columns by default within the MIT model and can be disabled both for all columns or a single column.
We are able to kind the rows in three orders: ascending (ASC), descending (DESC) or null (sorting might be disabled).
To kind the rows, click on or hover on any column header, this shows an arrow indicator pointing up or down relying in your sorting order. When it is ascending the arrow factors upward, and factors downward for descending. Alternatively, we are able to additionally entry it from the grid column menu.
Preliminary kind order
We are able to initialize a sorting order for every or all fields within the grid utilizing the intialSorter
property of the useDataGrid
part. This lets us kind the rows on the preliminary web page render.
// src/pages/workers.tsx
const { dataGridProps } = useDataGrid({initialSorter: [{ field: 'level', order: 'desc' }]});
The above instance will kind the rows utilizing the stage column on the preliminary render in descending order like so:
Managed sorting
We are able to additionally kind rows externally utilizing the setSorter
operate from the useDataGrid
hook. The next code reveals how we are able to kind the rows by clicking on customized buttons outdoors the DataGrid part.
// src/pages/workers.tsx
import React from 'react';
import styled from 'styled-components';
import {
useDataGrid,
DataGrid,
GridColumns,
Record,
// ====>
Button,
ButtonGroup,
// <====
} from '@pankod/refine-mui';
// ====>
const ButtonsWrapper = styled.div`
width: 100%;
margin: 20px 0;
`;
// <====
const EmployeeList: React.FC = () => {
// ====>
const { dataGridProps, setSorter } = useDataGrid();
// <====
const columns = React.useMemo<GridColumns>(
() => [
{ field: 'id', headerName: 'ID', Width: 30 },
{
field: 'full_name',
headerName: 'Full Name',
minWidth: 150,
flex: 1,
valueGetter: (params) =>
`$ '' $`,
},
{
field: 'email',
headerName: 'Email',
minWidth: 250,
},
{
field: 'department',
headerName: 'Department',
minWidth: 150,
},
{
field: 'role',
headerName: 'Role',
minWidth: 150,
},
{
field: 'level',
headerName: 'Level',
Width: 30,
},
],
[]
);
// ====>
const handleSorting = (order: 'asc' | 'desc') => {
setSorter([
{
field: 'level',
order,
},
]);
};
// <====
return (
<Record>
// ====>
<ButtonsWrapper>
<ButtonGroup variant="outlined">
<Button onClick={() => handleSorting('asc')}>Asc</Button>
<Button onClick={() => handleSorting('desc')}>Desc</Button>
</ButtonGroup>
</ButtonsWrapper>
<DataGrid
{...dataGridProps}
checkboxSelection
columns={columns}
autoHeight
/>
// <====
</Record>
);
};
export default EmployeeList;
This is a GIF displaying the results of the above instance.
Consult with the sorting documentation to be taught extra concerning the characteristic.
Filtering
Filtering lets us search the rows for values within the DataGrid part based mostly on one criterion at a time.
We are able to entry the type characteristic by both clicking on the filter merchandise within the column menu:
or by utilizing the filter button within the grid toolbar:
You’ll be able to import the GridToolbar part and use it like so:
// src/pages/workers.tsx
import { GridToolbar } from "@pankod/refine-mui"
<DataGrid
{...dataGridProps}
checkboxSelection
columns={columns}
parts={{ Toolbar: GridToolbar }}
autoHeight
/>
The filter characteristic works by looking the rows for values that match a given filter operator. The listing of operators which can be utilized within the sortModel may be discovered right here.
As an example in our workers desk we are able to filter the division column for rows that include a Assist
worth by utilizing any of the above strategies.
This is the code for the above instance. Replace the workers.tsx
with highlighted code.
// src/pages/workers.tsx
import React from 'react';
import {
useDataGrid,
DataGrid,
GridColumns,
Record,
//highlight-next-line
GridToolbar,
} from '@pankod/refine-mui';
// ====>
const { dataGridProps} = useDataGrid();
// <====
...
// ====>
const {
filterMode,
filterModel,
onFilterModelChange,
...restDataGridProps
} = dataGridProps;
// <====
return (
<Record>
// ====>
<DataGrid
{...restDataGridProps}
filterMode={filterMode}
filterModel={filterModel}
onFilterModelChange={onFilterModelChange}
columns={columns}
parts={{ Toolbar: GridToolbar }}
autoHeight
/>
// <====
</Record>
);
export default EmployeeList;
Managed filtering
We are able to additionally select to filter the desk externally by utilizing the setFilters
operate of the useDataGrid
hook to set a filter state. The operate accepts three properties to filter the desk.
-
area
– the column area within the desk to use the filter -
operator
– the criterion to filter the desk -
worth
– the worth to seek for
This is an instance displaying how we are able to use a customized checkbox to look the rows for workers with position that equals Recruiter.
Replace the workers.tsx
with highlighted code:
// src/pages/workers.tsx
import React from 'react';
import {
useDataGrid,
DataGrid,
GridColumns,
Record,
GridToolbar,
// ====>
FormControlLabel,
Checkbox,
// <====
} from '@pankod/refine-mui';
const EmployeeList: React.FC = () => {
const { dataGridProps, setFilters } = useDataGrid();
const columns = React.useMemo<GridColumns>(
() => [
{ field: 'id', headerName: 'ID', Width: 30 },
{
field: 'full_name',
headerName: 'Full Name',
minWidth: 150,
flex: 1,
valueGetter: (params) =>
`$ '' $`,
},
{
field: 'email',
headerName: 'Email',
minWidth: 250,
},
{
field: 'department',
headerName: 'Department',
minWidth: 150,
},
{
field: 'role',
headerName: 'Role',
minWidth: 150,
},
{
field: 'level',
headerName: 'Level',
Width: 30,
},
],
[]
);
const {
filterMode,
filterModel,
onFilterModelChange,
...restDataGridProps
} = dataGridProps;
// ====>
const handleFilter = (
e: React.ChangeEvent<HTMLInputElement>,
checked: boolean
) => {
setFilters([
{
field: 'role',
value: checked ? 'Recruiter' : undefined,
operator: 'eq',
},
]);
};
// <====
return (
<Record>
// ====>
<FormControlLabel
label="Filter Staff with Recruiter Function"
management={<Checkbox onChange={handleFilter} />}
/>
// <====
<DataGrid
{...restDataGridProps}
filterMode={filterMode}
filterModel={filterModel}
onFilterModelChange={onFilterModelChange}
columns={columns}
parts={{ Toolbar: GridToolbar }}
autoHeight
/>
</Record>
);
};
export default EmployeeList;
Which provides the next consequence whenever you click on on the checkbox:
Consult with the filtering documentation for extra info on out there settings and superior utilization.
Conclusion
On this article we launched you to the MUI <DataGrid/>
part and learn how to use it to render tabular knowledge. We additionally realized learn how to simplify operations akin to pagination, sorting and filtering on the part utilizing the useDataGrid
hook.
We hope this text helps you in getting began with the <DataGrid/>
part in your refine purposes.
The place to go subsequent? Examine the useDataGrid hook documentation right here and the MUI X <DataGrid/>
documentation for extra utilization info and reference.
Author: Michael Hungbo
Stay StackBlitz Instance
Construct your React-based CRUD purposes with out constraints
Constructing CRUD purposes includes many repetitive job consuming your treasured growth time. If you’re ranging from scratch, you additionally need to implement customized options for crucial components of your software like authentication, authorization, state administration and networking.
Take a look at refine, if you’re taken with a headless framework with sturdy structure and stuffed with trade greatest practices in your subsequent CRUD challenge.
refine is a open-source React-based framework for constructing CRUD purposes with out constraints.
It might probably pace up your growth time as much as 3X with out compromising freedom on styling, customization and challenge workflow.
refine is headless by design and it connects 30+ backend companies out-of-the-box together with customized REST and GraphQL API’s.
Go to refine GitHub repository for extra info, demos, tutorials, and instance initiatives.