afraid-scarlet
afraid-scarlet6mo ago

How to filter on relation fields in a DataGrid?

I have a DataGrid that has a column with a relationship field. I show this field with its 'name' field. How can I configure the DataGrid filter to be able to filter using this 'name' field?
3 Replies
kapa.ai
kapa.ai6mo ago
Hi @❴𝖒𝖔𝖗❵. I'm kapa.ai, your friendly support bot. I will try to answer your question by searching through the knowledge base. :wave: ---------------------- You can use the useSelect hook to fetch relational data and filter the <DataGrid> by categories. Here is an example of how you can handle relational data:
import React from "react";
import { Option, useSelect } from "@refinedev/core";
import { useDataGrid, List } from "@refinedev/mui";
import { DataGrid, GridColDef, GridValueFormatterParams } from "@mui/x-data-grid";

import { ICategory, IPost } from "interfaces";

const PostsList: React.FC = () => {
const { dataGridProps } = useDataGrid<IPost>({
pagination: {
current: 2,
pageSize: 10,
},
sorters: {
initial: [
{
field: "title",
order: "asc",
},
],
},
filters: {
initial: [
{
field: "status",
operator: "eq",
value: "draft",
},
],
},
syncWithLocation: true,
});

const {
options,
queryResult: { isLoading },
} = useSelect<ICategory>({
resource: "categories",
hasPagination: false,
});

const columns = React.useMemo<GridColDef<IPost>[]>(
() => [
{
field: "id",
headerName: "ID",
type: "number",
width: 50,
},
{ field: "title", headerName: "Title", minWidth: 400, flex: 1 },
{
field: "category.id",
headerName: "Category",
type: "singleSelect",
headerAlign: "left",
align: "left",
minWidth: 250,
flex: 0.5,
valueOptions: options,
valueFormatter: (params: GridValueFormatterParams<Option>) => {
return params.value;
},
renderCell: function render({ row }) {
if (isLoading) {
return "Loading...";
}

const category = options.find((item) => item.value.toString() === row.category.id.toString());
return category?.label;
},
},
{
field: "status",
headerName: "Status",
minWidth: 120,
flex: 0.3,
type: "singleSelect",
valueOptions: ["draft", "published", "rejected"],
},
],
[options, isLoading],
);

return (
<List>
import React from "react";
import { Option, useSelect } from "@refinedev/core";
import { useDataGrid, List } from "@refinedev/mui";
import { DataGrid, GridColDef, GridValueFormatterParams } from "@mui/x-data-grid";

import { ICategory, IPost } from "interfaces";

const PostsList: React.FC = () => {
const { dataGridProps } = useDataGrid<IPost>({
pagination: {
current: 2,
pageSize: 10,
},
sorters: {
initial: [
{
field: "title",
order: "asc",
},
],
},
filters: {
initial: [
{
field: "status",
operator: "eq",
value: "draft",
},
],
},
syncWithLocation: true,
});

const {
options,
queryResult: { isLoading },
} = useSelect<ICategory>({
resource: "categories",
hasPagination: false,
});

const columns = React.useMemo<GridColDef<IPost>[]>(
() => [
{
field: "id",
headerName: "ID",
type: "number",
width: 50,
},
{ field: "title", headerName: "Title", minWidth: 400, flex: 1 },
{
field: "category.id",
headerName: "Category",
type: "singleSelect",
headerAlign: "left",
align: "left",
minWidth: 250,
flex: 0.5,
valueOptions: options,
valueFormatter: (params: GridValueFormatterParams<Option>) => {
return params.value;
},
renderCell: function render({ row }) {
if (isLoading) {
return "Loading...";
}

const category = options.find((item) => item.value.toString() === row.category.id.toString());
return category?.label;
},
},
{
field: "status",
headerName: "Status",
minWidth: 120,
flex: 0.3,
type: "singleSelect",
valueOptions: ["draft", "published", "rejected"],
},
],
[options, isLoading],
);

return (
<List>
In this example, the useSelect hook is used to fetch the categories, which are then used as valueOptions for the category.id field in the DataGrid. The valueFormatter and renderCell functions are used to display the category label in the DataGrid. For more information, you can refer to the refine documentation (https://refine.dev/docs/ui-integrations/material-ui/hooks/use-data-grid#how-can-i-handle-relational-data). If you want to filter based on a table from an inner join, you will need to use .select('*, mytable!inner(*)') within Supabase. For more information, you can refer to the refine documentation (https://refine.dev/docs/data/packages/supabase#deep-filtering). ---------------------- Note: you can ask me a follow up question by @ mentioning me again :speech_balloon: ----------------------
kapa.ai
kapa.ai6mo ago
<@245678638211661824> kapa.ai is still learning and improving, please let us know how it did by reacting below
afraid-scarlet
afraid-scarlet6mo ago
I am using Refine with MUI.