T
TanStack17mo ago
noble-gold

Initializing QueryClient in a top level component using useState instead of Global Variable

Hi, We have a requirement wherein, we need to access Jotai atoms inside QueryClient initializtion as below. Hence, we moved the queryClient initialization from being a global variable to inside a state variable in top level component. This allows us to redirect the user to login page if the session has expired on server. Anything we should be worried about here? Is this approach fine?
const AllProviders = ({ children }: { children: ReactNode }) => {
const logoutUser = useSetAtom(logoutUserAtom);
const [queryClient] = useState(
new QueryClient({
queryCache: new QueryCache({
onError: (error) => {
if (error.session_expired) {
logoutUser();
}
toast.error(errorMessage, { toastId: errorMessage });
},
}),
}),
);

return (
<QueryClientProvider client={queryClient}>
<StyledEngineProvider injectFirst>
<ThemeProvider theme={rootTheme}>
<AuthProvider>{children}</AuthProvider>
</ThemeProvider>
</StyledEngineProvider>
<ReactQueryDevtools initialIsOpen={false} />
</QueryClientProvider>
);
};
const AllProviders = ({ children }: { children: ReactNode }) => {
const logoutUser = useSetAtom(logoutUserAtom);
const [queryClient] = useState(
new QueryClient({
queryCache: new QueryCache({
onError: (error) => {
if (error.session_expired) {
logoutUser();
}
toast.error(errorMessage, { toastId: errorMessage });
},
}),
}),
);

return (
<QueryClientProvider client={queryClient}>
<StyledEngineProvider injectFirst>
<ThemeProvider theme={rootTheme}>
<AuthProvider>{children}</AuthProvider>
</ThemeProvider>
</StyledEngineProvider>
<ReactQueryDevtools initialIsOpen={false} />
</QueryClientProvider>
);
};
2 Replies
eastern-cyan
eastern-cyan17mo ago
yes
noble-gold
noble-goldOP17mo ago
Thank you One thing I found out for anyone checking this out. The above does not handle mutation scenario. So had to modify as follow. Had to add in defaultOptions. I noticed, in defaultOptions, we have callbacks for Mutations but not for Queries. Also, we could define mutationCache, with similar logic. But, I am not sure of the use of mutationCache in our application
const AllProviders = ({ children }: { children: ReactNode }) => {
const logoutUser = useSetAtom(logoutUserAtom);
const [queryClient] = useState(
new QueryClient({
queryCache: new QueryCache({
onError: (error) => {
if (error.session_expired) {
logoutUser();
}
toast.error(errorMessage, { toastId: errorMessage });
},
}),
}),
defaultOptions: {
mutations: {
onError: (error) => {
if (error.session_expired) {
logoutUser();
}
},
},
);

return (
<QueryClientProvider client={queryClient}>
<StyledEngineProvider injectFirst>
<ThemeProvider theme={rootTheme}>
<AuthProvider>{children}</AuthProvider>
</ThemeProvider>
</StyledEngineProvider>
<ReactQueryDevtools initialIsOpen={false} />
</QueryClientProvider>
);
};
const AllProviders = ({ children }: { children: ReactNode }) => {
const logoutUser = useSetAtom(logoutUserAtom);
const [queryClient] = useState(
new QueryClient({
queryCache: new QueryCache({
onError: (error) => {
if (error.session_expired) {
logoutUser();
}
toast.error(errorMessage, { toastId: errorMessage });
},
}),
}),
defaultOptions: {
mutations: {
onError: (error) => {
if (error.session_expired) {
logoutUser();
}
},
},
);

return (
<QueryClientProvider client={queryClient}>
<StyledEngineProvider injectFirst>
<ThemeProvider theme={rootTheme}>
<AuthProvider>{children}</AuthProvider>
</ThemeProvider>
</StyledEngineProvider>
<ReactQueryDevtools initialIsOpen={false} />
</QueryClientProvider>
);
};

Did you find this page helpful?