query-key-factory VS material-react-table

Compare query-key-factory vs material-react-table and see what are their differences.

query-key-factory

A library for creating typesafe standardized query keys, useful for cache management in @tanstack/query (by lukemorales)

material-react-table

A fully featured Material UI V5 implementation of TanStack React Table V8, written from the ground up in TypeScript (by KevinVandy)
SurveyJS - Open-Source JSON Form Builder to Create Dynamic Forms Right in Your App
With SurveyJS form UI libraries, you can build and style forms in a fully-integrated drag & drop form builder, render them in your JS app, and store form submission data in any backend, inc. PHP, ASP.NET Core, and Node.js.
surveyjs.io
featured
InfluxDB - Power Real-Time Data Analytics at Scale
Get real-time insights from all types of time series data with InfluxDB. Ingest, query, and analyze billions of data points in real-time with unbounded cardinality.
www.influxdata.com
featured
query-key-factory material-react-table
3 1
1,012 1,330
- -
6.7 9.7
2 months ago 6 days ago
TypeScript TypeScript
MIT License MIT License
The number of mentions indicates the total number of mentions that we've tracked plus the number of user suggested alternatives.
Stars - the number of stars that a project has on GitHub. Growth - month over month growth in stars.
Activity is a relative number indicating how actively a project is being developed. Recent commits have higher weight than older ones.
For example, an activity of 9.0 indicates that a project is amongst the top 10% of the most actively developed projects that we are tracking.

query-key-factory

Posts with mentions or reviews of query-key-factory. We have used some of these posts to build our list of alternatives and similar projects.

material-react-table

