-
Notifications
You must be signed in to change notification settings - Fork 24
/
Copy pathStateProvider.tsx
67 lines (60 loc) · 1.77 KB
/
StateProvider.tsx
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
import {
DehydratedState,
QueryClientProvider,
useQueryClient,
} from '@tanstack/react-query'
import { ReactNode, useEffect, useMemo } from 'react'
import { MutableSnapshot, RecoilRoot, useSetRecoilState } from 'recoil'
import { makeReactQueryClient, queryClientAtom } from '@dao-dao/state'
export type StateProviderProps = {
/**
* Children to render.
*/
children: ReactNode
/**
* Optional dehyrated state from a react-query client instance on the server
* to initialize data.
*/
dehyratedState?: DehydratedState
/**
* Optional RecoilRoot state initializer.
*/
recoilStateInitializer?: (mutableSnapshot: MutableSnapshot) => void
}
/**
* A provider that wraps an app with the state providers, like React Query and
* Recoil.
*/
export const StateProvider = ({
children,
dehyratedState,
recoilStateInitializer,
}: StateProviderProps) => {
const client = useMemo(
() => makeReactQueryClient(dehyratedState),
[dehyratedState]
)
return (
<QueryClientProvider client={client}>
<RecoilRoot
initializeState={(snapshot) => {
// Give query client to Recoil so selectors can access queries.
snapshot.set(queryClientAtom, client)
// Call the recoil root state initializer if provided.
recoilStateInitializer?.(snapshot)
}}
>
<InnerStateProvider>{children}</InnerStateProvider>
</RecoilRoot>
</QueryClientProvider>
)
}
const InnerStateProvider = ({ children }: { children: ReactNode }) => {
const queryClient = useQueryClient()
const setQueryClient = useSetRecoilState(queryClientAtom)
// Update Recoil atom when the query client changes.
useEffect(() => {
setQueryClient(queryClient)
}, [queryClient, setQueryClient])
return <>{children} </>
}