I have a large dataset sometimes containing millions of products data. When I am sending it to frontend I limit it to 1000 product at first to be fast. This is how I am doing with Django rest:
def get_products(self, request, pk=None):
page = int(request.query_params['page']) if 'page' in request.query_params else 0
page_size = 1000
data = list(collection.find(filter_query, {'_id': 0}).skip(page * page_size).limit(page_size))
total_count: collection.count()
return Response({'message': 'success', 'data': data, 'count':total_count}, 200)
So in React, I accept the first 1000 products at first request. I show them on AG-GRID table. But I also need to show real page numbers ( I have the total count of the products). If user clicks on page=650 for example, I will send another request to the backend with the equivalent page number and fetch the remaining data.
`http://localhost:8000/${ID}/products?page=${page}`
This is how I fetch data and show in AG grid on frontend:
React.useEffect(() => {
jwtAxios(
`http://localhost:8000/${ID}/products/`
).then((result) => {
if (!result || !result.data.data || !result.data.data.length) {
setRowData([]);
setColumnData([]);
return;
}
setRowData(result.data.data);
// Get column fields
const columnDefs = [];
Object.keys(result.data.data[0]).map((fieldName) => {
columnDefs.push({
headerName: fieldName,
field: fieldName,
});
return null;
});
setColumnData(columnDefs);
});
}, [catalogID]);
// enables pagination in the grid
const pagination = true;
const paginationPageSize = 20;
function imageCellRenderer(params) {
return `<img alt="${params.value}" src="${params.value}" width="60px" height="80px">`;
}
return (
<Grid container item xs={12} spacing={6}>
<Grid item xs={12}>
<Paper className={classes.paper} elevation={1}>
<Grid
container
item
xs={12}
justify='center'
alignContent='center'
className={classes.previewTable}>
<div
className='ag-theme-material'
style={{width: '100%', height: '100%'}}>
<AgGridReact
defaultColDef={{
editable: false,
sortable: true,
minWidth: 800,
filter: true,
resizable: true,
enableBrowserTooltips: 'true',
}}
tooltipShowDelay={1}
rowSelection='multiple'
rowStyle={rowStyle}
pagination={pagination}
paginationPageSize={paginationPageSize}
overlayLoadingTemplate={
'<span className="ag-overlay-loading-center" style="padding: 10px; border: 2px solid #444; background: #fffef0;">Please wait while your data is loading</span>'
}
overlayNoRowsTemplate={
'<span className="ag-overlay-loading-center"<span className="ag-overlay-loading-center" style="padding: 10px; border: 2px solid #444; background: #fffef0;">There is no data to preview</span>'
}
rowData={rowData}>
{columnData.map((col) => {
if (
col.field.includes(
'image_link',
) &&
!col.field.includes(
'additional',
)
) {
return (
<AgGridColumn
field={col.field}
minWidth={130}
tooltipField={col.field}
key={col.field}
cellRenderer={
imageCellRenderer
}
/>
);
}
return (
<AgGridColumn
field={col.field}
minWidth={130}
tooltipField={col.field}
key={col.field}
/>
);
})}
</AgGridReact>
I am not sure how to achieve that because AG grid only shows the pages according to the data from backend. Or is there a better way to show fast big data to frontend? I couldn't find any source regarding this. Thanks.