T
TanStack3y ago
other-emerald

When is "select" function called exactly?

Hi! I'm working on reducing number of re-renders of a particularly slow component. Currently, we are transforming data returned by useQuery call using useMemo, which results in everything being called twice whenever there's a change. I moved the code from useMemo into a select handler and extracted the handler to a stable function reference. However, when useQuery params change, it looks like the select handler is called twice - once with the new data, as expected, and then the second time with exactly the same data as before. As my select handler is not memoized and returns a new instance of an object for the same input data every time it's called, it causes an additional re-render. Is it supposed to work like this? I thought that if the response data hasn't changed, react-query won't even call the select handler again. Here's a slightly simplified code:
const { data, isLoading } = useCustomQuery(
{ ids },
{ ...options, select: transformData },
)
const { data, isLoading } = useCustomQuery(
{ ids },
{ ...options, select: transformData },
)
and
export const myCustomQuery = (params, options) =>
useQuery(
['customQuery', params],
() => fetchData(params),
options,
)
export const myCustomQuery = (params, options) =>
useQuery(
['customQuery', params],
() => fetchData(params),
options,
)
BTW. We're still on the "latest" version of react-query 3 :/
3 Replies
metropolitan-bronze
metropolitan-bronze3y ago
Have you read this? https://tkdodo.eu/blog/react-query-data-transformations Perhaps putting the transform into the queryFn will help
React Query Data Transformations
Learn the possibilities to perform the quite common and important task of transforming your data with react-query
fascinating-indigo
fascinating-indigo3y ago
select results are structurally shared, so even if you return a new reference every time, RQ will know if something changed inside it But note that when a render was triggered by something else, we can't stop that render. This optimization is only for renders that would be initiated by RQ
other-emerald
other-emeraldOP3y ago
Thanks!

Did you find this page helpful?