Posts with mentions or reviews of material-react-table. We have used some of these posts to build our list of alternatives and similar projects.
  • Create a reusable react-table component with Typescript
    1 project | dev.to | 28 Nov 2022
    const AComponentThatUsesTable = () => { return ( {/* .... */} ); }; Enter fullscreen mode Exit fullscreen mode And the result would be this:Pretty, isn't it?At the moment this table doesn't support a lot of personalization, luckily we can make it to support it quite easily thanks to the existing methods provided by react-table. Let's add the option to show conditionally a footer interface ReactTableProps { // ... showFooter: boolean; } export const Table = ({ data, columns, showFooter = true }: ReactTableProps) => { // ... return ( {/* ... */} {/* ... */} {showFooter ? ( {table.getFooterGroups().map((footerGroup) => ( {footerGroup.headers.map((header) => ( ))} ))} ) : null} {header.isPlaceholder ? null : flexRender(header.column.columnDef.footer, header.getContext())} ); }; Enter fullscreen mode Exit fullscreen mode Don't forget declaring the footer property in the columns array objects to display whatever we want to show in itE.g. const cols = useMemo[]>( () => [ { header: 'Name', cell: (row) => row.renderValue(), accessorKey: 'name', footer: 'Total', }, { header: 'Price', cell: (row) => row.renderValue(), accessorKey: 'price', footer: () => cartTotal, }, { header: 'Quantity', cell: (row) => row.renderValue(), accessorKey: 'quantity', }, ], [cartTotal] ); {/* .... */} Enter fullscreen mode Exit fullscreen mode The component now accepts a boolean props that displays footer conditionallyNow let's implement something more meaningful, like navigation features —pagination included! import { useReactTable, getPaginationRowModel, } from '@tanstack/react-table'; interface ReactTableProps { // ... showNavigation?: boolean; } export const Table = ({ // ... showNavigation = true, }: ReactTableProps) => { const table = useReactTable({ // ... getPaginationRowModel: getPaginationRowModel(), }); return ( {/* ... */} {showNavigation ? ( <> table.setPageIndex(0)} disabled={!table.getCanPreviousPage()} > {'<<'} table.previousPage()} disabled={!table.getCanPreviousPage()} > {'<'} table.nextPage()} disabled={!table.getCanNextPage()} > {'>'} table.setPageIndex(table.getPageCount() - 1)} disabled={!table.getCanNextPage()} > {'>>'} Page {table.getState().pagination.pageIndex + 1} of {table.getPageCount()} | Go to page: { const page = e.target.value ? Number(e.target.value) - 1 : 0; table.setPageIndex(page); }} className="w-16 rounded border p-1" /> { table.setPageSize(Number(e.target.value)); }} > {[10, 20, 30, 40, 50].map((pageSize) => ( Show {pageSize} ))} ) : null} ); }; Enter fullscreen mode Exit fullscreen mode Pagination will also be displayed only if we pass the prop showPagination const AComponentThatUsesTable = () => { return ( {/* .... */} ); }; Enter fullscreen mode Exit fullscreen mode And we have this wonderful controllers ready to be used:You can change the Show ${N} options by changing this array in the Table component { table.setPageSize(Number(e.target.value)); }} > {/* change items per page in this array */} {[10, 20, 30, 40, 50].map((pageSize) => ( Show {pageSize} ))} Enter fullscreen mode Exit fullscreen mode Finally, a component that it's imprescindible in big tables, a filter input.We'll use a debounced input, this way the filter won't be triggered at every key stroke of the input.A reusable component would also be nice to keep our code DRYer and to take advantage of this strategy elsewhere in our project import { useEffect } from 'react'; import { useState } from 'react'; interface Props extends Omit, 'onChange'> { value: string | number; onChange: (val: string | number) => void; debounceTime?: number; } export const DebouncedInput = ({ value: initialValue, onChange, debounceTime = 300, ...props }: Props) => { const [value, setValue] = useState(initialValue); // setValue if any initialValue changes useEffect(() => { setValue(initialValue); }, [initialValue]); // debounce onChange — triggered on every keypress useEffect(() => { const timeout = setTimeout(() => { onChange(value); }, debounceTime); return () => { clearTimeout(timeout); }; }, [value, onChange, debounceTime]); return setValue(e.target.value)} />; }; Enter fullscreen mode Exit fullscreen mode We can try with these initial functions. The fuzzy function will be our default filterFn when no other function is passed to the Table component. I took these functions from Material-React-Table, a great repository for an opinionated ready-to-use table based on react-table. /* eslint-disable @typescript-eslint/no-explicit-any */ import { rankItem, rankings } from '@tanstack/match-sorter-utils'; import type { RankingInfo } from '@tanstack/match-sorter-utils'; import type { Row } from '@tanstack/react-table'; // most of table work acceptably well with this function const fuzzy = = {}>( row: Row, columnId: string, filterValue: string | number, addMeta: (item: RankingInfo) => void ) => { const itemRank = rankItem(row.getValue(columnId), filterValue as string, { threshold: rankings.MATCHES, }); addMeta(itemRank); return itemRank.passed; }; // if the value is falsy, then the columnFilters state entry for that filter will removed from that array. // https://github.com/KevinVandy/material-react-table/discussions/223#discussioncomment-4249221 fuzzy.autoRemove = (val: any) => !val; const contains = = {}>( row: Row, id: string, filterValue: string | number ) => row .getValue(id) .toString() .toLowerCase() .trim() .includes(filterValue.toString().toLowerCase().trim()); contains.autoRemove = (val: any) => !val; const startsWith = = {}>( row: Row, id: string, filterValue: string | number ) => row .getValue(id) .toString() .toLowerCase() .trim() .startsWith(filterValue.toString().toLowerCase().trim()); startsWith.autoRemove = (val: any) => !val; export const filterFns = { fuzzy, contains, startsWith, }; Enter fullscreen mode Exit fullscreen mode Add a filterFn property to the interface and also in the Table component props interface ReactTableProps { data: T[]; columns: ColumnDef[]; showFooter?: boolean; showNavigation?: boolean; showGlobalFilter?: boolean; filterFn?: FilterFn; } export const Table = ({ data, columns, showFooter = true, showNavigation = true, showGlobalFilter = false, filterFn = filterFns.fuzzy, }: ReactTableProps) => { // this is the search value const [globalFilter, setGlobalFilter] = useState(''); Enter fullscreen mode Exit fullscreen mode Update the useReactTable options // table.tsx const table = useReactTable({ data, columns, // state: { globalFilter }, getCoreRowModel: getCoreRowModel(), getFilteredRowModel: getFilteredRowModel(), getPaginationRowModel: getPaginationRowModel(), // onGlobalFilterChange: setGlobalFilter, globalFilterFn: filterFn, }); Enter fullscreen mode Exit fullscreen mode And finally add the conditional jsx for the filter function. export const Table = ({ /* ... */ return ( {showGlobalFilter ? ( setGlobalFilter(String(value))} className="font-lg border-block border p-2 shadow mb-2" placeholder="Search all columns..." /> ) : null} /* ... */ Enter fullscreen mode Exit fullscreen mode Passing the showGlobalFilter prop as true should be enough Enter fullscreen mode Exit fullscreen mode But we could also pass one our the filter functions declared above e.g. Enter fullscreen mode Exit fullscreen mode And there you go, we have our super useful debounced filter input 🤩.And this was it. We can now make use of our reusable Table component wherever we want to and with fully type safety.Resources:https://github.com/KevinVandy/material-react-table/blob/main/src/filterFns.tsPhoto from Roman Mager in Unsplashhttps://codesandbox.io/s/tanstack-table-example-fully-controlled-wthmte?file=/src/main.tsxhttps://tanstack.com/table/v8

What are some alternatives?

When comparing query-key-factory and material-react-table you can also consider the following projects:

react-query-helper - A helper library to use react-query more efficient, consistency

devlog - DevLog - I have built an admin dashboard using React with Material UI, Supabase and Refine. The purpose of this dashboard is to efficiently manage blogs.

react-query-auth-token-refresh - Demo code for React Query Auth Token Refresh Article

rapini - :leafy_green: OpenAPI to React Query (or SWR) & Axios

hyper-fetch - ⚡ Fetching and realtime data exchange framework.

primereact - The Most Complete React UI Component Library

react-query-kit - 🕊️ A toolkit for ReactQuery that make ReactQuery hooks reusable and typesafe

obsidian-bd-folder - Obsidian Plugin to Allow Notion like database based on folders [Moved to: https://github.com/RafaelGB/obsidian-db-folder]

pocketbook - Minimal social app with rakkasjs vite ssr, shadcn and pocketbase

react-headless - React headless components

TanStack Query - 🤖 Powerful asynchronous state management, server-state utilities and data fetching for the web. TS/JS, React Query, Solid Query, Svelte Query and Vue Query.

react-custable - A custom table for react