@tanstack/react-query 4.0.5
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/build/cjs/query-core/build/esm/index.js +3110 -0
- package/build/cjs/query-core/build/esm/index.js.map +1 -0
- package/build/cjs/react-query/src/Hydrate.js +66 -0
- package/build/cjs/react-query/src/Hydrate.js.map +1 -0
- package/build/cjs/react-query/src/QueryClientProvider.js +96 -0
- package/build/cjs/react-query/src/QueryClientProvider.js.map +1 -0
- package/build/cjs/react-query/src/QueryErrorResetBoundary.js +67 -0
- package/build/cjs/react-query/src/QueryErrorResetBoundary.js.map +1 -0
- package/build/cjs/react-query/src/index.js +64 -0
- package/build/cjs/react-query/src/index.js.map +1 -0
- package/build/cjs/react-query/src/isRestoring.js +43 -0
- package/build/cjs/react-query/src/isRestoring.js.map +1 -0
- package/build/cjs/react-query/src/useBaseQuery.js +117 -0
- package/build/cjs/react-query/src/useBaseQuery.js.map +1 -0
- package/build/cjs/react-query/src/useInfiniteQuery.js +24 -0
- package/build/cjs/react-query/src/useInfiniteQuery.js.map +1 -0
- package/build/cjs/react-query/src/useIsFetching.js +50 -0
- package/build/cjs/react-query/src/useIsFetching.js.map +1 -0
- package/build/cjs/react-query/src/useIsMutating.js +50 -0
- package/build/cjs/react-query/src/useIsMutating.js.map +1 -0
- package/build/cjs/react-query/src/useMutation.js +68 -0
- package/build/cjs/react-query/src/useMutation.js.map +1 -0
- package/build/cjs/react-query/src/useQueries.js +71 -0
- package/build/cjs/react-query/src/useQueries.js.map +1 -0
- package/build/cjs/react-query/src/useQuery.js +24 -0
- package/build/cjs/react-query/src/useQuery.js.map +1 -0
- package/build/cjs/react-query/src/utils.js +25 -0
- package/build/cjs/react-query/src/utils.js.map +1 -0
- package/build/esm/index.js +3368 -0
- package/build/esm/index.js.map +1 -0
- package/build/stats-html.html +2689 -0
- package/build/stats.json +666 -0
- package/build/types/packages/query-core/src/focusManager.d.ts +16 -0
- package/build/types/packages/query-core/src/hydration.d.ts +34 -0
- package/build/types/packages/query-core/src/index.d.ts +20 -0
- package/build/types/packages/query-core/src/infiniteQueryBehavior.d.ts +15 -0
- package/build/types/packages/query-core/src/infiniteQueryObserver.d.ts +18 -0
- package/build/types/packages/query-core/src/logger.d.ts +8 -0
- package/build/types/packages/query-core/src/mutation.d.ts +70 -0
- package/build/types/packages/query-core/src/mutationCache.d.ts +52 -0
- package/build/types/packages/query-core/src/mutationObserver.d.ts +23 -0
- package/build/types/packages/query-core/src/notifyManager.d.ts +18 -0
- package/build/types/packages/query-core/src/onlineManager.d.ts +16 -0
- package/build/types/packages/query-core/src/queriesObserver.d.ts +23 -0
- package/build/types/packages/query-core/src/query.d.ts +119 -0
- package/build/types/packages/query-core/src/queryCache.d.ts +59 -0
- package/build/types/packages/query-core/src/queryClient.d.ts +65 -0
- package/build/types/packages/query-core/src/queryObserver.d.ts +61 -0
- package/build/types/packages/query-core/src/removable.d.ts +9 -0
- package/build/types/packages/query-core/src/retryer.d.ts +33 -0
- package/build/types/packages/query-core/src/subscribable.d.ts +10 -0
- package/build/types/packages/query-core/src/types.d.ts +417 -0
- package/build/types/packages/query-core/src/utils.d.ts +99 -0
- package/build/types/packages/react-query/src/Hydrate.d.ts +10 -0
- package/build/types/packages/react-query/src/QueryClientProvider.d.ts +24 -0
- package/build/types/packages/react-query/src/QueryErrorResetBoundary.d.ts +12 -0
- package/build/types/packages/react-query/src/__tests__/Hydrate.test.d.ts +1 -0
- package/build/types/packages/react-query/src/__tests__/QueryClientProvider.test.d.ts +1 -0
- package/build/types/packages/react-query/src/__tests__/QueryResetErrorBoundary.test.d.ts +6 -0
- package/build/types/packages/react-query/src/__tests__/ssr-hydration.test.d.ts +1 -0
- package/build/types/packages/react-query/src/__tests__/ssr.test.d.ts +4 -0
- package/build/types/packages/react-query/src/__tests__/suspense.test.d.ts +1 -0
- package/build/types/packages/react-query/src/__tests__/useInfiniteQuery.test.d.ts +1 -0
- package/build/types/packages/react-query/src/__tests__/useIsFetching.test.d.ts +1 -0
- package/build/types/packages/react-query/src/__tests__/useIsMutating.test.d.ts +1 -0
- package/build/types/packages/react-query/src/__tests__/useMutation.test.d.ts +1 -0
- package/build/types/packages/react-query/src/__tests__/useQueries.test.d.ts +1 -0
- package/build/types/packages/react-query/src/__tests__/useQuery.test.d.ts +1 -0
- package/build/types/packages/react-query/src/__tests__/useQuery.types.test.d.ts +2 -0
- package/build/types/packages/react-query/src/__tests__/utils.d.ts +8 -0
- package/build/types/packages/react-query/src/index.d.ts +17 -0
- package/build/types/packages/react-query/src/isRestoring.d.ts +3 -0
- package/build/types/packages/react-query/src/reactBatchedUpdates.d.ts +2 -0
- package/build/types/packages/react-query/src/reactBatchedUpdates.native.d.ts +2 -0
- package/build/types/packages/react-query/src/setBatchUpdatesFn.d.ts +1 -0
- package/build/types/packages/react-query/src/types.d.ts +35 -0
- package/build/types/packages/react-query/src/useBaseQuery.d.ts +3 -0
- package/build/types/packages/react-query/src/useInfiniteQuery.d.ts +5 -0
- package/build/types/packages/react-query/src/useIsFetching.d.ts +7 -0
- package/build/types/packages/react-query/src/useIsMutating.d.ts +7 -0
- package/build/types/packages/react-query/src/useMutation.d.ts +6 -0
- package/build/types/packages/react-query/src/useQueries.d.ts +49 -0
- package/build/types/packages/react-query/src/useQuery.d.ts +20 -0
- package/build/types/packages/react-query/src/utils.d.ts +1 -0
- package/build/types/tests/utils.d.ts +24 -0
- package/build/umd/index.development.js +3429 -0
- package/build/umd/index.development.js.map +1 -0
- package/build/umd/index.production.js +22 -0
- package/build/umd/index.production.js.map +1 -0
- package/codemods/v4/key-transformation.js +138 -0
- package/codemods/v4/replace-import-specifier.js +25 -0
- package/codemods/v4/utils/index.js +166 -0
- package/codemods/v4/utils/replacers/key-replacer.js +160 -0
- package/codemods/v4/utils/transformers/query-cache-transformer.js +115 -0
- package/codemods/v4/utils/transformers/query-client-transformer.js +49 -0
- package/codemods/v4/utils/transformers/use-query-like-transformer.js +32 -0
- package/codemods/v4/utils/unprocessable-key-error.js +8 -0
- package/package.json +63 -0
- package/src/Hydrate.tsx +36 -0
- package/src/QueryClientProvider.tsx +90 -0
- package/src/QueryErrorResetBoundary.tsx +52 -0
- package/src/__tests__/Hydrate.test.tsx +247 -0
- package/src/__tests__/QueryClientProvider.test.tsx +275 -0
- package/src/__tests__/QueryResetErrorBoundary.test.tsx +630 -0
- package/src/__tests__/ssr-hydration.test.tsx +274 -0
- package/src/__tests__/ssr.test.tsx +151 -0
- package/src/__tests__/suspense.test.tsx +1015 -0
- package/src/__tests__/useInfiniteQuery.test.tsx +1773 -0
- package/src/__tests__/useIsFetching.test.tsx +274 -0
- package/src/__tests__/useIsMutating.test.tsx +260 -0
- package/src/__tests__/useMutation.test.tsx +1099 -0
- package/src/__tests__/useQueries.test.tsx +1107 -0
- package/src/__tests__/useQuery.test.tsx +5746 -0
- package/src/__tests__/useQuery.types.test.tsx +157 -0
- package/src/__tests__/utils.tsx +45 -0
- package/src/index.ts +29 -0
- package/src/isRestoring.tsx +6 -0
- package/src/reactBatchedUpdates.native.ts +4 -0
- package/src/reactBatchedUpdates.ts +2 -0
- package/src/setBatchUpdatesFn.ts +4 -0
- package/src/types.ts +122 -0
- package/src/useBaseQuery.ts +140 -0
- package/src/useInfiniteQuery.ts +101 -0
- package/src/useIsFetching.ts +39 -0
- package/src/useIsMutating.ts +43 -0
- package/src/useMutation.ts +126 -0
- package/src/useQueries.ts +192 -0
- package/src/useQuery.ts +104 -0
- package/src/utils.ts +11 -0
package/package.json
ADDED
|
@@ -0,0 +1,63 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "@tanstack/react-query",
|
|
3
|
+
"version": "4.0.5",
|
|
4
|
+
"description": "Hooks for managing, caching and syncing asynchronous and remote data in React",
|
|
5
|
+
"author": "tannerlinsley",
|
|
6
|
+
"license": "MIT",
|
|
7
|
+
"repository": "tanstack/query",
|
|
8
|
+
"homepage": "https://tanstack.com/query",
|
|
9
|
+
"funding": {
|
|
10
|
+
"type": "github",
|
|
11
|
+
"url": "https://github.com/sponsors/tannerlinsley"
|
|
12
|
+
},
|
|
13
|
+
"module": "build/esm/index.js",
|
|
14
|
+
"main": "build/cjs/react-query/src/index.js",
|
|
15
|
+
"browser": "build/umd/index.production.js",
|
|
16
|
+
"types": "build/types/packages/react-query/src/index.d.ts",
|
|
17
|
+
"sideEffects": [
|
|
18
|
+
"lib/index.js",
|
|
19
|
+
"lib/index.mjs",
|
|
20
|
+
"lib/reactjs/index.js",
|
|
21
|
+
"lib/reactjs/index.mjs",
|
|
22
|
+
"lib/reactjs/setBatchUpdatesFn.js",
|
|
23
|
+
"lib/reactjs/setBatchUpdatesFn.mjs"
|
|
24
|
+
],
|
|
25
|
+
"scripts": {
|
|
26
|
+
"test:codemods": "../../node_modules/.bin/jest --config codemods/jest.config.js",
|
|
27
|
+
"test:eslint": "../../node_modules/.bin/eslint --ext .ts,.tsx ./src",
|
|
28
|
+
"test:jest": "yarn test:codemods && ../../node_modules/.bin/jest --config jest.config.js",
|
|
29
|
+
"test:jest:dev": "yarn test:jest --watch",
|
|
30
|
+
"compile": "../../node_modules/.bin/tsc -p tsconfig.json --noEmit --emitDeclarationOnly false"
|
|
31
|
+
},
|
|
32
|
+
"files": [
|
|
33
|
+
"build/*",
|
|
34
|
+
"src",
|
|
35
|
+
"codemods",
|
|
36
|
+
"!codemods/jest.config.js",
|
|
37
|
+
"!codemods/**/__testfixtures__",
|
|
38
|
+
"!codemods/**/__tests__"
|
|
39
|
+
],
|
|
40
|
+
"devDependencies": {
|
|
41
|
+
"@types/jscodeshift": "^0.11.3",
|
|
42
|
+
"jscodeshift": "^0.13.1",
|
|
43
|
+
"react-error-boundary": "^3.1.4"
|
|
44
|
+
},
|
|
45
|
+
"dependencies": {
|
|
46
|
+
"@tanstack/query-core": "^4.0.0-beta.1",
|
|
47
|
+
"@types/use-sync-external-store": "^0.0.3",
|
|
48
|
+
"use-sync-external-store": "^1.2.0"
|
|
49
|
+
},
|
|
50
|
+
"peerDependencies": {
|
|
51
|
+
"react": "^16.8.0 || ^17.0.0 || ^18.0.0",
|
|
52
|
+
"react-dom": "^16.8.0 || ^17.0.0 || ^18.0.0",
|
|
53
|
+
"react-native": "*"
|
|
54
|
+
},
|
|
55
|
+
"peerDependenciesMeta": {
|
|
56
|
+
"react-dom": {
|
|
57
|
+
"optional": true
|
|
58
|
+
},
|
|
59
|
+
"react-native": {
|
|
60
|
+
"optional": true
|
|
61
|
+
}
|
|
62
|
+
}
|
|
63
|
+
}
|
package/src/Hydrate.tsx
ADDED
|
@@ -0,0 +1,36 @@
|
|
|
1
|
+
import * as React from 'react'
|
|
2
|
+
|
|
3
|
+
import { hydrate, HydrateOptions } from '@tanstack/query-core'
|
|
4
|
+
import { useQueryClient } from './QueryClientProvider'
|
|
5
|
+
import { ContextOptions } from './types'
|
|
6
|
+
|
|
7
|
+
export function useHydrate(
|
|
8
|
+
state: unknown,
|
|
9
|
+
options: HydrateOptions & ContextOptions = {},
|
|
10
|
+
) {
|
|
11
|
+
const queryClient = useQueryClient({ context: options.context })
|
|
12
|
+
|
|
13
|
+
const optionsRef = React.useRef(options)
|
|
14
|
+
optionsRef.current = options
|
|
15
|
+
|
|
16
|
+
// Running hydrate again with the same queries is safe,
|
|
17
|
+
// it wont overwrite or initialize existing queries,
|
|
18
|
+
// relying on useMemo here is only a performance optimization.
|
|
19
|
+
// hydrate can and should be run *during* render here for SSR to work properly
|
|
20
|
+
React.useMemo(() => {
|
|
21
|
+
if (state) {
|
|
22
|
+
hydrate(queryClient, state, optionsRef.current)
|
|
23
|
+
}
|
|
24
|
+
}, [queryClient, state])
|
|
25
|
+
}
|
|
26
|
+
|
|
27
|
+
export interface HydrateProps {
|
|
28
|
+
state?: unknown
|
|
29
|
+
options?: HydrateOptions
|
|
30
|
+
children?: React.ReactNode
|
|
31
|
+
}
|
|
32
|
+
|
|
33
|
+
export const Hydrate = ({ children, options, state }: HydrateProps) => {
|
|
34
|
+
useHydrate(state, options)
|
|
35
|
+
return children as React.ReactElement
|
|
36
|
+
}
|
|
@@ -0,0 +1,90 @@
|
|
|
1
|
+
import * as React from 'react'
|
|
2
|
+
|
|
3
|
+
import { QueryClient } from '@tanstack/query-core'
|
|
4
|
+
import { ContextOptions } from './types'
|
|
5
|
+
|
|
6
|
+
declare global {
|
|
7
|
+
interface Window {
|
|
8
|
+
ReactQueryClientContext?: React.Context<QueryClient | undefined>
|
|
9
|
+
}
|
|
10
|
+
}
|
|
11
|
+
|
|
12
|
+
export const defaultContext = React.createContext<QueryClient | undefined>(
|
|
13
|
+
undefined,
|
|
14
|
+
)
|
|
15
|
+
const QueryClientSharingContext = React.createContext<boolean>(false)
|
|
16
|
+
|
|
17
|
+
// If we are given a context, we will use it.
|
|
18
|
+
// Otherwise, if contextSharing is on, we share the first and at least one
|
|
19
|
+
// instance of the context across the window
|
|
20
|
+
// to ensure that if React Query is used across
|
|
21
|
+
// different bundles or microfrontends they will
|
|
22
|
+
// all use the same **instance** of context, regardless
|
|
23
|
+
// of module scoping.
|
|
24
|
+
function getQueryClientContext(
|
|
25
|
+
context: React.Context<QueryClient | undefined> | undefined,
|
|
26
|
+
contextSharing: boolean,
|
|
27
|
+
) {
|
|
28
|
+
if (context) {
|
|
29
|
+
return context
|
|
30
|
+
}
|
|
31
|
+
if (contextSharing && typeof window !== 'undefined') {
|
|
32
|
+
if (!window.ReactQueryClientContext) {
|
|
33
|
+
window.ReactQueryClientContext = defaultContext
|
|
34
|
+
}
|
|
35
|
+
|
|
36
|
+
return window.ReactQueryClientContext
|
|
37
|
+
}
|
|
38
|
+
|
|
39
|
+
return defaultContext
|
|
40
|
+
}
|
|
41
|
+
|
|
42
|
+
export const useQueryClient = ({ context }: ContextOptions = {}) => {
|
|
43
|
+
const queryClient = React.useContext(
|
|
44
|
+
getQueryClientContext(context, React.useContext(QueryClientSharingContext)),
|
|
45
|
+
)
|
|
46
|
+
|
|
47
|
+
if (!queryClient) {
|
|
48
|
+
throw new Error('No QueryClient set, use QueryClientProvider to set one')
|
|
49
|
+
}
|
|
50
|
+
|
|
51
|
+
return queryClient
|
|
52
|
+
}
|
|
53
|
+
|
|
54
|
+
type QueryClientProviderPropsBase = {
|
|
55
|
+
client: QueryClient
|
|
56
|
+
children?: React.ReactNode
|
|
57
|
+
}
|
|
58
|
+
type QueryClientProviderPropsWithContext = ContextOptions & {
|
|
59
|
+
contextSharing?: never
|
|
60
|
+
} & QueryClientProviderPropsBase
|
|
61
|
+
type QueryClientProviderPropsWithContextSharing = {
|
|
62
|
+
context?: never
|
|
63
|
+
contextSharing?: boolean
|
|
64
|
+
} & QueryClientProviderPropsBase
|
|
65
|
+
|
|
66
|
+
export type QueryClientProviderProps =
|
|
67
|
+
| QueryClientProviderPropsWithContext
|
|
68
|
+
| QueryClientProviderPropsWithContextSharing
|
|
69
|
+
|
|
70
|
+
export const QueryClientProvider = ({
|
|
71
|
+
client,
|
|
72
|
+
children,
|
|
73
|
+
context,
|
|
74
|
+
contextSharing = false,
|
|
75
|
+
}: QueryClientProviderProps): JSX.Element => {
|
|
76
|
+
React.useEffect(() => {
|
|
77
|
+
client.mount()
|
|
78
|
+
return () => {
|
|
79
|
+
client.unmount()
|
|
80
|
+
}
|
|
81
|
+
}, [client])
|
|
82
|
+
|
|
83
|
+
const Context = getQueryClientContext(context, contextSharing)
|
|
84
|
+
|
|
85
|
+
return (
|
|
86
|
+
<QueryClientSharingContext.Provider value={!context && contextSharing}>
|
|
87
|
+
<Context.Provider value={client}>{children}</Context.Provider>
|
|
88
|
+
</QueryClientSharingContext.Provider>
|
|
89
|
+
)
|
|
90
|
+
}
|
|
@@ -0,0 +1,52 @@
|
|
|
1
|
+
import * as React from 'react'
|
|
2
|
+
|
|
3
|
+
// CONTEXT
|
|
4
|
+
|
|
5
|
+
interface QueryErrorResetBoundaryValue {
|
|
6
|
+
clearReset: () => void
|
|
7
|
+
isReset: () => boolean
|
|
8
|
+
reset: () => void
|
|
9
|
+
}
|
|
10
|
+
|
|
11
|
+
function createValue(): QueryErrorResetBoundaryValue {
|
|
12
|
+
let isReset = false
|
|
13
|
+
return {
|
|
14
|
+
clearReset: () => {
|
|
15
|
+
isReset = false
|
|
16
|
+
},
|
|
17
|
+
reset: () => {
|
|
18
|
+
isReset = true
|
|
19
|
+
},
|
|
20
|
+
isReset: () => {
|
|
21
|
+
return isReset
|
|
22
|
+
},
|
|
23
|
+
}
|
|
24
|
+
}
|
|
25
|
+
|
|
26
|
+
const QueryErrorResetBoundaryContext = React.createContext(createValue())
|
|
27
|
+
|
|
28
|
+
// HOOK
|
|
29
|
+
|
|
30
|
+
export const useQueryErrorResetBoundary = () =>
|
|
31
|
+
React.useContext(QueryErrorResetBoundaryContext)
|
|
32
|
+
|
|
33
|
+
// COMPONENT
|
|
34
|
+
|
|
35
|
+
export interface QueryErrorResetBoundaryProps {
|
|
36
|
+
children:
|
|
37
|
+
| ((value: QueryErrorResetBoundaryValue) => React.ReactNode)
|
|
38
|
+
| React.ReactNode
|
|
39
|
+
}
|
|
40
|
+
|
|
41
|
+
export const QueryErrorResetBoundary = ({
|
|
42
|
+
children,
|
|
43
|
+
}: QueryErrorResetBoundaryProps) => {
|
|
44
|
+
const [value] = React.useState(() => createValue())
|
|
45
|
+
return (
|
|
46
|
+
<QueryErrorResetBoundaryContext.Provider value={value}>
|
|
47
|
+
{typeof children === 'function'
|
|
48
|
+
? (children as Function)(value)
|
|
49
|
+
: children}
|
|
50
|
+
</QueryErrorResetBoundaryContext.Provider>
|
|
51
|
+
)
|
|
52
|
+
}
|
|
@@ -0,0 +1,247 @@
|
|
|
1
|
+
import * as React from 'react'
|
|
2
|
+
import { render } from '@testing-library/react'
|
|
3
|
+
|
|
4
|
+
import {
|
|
5
|
+
QueryClient,
|
|
6
|
+
QueryClientProvider,
|
|
7
|
+
QueryCache,
|
|
8
|
+
useQuery,
|
|
9
|
+
dehydrate,
|
|
10
|
+
useHydrate,
|
|
11
|
+
Hydrate,
|
|
12
|
+
} from '@tanstack/react-query'
|
|
13
|
+
import { createQueryClient, sleep } from '../../../../tests/utils'
|
|
14
|
+
import * as coreModule from '@tanstack/query-core'
|
|
15
|
+
|
|
16
|
+
describe('React hydration', () => {
|
|
17
|
+
const fetchData: (value: string) => Promise<string> = (value) =>
|
|
18
|
+
new Promise((res) => setTimeout(() => res(value), 10))
|
|
19
|
+
const dataQuery: (key: [string]) => Promise<string> = (key) =>
|
|
20
|
+
fetchData(key[0])
|
|
21
|
+
let stringifiedState: string
|
|
22
|
+
|
|
23
|
+
beforeAll(async () => {
|
|
24
|
+
const queryCache = new QueryCache()
|
|
25
|
+
const queryClient = createQueryClient({ queryCache })
|
|
26
|
+
await queryClient.prefetchQuery(['string'], () =>
|
|
27
|
+
dataQuery(['stringCached']),
|
|
28
|
+
)
|
|
29
|
+
const dehydrated = dehydrate(queryClient)
|
|
30
|
+
stringifiedState = JSON.stringify(dehydrated)
|
|
31
|
+
queryClient.clear()
|
|
32
|
+
})
|
|
33
|
+
|
|
34
|
+
describe('useHydrate', () => {
|
|
35
|
+
test('should hydrate queries to the cache on context', async () => {
|
|
36
|
+
const dehydratedState = JSON.parse(stringifiedState)
|
|
37
|
+
const queryCache = new QueryCache()
|
|
38
|
+
const queryClient = createQueryClient({ queryCache })
|
|
39
|
+
|
|
40
|
+
function Page() {
|
|
41
|
+
useHydrate(dehydratedState)
|
|
42
|
+
const { data } = useQuery(['string'], () => dataQuery(['string']))
|
|
43
|
+
return (
|
|
44
|
+
<div>
|
|
45
|
+
<h1>{data}</h1>
|
|
46
|
+
</div>
|
|
47
|
+
)
|
|
48
|
+
}
|
|
49
|
+
|
|
50
|
+
const rendered = render(
|
|
51
|
+
<QueryClientProvider client={queryClient}>
|
|
52
|
+
<Page />
|
|
53
|
+
</QueryClientProvider>,
|
|
54
|
+
)
|
|
55
|
+
|
|
56
|
+
await rendered.findByText('stringCached')
|
|
57
|
+
await rendered.findByText('string')
|
|
58
|
+
queryClient.clear()
|
|
59
|
+
})
|
|
60
|
+
|
|
61
|
+
test('should hydrate queries to the cache on custom context', async () => {
|
|
62
|
+
const context = React.createContext<QueryClient | undefined>(undefined)
|
|
63
|
+
|
|
64
|
+
const queryCacheOuter = new QueryCache()
|
|
65
|
+
const queryCacheInner = new QueryCache()
|
|
66
|
+
|
|
67
|
+
const queryClientInner = new QueryClient({ queryCache: queryCacheInner })
|
|
68
|
+
const queryClientOuter = new QueryClient({ queryCache: queryCacheOuter })
|
|
69
|
+
|
|
70
|
+
const dehydratedState = JSON.parse(stringifiedState)
|
|
71
|
+
|
|
72
|
+
function Page() {
|
|
73
|
+
useHydrate(dehydratedState, { context })
|
|
74
|
+
const { data } = useQuery(['string'], () => dataQuery(['string']), {
|
|
75
|
+
context,
|
|
76
|
+
})
|
|
77
|
+
return (
|
|
78
|
+
<div>
|
|
79
|
+
<h1>{data}</h1>
|
|
80
|
+
</div>
|
|
81
|
+
)
|
|
82
|
+
}
|
|
83
|
+
|
|
84
|
+
const rendered = render(
|
|
85
|
+
<QueryClientProvider client={queryClientOuter} context={context}>
|
|
86
|
+
<QueryClientProvider client={queryClientInner}>
|
|
87
|
+
<Page />
|
|
88
|
+
</QueryClientProvider>
|
|
89
|
+
</QueryClientProvider>,
|
|
90
|
+
)
|
|
91
|
+
|
|
92
|
+
await rendered.findByText('stringCached')
|
|
93
|
+
await rendered.findByText('string')
|
|
94
|
+
|
|
95
|
+
queryClientInner.clear()
|
|
96
|
+
queryClientOuter.clear()
|
|
97
|
+
})
|
|
98
|
+
})
|
|
99
|
+
|
|
100
|
+
describe('ReactQueryCacheProvider with hydration support', () => {
|
|
101
|
+
test('should hydrate new queries if queries change', async () => {
|
|
102
|
+
const dehydratedState = JSON.parse(stringifiedState)
|
|
103
|
+
const queryCache = new QueryCache()
|
|
104
|
+
const queryClient = createQueryClient({ queryCache })
|
|
105
|
+
|
|
106
|
+
function Page({ queryKey }: { queryKey: [string] }) {
|
|
107
|
+
const { data } = useQuery(queryKey, () => dataQuery(queryKey))
|
|
108
|
+
return (
|
|
109
|
+
<div>
|
|
110
|
+
<h1>{data}</h1>
|
|
111
|
+
</div>
|
|
112
|
+
)
|
|
113
|
+
}
|
|
114
|
+
|
|
115
|
+
const rendered = render(
|
|
116
|
+
<QueryClientProvider client={queryClient}>
|
|
117
|
+
<Hydrate state={dehydratedState}>
|
|
118
|
+
<Page queryKey={['string']} />
|
|
119
|
+
</Hydrate>
|
|
120
|
+
</QueryClientProvider>,
|
|
121
|
+
)
|
|
122
|
+
|
|
123
|
+
await rendered.findByText('string')
|
|
124
|
+
|
|
125
|
+
const intermediateCache = new QueryCache()
|
|
126
|
+
const intermediateClient = createQueryClient({
|
|
127
|
+
queryCache: intermediateCache,
|
|
128
|
+
})
|
|
129
|
+
await intermediateClient.prefetchQuery(['string'], () =>
|
|
130
|
+
dataQuery(['should change']),
|
|
131
|
+
)
|
|
132
|
+
await intermediateClient.prefetchQuery(['added string'], () =>
|
|
133
|
+
dataQuery(['added string']),
|
|
134
|
+
)
|
|
135
|
+
const dehydrated = dehydrate(intermediateClient)
|
|
136
|
+
intermediateClient.clear()
|
|
137
|
+
|
|
138
|
+
rendered.rerender(
|
|
139
|
+
<QueryClientProvider client={queryClient}>
|
|
140
|
+
<Hydrate state={dehydrated}>
|
|
141
|
+
<Page queryKey={['string']} />
|
|
142
|
+
<Page queryKey={['added string']} />
|
|
143
|
+
</Hydrate>
|
|
144
|
+
</QueryClientProvider>,
|
|
145
|
+
)
|
|
146
|
+
|
|
147
|
+
// Existing query data should be overwritten if older,
|
|
148
|
+
// so this should have changed
|
|
149
|
+
await sleep(10)
|
|
150
|
+
rendered.getByText('should change')
|
|
151
|
+
// New query data should be available immediately
|
|
152
|
+
rendered.getByText('added string')
|
|
153
|
+
|
|
154
|
+
queryClient.clear()
|
|
155
|
+
})
|
|
156
|
+
|
|
157
|
+
test('should hydrate queries to new cache if cache changes', async () => {
|
|
158
|
+
const dehydratedState = JSON.parse(stringifiedState)
|
|
159
|
+
const queryCache = new QueryCache()
|
|
160
|
+
const queryClient = createQueryClient({ queryCache })
|
|
161
|
+
|
|
162
|
+
function Page() {
|
|
163
|
+
const { data } = useQuery(['string'], () => dataQuery(['string']))
|
|
164
|
+
return (
|
|
165
|
+
<div>
|
|
166
|
+
<h1>{data}</h1>
|
|
167
|
+
</div>
|
|
168
|
+
)
|
|
169
|
+
}
|
|
170
|
+
|
|
171
|
+
const rendered = render(
|
|
172
|
+
<QueryClientProvider client={queryClient}>
|
|
173
|
+
<Hydrate state={dehydratedState}>
|
|
174
|
+
<Page />
|
|
175
|
+
</Hydrate>
|
|
176
|
+
</QueryClientProvider>,
|
|
177
|
+
)
|
|
178
|
+
|
|
179
|
+
await rendered.findByText('string')
|
|
180
|
+
|
|
181
|
+
const newClientQueryCache = new QueryCache()
|
|
182
|
+
const newClientQueryClient = createQueryClient({
|
|
183
|
+
queryCache: newClientQueryCache,
|
|
184
|
+
})
|
|
185
|
+
|
|
186
|
+
rendered.rerender(
|
|
187
|
+
<QueryClientProvider client={newClientQueryClient}>
|
|
188
|
+
<Hydrate state={dehydratedState}>
|
|
189
|
+
<Page />
|
|
190
|
+
</Hydrate>
|
|
191
|
+
</QueryClientProvider>,
|
|
192
|
+
)
|
|
193
|
+
|
|
194
|
+
await sleep(10)
|
|
195
|
+
rendered.getByText('string')
|
|
196
|
+
|
|
197
|
+
queryClient.clear()
|
|
198
|
+
newClientQueryClient.clear()
|
|
199
|
+
})
|
|
200
|
+
})
|
|
201
|
+
|
|
202
|
+
test('should not hydrate queries if state is null', async () => {
|
|
203
|
+
const queryCache = new QueryCache()
|
|
204
|
+
const queryClient = createQueryClient({ queryCache })
|
|
205
|
+
|
|
206
|
+
const hydrateSpy = jest.spyOn(coreModule, 'hydrate')
|
|
207
|
+
|
|
208
|
+
function Page() {
|
|
209
|
+
useHydrate(null)
|
|
210
|
+
return null
|
|
211
|
+
}
|
|
212
|
+
|
|
213
|
+
render(
|
|
214
|
+
<QueryClientProvider client={queryClient}>
|
|
215
|
+
<Page />
|
|
216
|
+
</QueryClientProvider>,
|
|
217
|
+
)
|
|
218
|
+
|
|
219
|
+
expect(hydrateSpy).toHaveBeenCalledTimes(0)
|
|
220
|
+
|
|
221
|
+
hydrateSpy.mockRestore()
|
|
222
|
+
queryClient.clear()
|
|
223
|
+
})
|
|
224
|
+
|
|
225
|
+
test('should not hydrate queries if state is undefined', async () => {
|
|
226
|
+
const queryCache = new QueryCache()
|
|
227
|
+
const queryClient = createQueryClient({ queryCache })
|
|
228
|
+
|
|
229
|
+
const hydrateSpy = jest.spyOn(coreModule, 'hydrate')
|
|
230
|
+
|
|
231
|
+
function Page() {
|
|
232
|
+
useHydrate(undefined)
|
|
233
|
+
return null
|
|
234
|
+
}
|
|
235
|
+
|
|
236
|
+
render(
|
|
237
|
+
<QueryClientProvider client={queryClient}>
|
|
238
|
+
<Page />
|
|
239
|
+
</QueryClientProvider>,
|
|
240
|
+
)
|
|
241
|
+
|
|
242
|
+
expect(hydrateSpy).toHaveBeenCalledTimes(0)
|
|
243
|
+
|
|
244
|
+
hydrateSpy.mockRestore()
|
|
245
|
+
queryClient.clear()
|
|
246
|
+
})
|
|
247
|
+
})
|