@tanstack/react-query 4.29.2 → 4.29.3
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/lib/useQueries.esm.js +6 -6
- package/build/lib/useQueries.esm.js.map +1 -1
- package/build/lib/useQueries.js +6 -6
- package/build/lib/useQueries.js.map +1 -1
- package/build/lib/useQueries.mjs +6 -6
- package/build/lib/useQueries.mjs.map +1 -1
- package/build/umd/index.development.js +6 -6
- package/build/umd/index.development.js.map +1 -1
- package/build/umd/index.production.js +1 -1
- package/build/umd/index.production.js.map +1 -1
- package/package.json +1 -1
- package/src/__tests__/QueryResetErrorBoundary.test.tsx +683 -562
- package/src/useQueries.ts +8 -9
|
@@ -3,7 +3,7 @@ import { ErrorBoundary } from 'react-error-boundary'
|
|
|
3
3
|
import * as React from 'react'
|
|
4
4
|
|
|
5
5
|
import { createQueryClient, queryKey, renderWithClient, sleep } from './utils'
|
|
6
|
-
import { QueryCache, QueryErrorResetBoundary, useQuery } from '..'
|
|
6
|
+
import { QueryCache, QueryErrorResetBoundary, useQueries, useQuery } from '..'
|
|
7
7
|
|
|
8
8
|
// TODO: This should be removed with the types for react-error-boundary get updated.
|
|
9
9
|
declare module 'react-error-boundary' {
|
|
@@ -16,368 +16,628 @@ describe('QueryErrorResetBoundary', () => {
|
|
|
16
16
|
const queryCache = new QueryCache()
|
|
17
17
|
const queryClient = createQueryClient({ queryCache })
|
|
18
18
|
|
|
19
|
-
|
|
20
|
-
|
|
19
|
+
describe('useQuery', () => {
|
|
20
|
+
it('should retry fetch if the reset error boundary has been reset', async () => {
|
|
21
|
+
const key = queryKey()
|
|
22
|
+
|
|
23
|
+
let succeed = false
|
|
24
|
+
|
|
25
|
+
function Page() {
|
|
26
|
+
const { data } = useQuery(
|
|
27
|
+
key,
|
|
28
|
+
async () => {
|
|
29
|
+
await sleep(10)
|
|
30
|
+
if (!succeed) {
|
|
31
|
+
throw new Error('Error')
|
|
32
|
+
} else {
|
|
33
|
+
return 'data'
|
|
34
|
+
}
|
|
35
|
+
},
|
|
36
|
+
{
|
|
37
|
+
retry: false,
|
|
38
|
+
useErrorBoundary: true,
|
|
39
|
+
},
|
|
40
|
+
)
|
|
41
|
+
return <div>{data}</div>
|
|
42
|
+
}
|
|
43
|
+
|
|
44
|
+
const rendered = renderWithClient(
|
|
45
|
+
queryClient,
|
|
46
|
+
<QueryErrorResetBoundary>
|
|
47
|
+
{({ reset }) => (
|
|
48
|
+
<ErrorBoundary
|
|
49
|
+
onReset={reset}
|
|
50
|
+
fallbackRender={({ resetErrorBoundary }) => (
|
|
51
|
+
<div>
|
|
52
|
+
<div>error boundary</div>
|
|
53
|
+
<button
|
|
54
|
+
onClick={() => {
|
|
55
|
+
resetErrorBoundary()
|
|
56
|
+
}}
|
|
57
|
+
>
|
|
58
|
+
retry
|
|
59
|
+
</button>
|
|
60
|
+
</div>
|
|
61
|
+
)}
|
|
62
|
+
>
|
|
63
|
+
<Page />
|
|
64
|
+
</ErrorBoundary>
|
|
65
|
+
)}
|
|
66
|
+
</QueryErrorResetBoundary>,
|
|
67
|
+
)
|
|
21
68
|
|
|
22
|
-
|
|
69
|
+
await waitFor(() => rendered.getByText('error boundary'))
|
|
70
|
+
await waitFor(() => rendered.getByText('retry'))
|
|
71
|
+
succeed = true
|
|
72
|
+
fireEvent.click(rendered.getByText('retry'))
|
|
73
|
+
await waitFor(() => rendered.getByText('data'))
|
|
74
|
+
})
|
|
75
|
+
|
|
76
|
+
it('should not throw error if query is disabled', async () => {
|
|
77
|
+
const key = queryKey()
|
|
78
|
+
|
|
79
|
+
let succeed = false
|
|
80
|
+
|
|
81
|
+
function Page() {
|
|
82
|
+
const { data, status } = useQuery(
|
|
83
|
+
key,
|
|
84
|
+
async () => {
|
|
85
|
+
await sleep(10)
|
|
86
|
+
if (!succeed) {
|
|
87
|
+
throw new Error('Error')
|
|
88
|
+
} else {
|
|
89
|
+
return 'data'
|
|
90
|
+
}
|
|
91
|
+
},
|
|
92
|
+
{
|
|
93
|
+
retry: false,
|
|
94
|
+
enabled: !succeed,
|
|
95
|
+
useErrorBoundary: true,
|
|
96
|
+
},
|
|
97
|
+
)
|
|
98
|
+
return (
|
|
99
|
+
<div>
|
|
100
|
+
<div>status: {status}</div>
|
|
101
|
+
<div>{data}</div>
|
|
102
|
+
</div>
|
|
103
|
+
)
|
|
104
|
+
}
|
|
105
|
+
|
|
106
|
+
const rendered = renderWithClient(
|
|
107
|
+
queryClient,
|
|
108
|
+
<QueryErrorResetBoundary>
|
|
109
|
+
{({ reset }) => (
|
|
110
|
+
<ErrorBoundary
|
|
111
|
+
onReset={reset}
|
|
112
|
+
fallbackRender={({ resetErrorBoundary }) => (
|
|
113
|
+
<div>
|
|
114
|
+
<div>error boundary</div>
|
|
115
|
+
<button
|
|
116
|
+
onClick={() => {
|
|
117
|
+
resetErrorBoundary()
|
|
118
|
+
}}
|
|
119
|
+
>
|
|
120
|
+
retry
|
|
121
|
+
</button>
|
|
122
|
+
</div>
|
|
123
|
+
)}
|
|
124
|
+
>
|
|
125
|
+
<Page />
|
|
126
|
+
</ErrorBoundary>
|
|
127
|
+
)}
|
|
128
|
+
</QueryErrorResetBoundary>,
|
|
129
|
+
)
|
|
23
130
|
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
}
|
|
131
|
+
await waitFor(() => rendered.getByText('error boundary'))
|
|
132
|
+
await waitFor(() => rendered.getByText('retry'))
|
|
133
|
+
succeed = true
|
|
134
|
+
fireEvent.click(rendered.getByText('retry'))
|
|
135
|
+
await waitFor(() => rendered.getByText('status: error'))
|
|
136
|
+
})
|
|
137
|
+
|
|
138
|
+
it('should not throw error if query is disabled, and refetch if query becomes enabled again', async () => {
|
|
139
|
+
const key = queryKey()
|
|
140
|
+
|
|
141
|
+
let succeed = false
|
|
142
|
+
|
|
143
|
+
function Page() {
|
|
144
|
+
const [enabled, setEnabled] = React.useState(false)
|
|
145
|
+
const { data } = useQuery(
|
|
146
|
+
key,
|
|
147
|
+
async () => {
|
|
148
|
+
await sleep(10)
|
|
149
|
+
if (!succeed) {
|
|
150
|
+
throw new Error('Error')
|
|
151
|
+
} else {
|
|
152
|
+
return 'data'
|
|
153
|
+
}
|
|
154
|
+
},
|
|
155
|
+
{
|
|
156
|
+
retry: false,
|
|
157
|
+
enabled,
|
|
158
|
+
useErrorBoundary: true,
|
|
159
|
+
},
|
|
160
|
+
)
|
|
161
|
+
|
|
162
|
+
React.useEffect(() => {
|
|
163
|
+
setEnabled(true)
|
|
164
|
+
}, [])
|
|
165
|
+
|
|
166
|
+
return <div>{data}</div>
|
|
167
|
+
}
|
|
168
|
+
|
|
169
|
+
const rendered = renderWithClient(
|
|
170
|
+
queryClient,
|
|
171
|
+
<QueryErrorResetBoundary>
|
|
172
|
+
{({ reset }) => (
|
|
173
|
+
<ErrorBoundary
|
|
174
|
+
onReset={reset}
|
|
175
|
+
fallbackRender={({ resetErrorBoundary }) => (
|
|
176
|
+
<div>
|
|
177
|
+
<div>error boundary</div>
|
|
178
|
+
<button
|
|
179
|
+
onClick={() => {
|
|
180
|
+
resetErrorBoundary()
|
|
181
|
+
}}
|
|
182
|
+
>
|
|
183
|
+
retry
|
|
184
|
+
</button>
|
|
185
|
+
</div>
|
|
186
|
+
)}
|
|
187
|
+
>
|
|
188
|
+
<Page />
|
|
189
|
+
</ErrorBoundary>
|
|
190
|
+
)}
|
|
191
|
+
</QueryErrorResetBoundary>,
|
|
39
192
|
)
|
|
40
|
-
return <div>{data}</div>
|
|
41
|
-
}
|
|
42
|
-
|
|
43
|
-
const rendered = renderWithClient(
|
|
44
|
-
queryClient,
|
|
45
|
-
<QueryErrorResetBoundary>
|
|
46
|
-
{({ reset }) => (
|
|
47
|
-
<ErrorBoundary
|
|
48
|
-
onReset={reset}
|
|
49
|
-
fallbackRender={({ resetErrorBoundary }) => (
|
|
50
|
-
<div>
|
|
51
|
-
<div>error boundary</div>
|
|
52
|
-
<button
|
|
53
|
-
onClick={() => {
|
|
54
|
-
resetErrorBoundary()
|
|
55
|
-
}}
|
|
56
|
-
>
|
|
57
|
-
retry
|
|
58
|
-
</button>
|
|
59
|
-
</div>
|
|
60
|
-
)}
|
|
61
|
-
>
|
|
62
|
-
<Page />
|
|
63
|
-
</ErrorBoundary>
|
|
64
|
-
)}
|
|
65
|
-
</QueryErrorResetBoundary>,
|
|
66
|
-
)
|
|
67
|
-
|
|
68
|
-
await waitFor(() => rendered.getByText('error boundary'))
|
|
69
|
-
await waitFor(() => rendered.getByText('retry'))
|
|
70
|
-
succeed = true
|
|
71
|
-
fireEvent.click(rendered.getByText('retry'))
|
|
72
|
-
await waitFor(() => rendered.getByText('data'))
|
|
73
|
-
})
|
|
74
193
|
|
|
75
|
-
|
|
76
|
-
|
|
194
|
+
await waitFor(() => rendered.getByText('error boundary'))
|
|
195
|
+
await waitFor(() => rendered.getByText('retry'))
|
|
196
|
+
succeed = true
|
|
197
|
+
fireEvent.click(rendered.getByText('retry'))
|
|
198
|
+
await waitFor(() => rendered.getByText('data'))
|
|
199
|
+
})
|
|
77
200
|
|
|
78
|
-
|
|
201
|
+
it('should throw error if query is disabled and manually refetched', async () => {
|
|
202
|
+
const key = queryKey()
|
|
79
203
|
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
await sleep(10)
|
|
85
|
-
if (!succeed) {
|
|
204
|
+
function Page() {
|
|
205
|
+
const { data, refetch, status, fetchStatus } = useQuery<string>(
|
|
206
|
+
key,
|
|
207
|
+
async () => {
|
|
86
208
|
throw new Error('Error')
|
|
87
|
-
}
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
|
|
209
|
+
},
|
|
210
|
+
{
|
|
211
|
+
retry: false,
|
|
212
|
+
enabled: false,
|
|
213
|
+
useErrorBoundary: true,
|
|
214
|
+
},
|
|
215
|
+
)
|
|
216
|
+
|
|
217
|
+
return (
|
|
218
|
+
<div>
|
|
219
|
+
<button onClick={() => refetch()}>refetch</button>
|
|
220
|
+
<div>
|
|
221
|
+
status: {status}, fetchStatus: {fetchStatus}
|
|
222
|
+
</div>
|
|
223
|
+
<div>{data}</div>
|
|
224
|
+
</div>
|
|
225
|
+
)
|
|
226
|
+
}
|
|
227
|
+
|
|
228
|
+
const rendered = renderWithClient(
|
|
229
|
+
queryClient,
|
|
230
|
+
<QueryErrorResetBoundary>
|
|
231
|
+
{({ reset }) => (
|
|
232
|
+
<ErrorBoundary
|
|
233
|
+
onReset={reset}
|
|
234
|
+
fallbackRender={({ resetErrorBoundary }) => (
|
|
235
|
+
<div>
|
|
236
|
+
<div>error boundary</div>
|
|
237
|
+
<button
|
|
238
|
+
onClick={() => {
|
|
239
|
+
resetErrorBoundary()
|
|
240
|
+
}}
|
|
241
|
+
>
|
|
242
|
+
retry
|
|
243
|
+
</button>
|
|
244
|
+
</div>
|
|
245
|
+
)}
|
|
246
|
+
>
|
|
247
|
+
<Page />
|
|
248
|
+
</ErrorBoundary>
|
|
249
|
+
)}
|
|
250
|
+
</QueryErrorResetBoundary>,
|
|
96
251
|
)
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
252
|
+
|
|
253
|
+
await waitFor(() =>
|
|
254
|
+
rendered.getByText('status: loading, fetchStatus: idle'),
|
|
255
|
+
)
|
|
256
|
+
fireEvent.click(rendered.getByRole('button', { name: /refetch/i }))
|
|
257
|
+
await waitFor(() => rendered.getByText('error boundary'))
|
|
258
|
+
})
|
|
259
|
+
|
|
260
|
+
it('should not retry fetch if the reset error boundary has not been reset', async () => {
|
|
261
|
+
const key = queryKey()
|
|
262
|
+
|
|
263
|
+
let succeed = false
|
|
264
|
+
|
|
265
|
+
function Page() {
|
|
266
|
+
const { data } = useQuery(
|
|
267
|
+
key,
|
|
268
|
+
async () => {
|
|
269
|
+
await sleep(10)
|
|
270
|
+
if (!succeed) {
|
|
271
|
+
throw new Error('Error')
|
|
272
|
+
} else {
|
|
273
|
+
return 'data'
|
|
274
|
+
}
|
|
275
|
+
},
|
|
276
|
+
{
|
|
277
|
+
retry: false,
|
|
278
|
+
useErrorBoundary: true,
|
|
279
|
+
},
|
|
280
|
+
)
|
|
281
|
+
return <div>{data}</div>
|
|
282
|
+
}
|
|
283
|
+
|
|
284
|
+
const rendered = renderWithClient(
|
|
285
|
+
queryClient,
|
|
286
|
+
<QueryErrorResetBoundary>
|
|
287
|
+
{() => (
|
|
288
|
+
<ErrorBoundary
|
|
289
|
+
fallbackRender={({ resetErrorBoundary }) => (
|
|
290
|
+
<div>
|
|
291
|
+
<div>error boundary</div>
|
|
292
|
+
<button
|
|
293
|
+
onClick={() => {
|
|
294
|
+
resetErrorBoundary()
|
|
295
|
+
}}
|
|
296
|
+
>
|
|
297
|
+
retry
|
|
298
|
+
</button>
|
|
299
|
+
</div>
|
|
300
|
+
)}
|
|
301
|
+
>
|
|
302
|
+
<Page />
|
|
303
|
+
</ErrorBoundary>
|
|
304
|
+
)}
|
|
305
|
+
</QueryErrorResetBoundary>,
|
|
102
306
|
)
|
|
103
|
-
}
|
|
104
|
-
|
|
105
|
-
const rendered = renderWithClient(
|
|
106
|
-
queryClient,
|
|
107
|
-
<QueryErrorResetBoundary>
|
|
108
|
-
{({ reset }) => (
|
|
109
|
-
<ErrorBoundary
|
|
110
|
-
onReset={reset}
|
|
111
|
-
fallbackRender={({ resetErrorBoundary }) => (
|
|
112
|
-
<div>
|
|
113
|
-
<div>error boundary</div>
|
|
114
|
-
<button
|
|
115
|
-
onClick={() => {
|
|
116
|
-
resetErrorBoundary()
|
|
117
|
-
}}
|
|
118
|
-
>
|
|
119
|
-
retry
|
|
120
|
-
</button>
|
|
121
|
-
</div>
|
|
122
|
-
)}
|
|
123
|
-
>
|
|
124
|
-
<Page />
|
|
125
|
-
</ErrorBoundary>
|
|
126
|
-
)}
|
|
127
|
-
</QueryErrorResetBoundary>,
|
|
128
|
-
)
|
|
129
|
-
|
|
130
|
-
await waitFor(() => rendered.getByText('error boundary'))
|
|
131
|
-
await waitFor(() => rendered.getByText('retry'))
|
|
132
|
-
succeed = true
|
|
133
|
-
fireEvent.click(rendered.getByText('retry'))
|
|
134
|
-
await waitFor(() => rendered.getByText('status: error'))
|
|
135
|
-
})
|
|
136
307
|
|
|
137
|
-
|
|
138
|
-
|
|
308
|
+
await waitFor(() => rendered.getByText('error boundary'))
|
|
309
|
+
await waitFor(() => rendered.getByText('retry'))
|
|
310
|
+
succeed = true
|
|
311
|
+
fireEvent.click(rendered.getByText('retry'))
|
|
312
|
+
await waitFor(() => rendered.getByText('error boundary'))
|
|
313
|
+
})
|
|
314
|
+
|
|
315
|
+
it('should retry fetch if the reset error boundary has been reset and the query contains data from a previous fetch', async () => {
|
|
316
|
+
const key = queryKey()
|
|
317
|
+
|
|
318
|
+
let succeed = false
|
|
319
|
+
|
|
320
|
+
function Page() {
|
|
321
|
+
const { data } = useQuery(
|
|
322
|
+
key,
|
|
323
|
+
async () => {
|
|
324
|
+
await sleep(10)
|
|
325
|
+
if (!succeed) {
|
|
326
|
+
throw new Error('Error')
|
|
327
|
+
} else {
|
|
328
|
+
return 'data'
|
|
329
|
+
}
|
|
330
|
+
},
|
|
331
|
+
{
|
|
332
|
+
retry: false,
|
|
333
|
+
useErrorBoundary: true,
|
|
334
|
+
initialData: 'initial',
|
|
335
|
+
},
|
|
336
|
+
)
|
|
337
|
+
return <div>{data}</div>
|
|
338
|
+
}
|
|
339
|
+
|
|
340
|
+
const rendered = renderWithClient(
|
|
341
|
+
queryClient,
|
|
342
|
+
<QueryErrorResetBoundary>
|
|
343
|
+
{({ reset }) => (
|
|
344
|
+
<ErrorBoundary
|
|
345
|
+
onReset={reset}
|
|
346
|
+
fallbackRender={({ resetErrorBoundary }) => (
|
|
347
|
+
<div>
|
|
348
|
+
<div>error boundary</div>
|
|
349
|
+
<button
|
|
350
|
+
onClick={() => {
|
|
351
|
+
resetErrorBoundary()
|
|
352
|
+
}}
|
|
353
|
+
>
|
|
354
|
+
retry
|
|
355
|
+
</button>
|
|
356
|
+
</div>
|
|
357
|
+
)}
|
|
358
|
+
>
|
|
359
|
+
<Page />
|
|
360
|
+
</ErrorBoundary>
|
|
361
|
+
)}
|
|
362
|
+
</QueryErrorResetBoundary>,
|
|
363
|
+
)
|
|
139
364
|
|
|
140
|
-
|
|
365
|
+
await waitFor(() => rendered.getByText('error boundary'))
|
|
366
|
+
await waitFor(() => rendered.getByText('retry'))
|
|
367
|
+
succeed = true
|
|
368
|
+
fireEvent.click(rendered.getByText('retry'))
|
|
369
|
+
await waitFor(() => rendered.getByText('data'))
|
|
370
|
+
})
|
|
371
|
+
|
|
372
|
+
it('should not retry fetch if the reset error boundary has not been reset after a previous reset', async () => {
|
|
373
|
+
const key = queryKey()
|
|
374
|
+
|
|
375
|
+
let succeed = false
|
|
376
|
+
let shouldReset = true
|
|
377
|
+
|
|
378
|
+
function Page() {
|
|
379
|
+
const { data } = useQuery(
|
|
380
|
+
key,
|
|
381
|
+
async () => {
|
|
382
|
+
await sleep(10)
|
|
383
|
+
if (!succeed) {
|
|
384
|
+
throw new Error('Error')
|
|
385
|
+
} else {
|
|
386
|
+
return 'data'
|
|
387
|
+
}
|
|
388
|
+
},
|
|
389
|
+
{
|
|
390
|
+
retry: false,
|
|
391
|
+
useErrorBoundary: true,
|
|
392
|
+
},
|
|
393
|
+
)
|
|
394
|
+
return <div>{data}</div>
|
|
395
|
+
}
|
|
396
|
+
|
|
397
|
+
const rendered = renderWithClient(
|
|
398
|
+
queryClient,
|
|
399
|
+
<QueryErrorResetBoundary>
|
|
400
|
+
{({ reset }) => (
|
|
401
|
+
<ErrorBoundary
|
|
402
|
+
onReset={() => {
|
|
403
|
+
if (shouldReset) {
|
|
404
|
+
reset()
|
|
405
|
+
}
|
|
406
|
+
}}
|
|
407
|
+
fallbackRender={({ resetErrorBoundary }) => (
|
|
408
|
+
<div>
|
|
409
|
+
<div>error boundary</div>
|
|
410
|
+
<button
|
|
411
|
+
onClick={() => {
|
|
412
|
+
resetErrorBoundary()
|
|
413
|
+
}}
|
|
414
|
+
>
|
|
415
|
+
retry
|
|
416
|
+
</button>
|
|
417
|
+
</div>
|
|
418
|
+
)}
|
|
419
|
+
>
|
|
420
|
+
<Page />
|
|
421
|
+
</ErrorBoundary>
|
|
422
|
+
)}
|
|
423
|
+
</QueryErrorResetBoundary>,
|
|
424
|
+
)
|
|
141
425
|
|
|
142
|
-
|
|
143
|
-
|
|
144
|
-
|
|
145
|
-
|
|
146
|
-
|
|
147
|
-
|
|
148
|
-
|
|
426
|
+
await waitFor(() => rendered.getByText('error boundary'))
|
|
427
|
+
await waitFor(() => rendered.getByText('retry'))
|
|
428
|
+
shouldReset = true
|
|
429
|
+
fireEvent.click(rendered.getByText('retry'))
|
|
430
|
+
await waitFor(() => rendered.getByText('error boundary'))
|
|
431
|
+
succeed = true
|
|
432
|
+
shouldReset = false
|
|
433
|
+
fireEvent.click(rendered.getByText('retry'))
|
|
434
|
+
await waitFor(() => rendered.getByText('error boundary'))
|
|
435
|
+
})
|
|
436
|
+
|
|
437
|
+
it('should throw again on error after the reset error boundary has been reset', async () => {
|
|
438
|
+
const key = queryKey()
|
|
439
|
+
let fetchCount = 0
|
|
440
|
+
|
|
441
|
+
function Page() {
|
|
442
|
+
const { data } = useQuery<string>(
|
|
443
|
+
key,
|
|
444
|
+
async () => {
|
|
445
|
+
fetchCount++
|
|
446
|
+
await sleep(10)
|
|
149
447
|
throw new Error('Error')
|
|
150
|
-
}
|
|
151
|
-
|
|
152
|
-
|
|
153
|
-
|
|
154
|
-
|
|
155
|
-
|
|
156
|
-
|
|
157
|
-
|
|
158
|
-
|
|
448
|
+
},
|
|
449
|
+
{
|
|
450
|
+
retry: false,
|
|
451
|
+
useErrorBoundary: true,
|
|
452
|
+
},
|
|
453
|
+
)
|
|
454
|
+
return <div>{data}</div>
|
|
455
|
+
}
|
|
456
|
+
|
|
457
|
+
const rendered = renderWithClient(
|
|
458
|
+
queryClient,
|
|
459
|
+
<QueryErrorResetBoundary>
|
|
460
|
+
{({ reset }) => (
|
|
461
|
+
<ErrorBoundary
|
|
462
|
+
onReset={reset}
|
|
463
|
+
fallbackRender={({ resetErrorBoundary }) => (
|
|
464
|
+
<div>
|
|
465
|
+
<div>error boundary</div>
|
|
466
|
+
<button
|
|
467
|
+
onClick={() => {
|
|
468
|
+
resetErrorBoundary()
|
|
469
|
+
}}
|
|
470
|
+
>
|
|
471
|
+
retry
|
|
472
|
+
</button>
|
|
473
|
+
</div>
|
|
474
|
+
)}
|
|
475
|
+
>
|
|
476
|
+
<Page />
|
|
477
|
+
</ErrorBoundary>
|
|
478
|
+
)}
|
|
479
|
+
</QueryErrorResetBoundary>,
|
|
159
480
|
)
|
|
160
481
|
|
|
161
|
-
|
|
162
|
-
|
|
163
|
-
|
|
164
|
-
|
|
165
|
-
|
|
166
|
-
|
|
167
|
-
|
|
168
|
-
|
|
169
|
-
|
|
170
|
-
|
|
171
|
-
|
|
172
|
-
|
|
173
|
-
|
|
174
|
-
|
|
175
|
-
|
|
176
|
-
|
|
177
|
-
|
|
178
|
-
|
|
179
|
-
|
|
180
|
-
|
|
181
|
-
|
|
182
|
-
|
|
183
|
-
|
|
184
|
-
|
|
185
|
-
|
|
186
|
-
|
|
187
|
-
|
|
188
|
-
|
|
189
|
-
|
|
190
|
-
|
|
191
|
-
|
|
192
|
-
|
|
193
|
-
|
|
194
|
-
|
|
195
|
-
|
|
196
|
-
|
|
197
|
-
|
|
198
|
-
|
|
199
|
-
|
|
200
|
-
|
|
201
|
-
|
|
202
|
-
|
|
203
|
-
|
|
204
|
-
|
|
205
|
-
|
|
206
|
-
|
|
207
|
-
|
|
208
|
-
|
|
209
|
-
|
|
210
|
-
|
|
211
|
-
|
|
212
|
-
|
|
213
|
-
|
|
482
|
+
await waitFor(() => rendered.getByText('error boundary'))
|
|
483
|
+
await waitFor(() => rendered.getByText('retry'))
|
|
484
|
+
fireEvent.click(rendered.getByText('retry'))
|
|
485
|
+
await waitFor(() => rendered.getByText('error boundary'))
|
|
486
|
+
await waitFor(() => rendered.getByText('retry'))
|
|
487
|
+
fireEvent.click(rendered.getByText('retry'))
|
|
488
|
+
await waitFor(() => rendered.getByText('error boundary'))
|
|
489
|
+
expect(fetchCount).toBe(3)
|
|
490
|
+
})
|
|
491
|
+
|
|
492
|
+
it('should never render the component while the query is in error state', async () => {
|
|
493
|
+
const key = queryKey()
|
|
494
|
+
let fetchCount = 0
|
|
495
|
+
let renders = 0
|
|
496
|
+
|
|
497
|
+
function Page() {
|
|
498
|
+
const { data } = useQuery(
|
|
499
|
+
key,
|
|
500
|
+
async () => {
|
|
501
|
+
fetchCount++
|
|
502
|
+
await sleep(10)
|
|
503
|
+
if (fetchCount > 2) {
|
|
504
|
+
return 'data'
|
|
505
|
+
} else {
|
|
506
|
+
throw new Error('Error')
|
|
507
|
+
}
|
|
508
|
+
},
|
|
509
|
+
{
|
|
510
|
+
retry: false,
|
|
511
|
+
suspense: true,
|
|
512
|
+
},
|
|
513
|
+
)
|
|
514
|
+
renders++
|
|
515
|
+
return <div>{data}</div>
|
|
516
|
+
}
|
|
517
|
+
|
|
518
|
+
const rendered = renderWithClient(
|
|
519
|
+
queryClient,
|
|
520
|
+
<QueryErrorResetBoundary>
|
|
521
|
+
{({ reset }) => (
|
|
522
|
+
<ErrorBoundary
|
|
523
|
+
onReset={reset}
|
|
524
|
+
fallbackRender={({ resetErrorBoundary }) => (
|
|
525
|
+
<div>
|
|
526
|
+
<div>error boundary</div>
|
|
527
|
+
<button
|
|
528
|
+
onClick={() => {
|
|
529
|
+
resetErrorBoundary()
|
|
530
|
+
}}
|
|
531
|
+
>
|
|
532
|
+
retry
|
|
533
|
+
</button>
|
|
534
|
+
</div>
|
|
535
|
+
)}
|
|
536
|
+
>
|
|
537
|
+
<React.Suspense fallback={<div>loading</div>}>
|
|
538
|
+
<Page />
|
|
539
|
+
</React.Suspense>
|
|
540
|
+
</ErrorBoundary>
|
|
541
|
+
)}
|
|
542
|
+
</QueryErrorResetBoundary>,
|
|
214
543
|
)
|
|
215
544
|
|
|
216
|
-
|
|
217
|
-
|
|
218
|
-
|
|
545
|
+
await waitFor(() => rendered.getByText('error boundary'))
|
|
546
|
+
await waitFor(() => rendered.getByText('retry'))
|
|
547
|
+
fireEvent.click(rendered.getByText('retry'))
|
|
548
|
+
await waitFor(() => rendered.getByText('error boundary'))
|
|
549
|
+
await waitFor(() => rendered.getByText('retry'))
|
|
550
|
+
fireEvent.click(rendered.getByText('retry'))
|
|
551
|
+
await waitFor(() => rendered.getByText('data'))
|
|
552
|
+
expect(fetchCount).toBe(3)
|
|
553
|
+
expect(renders).toBe(1)
|
|
554
|
+
})
|
|
555
|
+
|
|
556
|
+
it('should render children', async () => {
|
|
557
|
+
function Page() {
|
|
558
|
+
return (
|
|
219
559
|
<div>
|
|
220
|
-
|
|
560
|
+
<span>page</span>
|
|
221
561
|
</div>
|
|
222
|
-
|
|
223
|
-
|
|
562
|
+
)
|
|
563
|
+
}
|
|
564
|
+
|
|
565
|
+
const rendered = renderWithClient(
|
|
566
|
+
queryClient,
|
|
567
|
+
<QueryErrorResetBoundary>
|
|
568
|
+
<Page />
|
|
569
|
+
</QueryErrorResetBoundary>,
|
|
224
570
|
)
|
|
225
|
-
}
|
|
226
|
-
|
|
227
|
-
const rendered = renderWithClient(
|
|
228
|
-
queryClient,
|
|
229
|
-
<QueryErrorResetBoundary>
|
|
230
|
-
{({ reset }) => (
|
|
231
|
-
<ErrorBoundary
|
|
232
|
-
onReset={reset}
|
|
233
|
-
fallbackRender={({ resetErrorBoundary }) => (
|
|
234
|
-
<div>
|
|
235
|
-
<div>error boundary</div>
|
|
236
|
-
<button
|
|
237
|
-
onClick={() => {
|
|
238
|
-
resetErrorBoundary()
|
|
239
|
-
}}
|
|
240
|
-
>
|
|
241
|
-
retry
|
|
242
|
-
</button>
|
|
243
|
-
</div>
|
|
244
|
-
)}
|
|
245
|
-
>
|
|
246
|
-
<Page />
|
|
247
|
-
</ErrorBoundary>
|
|
248
|
-
)}
|
|
249
|
-
</QueryErrorResetBoundary>,
|
|
250
|
-
)
|
|
251
|
-
|
|
252
|
-
await waitFor(() =>
|
|
253
|
-
rendered.getByText('status: loading, fetchStatus: idle'),
|
|
254
|
-
)
|
|
255
|
-
fireEvent.click(rendered.getByRole('button', { name: /refetch/i }))
|
|
256
|
-
await waitFor(() => rendered.getByText('error boundary'))
|
|
257
|
-
})
|
|
258
|
-
|
|
259
|
-
it('should not retry fetch if the reset error boundary has not been reset', async () => {
|
|
260
|
-
const key = queryKey()
|
|
261
571
|
|
|
262
|
-
|
|
263
|
-
|
|
264
|
-
|
|
265
|
-
|
|
266
|
-
|
|
267
|
-
|
|
268
|
-
|
|
269
|
-
|
|
270
|
-
|
|
271
|
-
|
|
272
|
-
|
|
273
|
-
|
|
274
|
-
|
|
275
|
-
|
|
276
|
-
|
|
277
|
-
|
|
278
|
-
|
|
572
|
+
expect(rendered.queryByText('page')).not.toBeNull()
|
|
573
|
+
})
|
|
574
|
+
|
|
575
|
+
it('should show error boundary when using tracked queries even though we do not track the error field', async () => {
|
|
576
|
+
const key = queryKey()
|
|
577
|
+
|
|
578
|
+
let succeed = false
|
|
579
|
+
|
|
580
|
+
function Page() {
|
|
581
|
+
const { data } = useQuery(
|
|
582
|
+
key,
|
|
583
|
+
async () => {
|
|
584
|
+
await sleep(10)
|
|
585
|
+
if (!succeed) {
|
|
586
|
+
throw new Error('Error')
|
|
587
|
+
} else {
|
|
588
|
+
return 'data'
|
|
589
|
+
}
|
|
590
|
+
},
|
|
591
|
+
{
|
|
592
|
+
retry: false,
|
|
593
|
+
useErrorBoundary: true,
|
|
594
|
+
},
|
|
595
|
+
)
|
|
596
|
+
return <div>{data}</div>
|
|
597
|
+
}
|
|
598
|
+
|
|
599
|
+
const rendered = renderWithClient(
|
|
600
|
+
queryClient,
|
|
601
|
+
<QueryErrorResetBoundary>
|
|
602
|
+
{({ reset }) => (
|
|
603
|
+
<ErrorBoundary
|
|
604
|
+
onReset={reset}
|
|
605
|
+
fallbackRender={({ resetErrorBoundary }) => (
|
|
606
|
+
<div>
|
|
607
|
+
<div>error boundary</div>
|
|
608
|
+
<button
|
|
609
|
+
onClick={() => {
|
|
610
|
+
resetErrorBoundary()
|
|
611
|
+
}}
|
|
612
|
+
>
|
|
613
|
+
retry
|
|
614
|
+
</button>
|
|
615
|
+
</div>
|
|
616
|
+
)}
|
|
617
|
+
>
|
|
618
|
+
<Page />
|
|
619
|
+
</ErrorBoundary>
|
|
620
|
+
)}
|
|
621
|
+
</QueryErrorResetBoundary>,
|
|
279
622
|
)
|
|
280
|
-
return <div>{data}</div>
|
|
281
|
-
}
|
|
282
|
-
|
|
283
|
-
const rendered = renderWithClient(
|
|
284
|
-
queryClient,
|
|
285
|
-
<QueryErrorResetBoundary>
|
|
286
|
-
{() => (
|
|
287
|
-
<ErrorBoundary
|
|
288
|
-
fallbackRender={({ resetErrorBoundary }) => (
|
|
289
|
-
<div>
|
|
290
|
-
<div>error boundary</div>
|
|
291
|
-
<button
|
|
292
|
-
onClick={() => {
|
|
293
|
-
resetErrorBoundary()
|
|
294
|
-
}}
|
|
295
|
-
>
|
|
296
|
-
retry
|
|
297
|
-
</button>
|
|
298
|
-
</div>
|
|
299
|
-
)}
|
|
300
|
-
>
|
|
301
|
-
<Page />
|
|
302
|
-
</ErrorBoundary>
|
|
303
|
-
)}
|
|
304
|
-
</QueryErrorResetBoundary>,
|
|
305
|
-
)
|
|
306
|
-
|
|
307
|
-
await waitFor(() => rendered.getByText('error boundary'))
|
|
308
|
-
await waitFor(() => rendered.getByText('retry'))
|
|
309
|
-
succeed = true
|
|
310
|
-
fireEvent.click(rendered.getByText('retry'))
|
|
311
|
-
await waitFor(() => rendered.getByText('error boundary'))
|
|
312
|
-
})
|
|
313
|
-
|
|
314
|
-
it('should retry fetch if the reset error boundary has been reset and the query contains data from a previous fetch', async () => {
|
|
315
|
-
const key = queryKey()
|
|
316
623
|
|
|
317
|
-
|
|
318
|
-
|
|
319
|
-
|
|
320
|
-
|
|
321
|
-
|
|
322
|
-
|
|
323
|
-
await sleep(10)
|
|
324
|
-
if (!succeed) {
|
|
325
|
-
throw new Error('Error')
|
|
326
|
-
} else {
|
|
327
|
-
return 'data'
|
|
328
|
-
}
|
|
329
|
-
},
|
|
330
|
-
{
|
|
331
|
-
retry: false,
|
|
332
|
-
useErrorBoundary: true,
|
|
333
|
-
initialData: 'initial',
|
|
334
|
-
},
|
|
335
|
-
)
|
|
336
|
-
return <div>{data}</div>
|
|
337
|
-
}
|
|
338
|
-
|
|
339
|
-
const rendered = renderWithClient(
|
|
340
|
-
queryClient,
|
|
341
|
-
<QueryErrorResetBoundary>
|
|
342
|
-
{({ reset }) => (
|
|
343
|
-
<ErrorBoundary
|
|
344
|
-
onReset={reset}
|
|
345
|
-
fallbackRender={({ resetErrorBoundary }) => (
|
|
346
|
-
<div>
|
|
347
|
-
<div>error boundary</div>
|
|
348
|
-
<button
|
|
349
|
-
onClick={() => {
|
|
350
|
-
resetErrorBoundary()
|
|
351
|
-
}}
|
|
352
|
-
>
|
|
353
|
-
retry
|
|
354
|
-
</button>
|
|
355
|
-
</div>
|
|
356
|
-
)}
|
|
357
|
-
>
|
|
358
|
-
<Page />
|
|
359
|
-
</ErrorBoundary>
|
|
360
|
-
)}
|
|
361
|
-
</QueryErrorResetBoundary>,
|
|
362
|
-
)
|
|
363
|
-
|
|
364
|
-
await waitFor(() => rendered.getByText('error boundary'))
|
|
365
|
-
await waitFor(() => rendered.getByText('retry'))
|
|
366
|
-
succeed = true
|
|
367
|
-
fireEvent.click(rendered.getByText('retry'))
|
|
368
|
-
await waitFor(() => rendered.getByText('data'))
|
|
624
|
+
await waitFor(() => rendered.getByText('error boundary'))
|
|
625
|
+
await waitFor(() => rendered.getByText('retry'))
|
|
626
|
+
succeed = true
|
|
627
|
+
fireEvent.click(rendered.getByText('retry'))
|
|
628
|
+
await waitFor(() => rendered.getByText('data'))
|
|
629
|
+
})
|
|
369
630
|
})
|
|
370
631
|
|
|
371
|
-
|
|
372
|
-
|
|
632
|
+
describe('useQueries', () => {
|
|
633
|
+
it('should retry fetch if the reset error boundary has been reset', async () => {
|
|
634
|
+
const key = queryKey()
|
|
373
635
|
|
|
374
|
-
|
|
375
|
-
let shouldReset = true
|
|
636
|
+
let succeed = false
|
|
376
637
|
|
|
377
|
-
|
|
378
|
-
|
|
379
|
-
|
|
380
|
-
async () => {
|
|
638
|
+
const queryOptions = {
|
|
639
|
+
queryKey: key,
|
|
640
|
+
queryFn: async () => {
|
|
381
641
|
await sleep(10)
|
|
382
642
|
if (!succeed) {
|
|
383
643
|
throw new Error('Error')
|
|
@@ -385,201 +645,56 @@ describe('QueryErrorResetBoundary', () => {
|
|
|
385
645
|
return 'data'
|
|
386
646
|
}
|
|
387
647
|
},
|
|
388
|
-
|
|
389
|
-
|
|
390
|
-
|
|
391
|
-
|
|
392
|
-
|
|
393
|
-
|
|
394
|
-
|
|
395
|
-
|
|
396
|
-
|
|
397
|
-
|
|
398
|
-
|
|
399
|
-
|
|
400
|
-
|
|
401
|
-
|
|
402
|
-
|
|
403
|
-
|
|
404
|
-
}
|
|
405
|
-
|
|
406
|
-
|
|
407
|
-
|
|
408
|
-
|
|
409
|
-
|
|
410
|
-
|
|
411
|
-
|
|
412
|
-
|
|
413
|
-
|
|
414
|
-
|
|
415
|
-
|
|
416
|
-
|
|
417
|
-
)}
|
|
418
|
-
>
|
|
419
|
-
<Page />
|
|
420
|
-
</ErrorBoundary>
|
|
421
|
-
)}
|
|
422
|
-
</QueryErrorResetBoundary>,
|
|
423
|
-
)
|
|
424
|
-
|
|
425
|
-
await waitFor(() => rendered.getByText('error boundary'))
|
|
426
|
-
await waitFor(() => rendered.getByText('retry'))
|
|
427
|
-
shouldReset = true
|
|
428
|
-
fireEvent.click(rendered.getByText('retry'))
|
|
429
|
-
await waitFor(() => rendered.getByText('error boundary'))
|
|
430
|
-
succeed = true
|
|
431
|
-
shouldReset = false
|
|
432
|
-
fireEvent.click(rendered.getByText('retry'))
|
|
433
|
-
await waitFor(() => rendered.getByText('error boundary'))
|
|
434
|
-
})
|
|
435
|
-
|
|
436
|
-
it('should throw again on error after the reset error boundary has been reset', async () => {
|
|
437
|
-
const key = queryKey()
|
|
438
|
-
let fetchCount = 0
|
|
439
|
-
|
|
440
|
-
function Page() {
|
|
441
|
-
const { data } = useQuery<string>(
|
|
442
|
-
key,
|
|
443
|
-
async () => {
|
|
444
|
-
fetchCount++
|
|
445
|
-
await sleep(10)
|
|
446
|
-
throw new Error('Error')
|
|
447
|
-
},
|
|
448
|
-
{
|
|
449
|
-
retry: false,
|
|
450
|
-
useErrorBoundary: true,
|
|
451
|
-
},
|
|
452
|
-
)
|
|
453
|
-
return <div>{data}</div>
|
|
454
|
-
}
|
|
455
|
-
|
|
456
|
-
const rendered = renderWithClient(
|
|
457
|
-
queryClient,
|
|
458
|
-
<QueryErrorResetBoundary>
|
|
459
|
-
{({ reset }) => (
|
|
460
|
-
<ErrorBoundary
|
|
461
|
-
onReset={reset}
|
|
462
|
-
fallbackRender={({ resetErrorBoundary }) => (
|
|
463
|
-
<div>
|
|
464
|
-
<div>error boundary</div>
|
|
465
|
-
<button
|
|
466
|
-
onClick={() => {
|
|
467
|
-
resetErrorBoundary()
|
|
468
|
-
}}
|
|
469
|
-
>
|
|
470
|
-
retry
|
|
471
|
-
</button>
|
|
472
|
-
</div>
|
|
473
|
-
)}
|
|
474
|
-
>
|
|
475
|
-
<Page />
|
|
476
|
-
</ErrorBoundary>
|
|
477
|
-
)}
|
|
478
|
-
</QueryErrorResetBoundary>,
|
|
479
|
-
)
|
|
480
|
-
|
|
481
|
-
await waitFor(() => rendered.getByText('error boundary'))
|
|
482
|
-
await waitFor(() => rendered.getByText('retry'))
|
|
483
|
-
fireEvent.click(rendered.getByText('retry'))
|
|
484
|
-
await waitFor(() => rendered.getByText('error boundary'))
|
|
485
|
-
await waitFor(() => rendered.getByText('retry'))
|
|
486
|
-
fireEvent.click(rendered.getByText('retry'))
|
|
487
|
-
await waitFor(() => rendered.getByText('error boundary'))
|
|
488
|
-
expect(fetchCount).toBe(3)
|
|
489
|
-
})
|
|
490
|
-
|
|
491
|
-
it('should never render the component while the query is in error state', async () => {
|
|
492
|
-
const key = queryKey()
|
|
493
|
-
let fetchCount = 0
|
|
494
|
-
let renders = 0
|
|
495
|
-
|
|
496
|
-
function Page() {
|
|
497
|
-
const { data } = useQuery(
|
|
498
|
-
key,
|
|
499
|
-
async () => {
|
|
500
|
-
fetchCount++
|
|
501
|
-
await sleep(10)
|
|
502
|
-
if (fetchCount > 2) {
|
|
503
|
-
return 'data'
|
|
504
|
-
} else {
|
|
505
|
-
throw new Error('Error')
|
|
506
|
-
}
|
|
507
|
-
},
|
|
508
|
-
{
|
|
509
|
-
retry: false,
|
|
510
|
-
suspense: true,
|
|
511
|
-
},
|
|
512
|
-
)
|
|
513
|
-
renders++
|
|
514
|
-
return <div>{data}</div>
|
|
515
|
-
}
|
|
516
|
-
|
|
517
|
-
const rendered = renderWithClient(
|
|
518
|
-
queryClient,
|
|
519
|
-
<QueryErrorResetBoundary>
|
|
520
|
-
{({ reset }) => (
|
|
521
|
-
<ErrorBoundary
|
|
522
|
-
onReset={reset}
|
|
523
|
-
fallbackRender={({ resetErrorBoundary }) => (
|
|
524
|
-
<div>
|
|
525
|
-
<div>error boundary</div>
|
|
526
|
-
<button
|
|
527
|
-
onClick={() => {
|
|
528
|
-
resetErrorBoundary()
|
|
529
|
-
}}
|
|
530
|
-
>
|
|
531
|
-
retry
|
|
532
|
-
</button>
|
|
533
|
-
</div>
|
|
534
|
-
)}
|
|
535
|
-
>
|
|
536
|
-
<React.Suspense fallback={<div>loading</div>}>
|
|
648
|
+
retry: false,
|
|
649
|
+
useErrorBoundary: true,
|
|
650
|
+
retryOnMount: true,
|
|
651
|
+
}
|
|
652
|
+
|
|
653
|
+
function Page() {
|
|
654
|
+
const [{ data }] = useQueries({ queries: [queryOptions] })
|
|
655
|
+
return <div>{data}</div>
|
|
656
|
+
}
|
|
657
|
+
|
|
658
|
+
const rendered = renderWithClient(
|
|
659
|
+
queryClient,
|
|
660
|
+
<QueryErrorResetBoundary>
|
|
661
|
+
{({ reset }) => (
|
|
662
|
+
<ErrorBoundary
|
|
663
|
+
onReset={reset}
|
|
664
|
+
fallbackRender={({ resetErrorBoundary }) => (
|
|
665
|
+
<div>
|
|
666
|
+
<div>error boundary</div>
|
|
667
|
+
<button
|
|
668
|
+
onClick={() => {
|
|
669
|
+
resetErrorBoundary()
|
|
670
|
+
}}
|
|
671
|
+
>
|
|
672
|
+
retry
|
|
673
|
+
</button>
|
|
674
|
+
</div>
|
|
675
|
+
)}
|
|
676
|
+
>
|
|
537
677
|
<Page />
|
|
538
|
-
</
|
|
539
|
-
|
|
540
|
-
|
|
541
|
-
</QueryErrorResetBoundary>,
|
|
542
|
-
)
|
|
543
|
-
|
|
544
|
-
await waitFor(() => rendered.getByText('error boundary'))
|
|
545
|
-
await waitFor(() => rendered.getByText('retry'))
|
|
546
|
-
fireEvent.click(rendered.getByText('retry'))
|
|
547
|
-
await waitFor(() => rendered.getByText('error boundary'))
|
|
548
|
-
await waitFor(() => rendered.getByText('retry'))
|
|
549
|
-
fireEvent.click(rendered.getByText('retry'))
|
|
550
|
-
await waitFor(() => rendered.getByText('data'))
|
|
551
|
-
expect(fetchCount).toBe(3)
|
|
552
|
-
expect(renders).toBe(1)
|
|
553
|
-
})
|
|
554
|
-
|
|
555
|
-
it('should render children', async () => {
|
|
556
|
-
function Page() {
|
|
557
|
-
return (
|
|
558
|
-
<div>
|
|
559
|
-
<span>page</span>
|
|
560
|
-
</div>
|
|
678
|
+
</ErrorBoundary>
|
|
679
|
+
)}
|
|
680
|
+
</QueryErrorResetBoundary>,
|
|
561
681
|
)
|
|
562
|
-
}
|
|
563
|
-
|
|
564
|
-
const rendered = renderWithClient(
|
|
565
|
-
queryClient,
|
|
566
|
-
<QueryErrorResetBoundary>
|
|
567
|
-
<Page />
|
|
568
|
-
</QueryErrorResetBoundary>,
|
|
569
|
-
)
|
|
570
682
|
|
|
571
|
-
|
|
572
|
-
|
|
683
|
+
await waitFor(() => rendered.getByText('error boundary'))
|
|
684
|
+
await waitFor(() => rendered.getByText('retry'))
|
|
685
|
+
succeed = true
|
|
686
|
+
fireEvent.click(rendered.getByText('retry'))
|
|
687
|
+
await waitFor(() => rendered.getByText('data'))
|
|
688
|
+
})
|
|
573
689
|
|
|
574
|
-
|
|
575
|
-
|
|
690
|
+
it('with suspense should retry fetch if the reset error boundary has been reset', async () => {
|
|
691
|
+
const key = queryKey()
|
|
576
692
|
|
|
577
|
-
|
|
693
|
+
let succeed = false
|
|
578
694
|
|
|
579
|
-
|
|
580
|
-
|
|
581
|
-
|
|
582
|
-
async () => {
|
|
695
|
+
const queryOptions = {
|
|
696
|
+
queryKey: key,
|
|
697
|
+
queryFn: async () => {
|
|
583
698
|
await sleep(10)
|
|
584
699
|
if (!succeed) {
|
|
585
700
|
throw new Error('Error')
|
|
@@ -587,43 +702,49 @@ describe('QueryErrorResetBoundary', () => {
|
|
|
587
702
|
return 'data'
|
|
588
703
|
}
|
|
589
704
|
},
|
|
590
|
-
|
|
591
|
-
|
|
592
|
-
|
|
593
|
-
|
|
705
|
+
retry: false,
|
|
706
|
+
useErrorBoundary: true,
|
|
707
|
+
retryOnMount: true,
|
|
708
|
+
suspense: true,
|
|
709
|
+
}
|
|
710
|
+
|
|
711
|
+
function Page() {
|
|
712
|
+
const [{ data }] = useQueries({ queries: [queryOptions] })
|
|
713
|
+
return <div>{data}</div>
|
|
714
|
+
}
|
|
715
|
+
|
|
716
|
+
const rendered = renderWithClient(
|
|
717
|
+
queryClient,
|
|
718
|
+
<QueryErrorResetBoundary>
|
|
719
|
+
{({ reset }) => (
|
|
720
|
+
<ErrorBoundary
|
|
721
|
+
onReset={reset}
|
|
722
|
+
fallbackRender={({ resetErrorBoundary }) => (
|
|
723
|
+
<div>
|
|
724
|
+
<div>error boundary</div>
|
|
725
|
+
<button
|
|
726
|
+
onClick={() => {
|
|
727
|
+
resetErrorBoundary()
|
|
728
|
+
}}
|
|
729
|
+
>
|
|
730
|
+
retry
|
|
731
|
+
</button>
|
|
732
|
+
</div>
|
|
733
|
+
)}
|
|
734
|
+
>
|
|
735
|
+
<React.Suspense fallback="Loader">
|
|
736
|
+
<Page />
|
|
737
|
+
</React.Suspense>
|
|
738
|
+
</ErrorBoundary>
|
|
739
|
+
)}
|
|
740
|
+
</QueryErrorResetBoundary>,
|
|
594
741
|
)
|
|
595
|
-
|
|
596
|
-
|
|
597
|
-
|
|
598
|
-
|
|
599
|
-
|
|
600
|
-
|
|
601
|
-
|
|
602
|
-
<ErrorBoundary
|
|
603
|
-
onReset={reset}
|
|
604
|
-
fallbackRender={({ resetErrorBoundary }) => (
|
|
605
|
-
<div>
|
|
606
|
-
<div>error boundary</div>
|
|
607
|
-
<button
|
|
608
|
-
onClick={() => {
|
|
609
|
-
resetErrorBoundary()
|
|
610
|
-
}}
|
|
611
|
-
>
|
|
612
|
-
retry
|
|
613
|
-
</button>
|
|
614
|
-
</div>
|
|
615
|
-
)}
|
|
616
|
-
>
|
|
617
|
-
<Page />
|
|
618
|
-
</ErrorBoundary>
|
|
619
|
-
)}
|
|
620
|
-
</QueryErrorResetBoundary>,
|
|
621
|
-
)
|
|
622
|
-
|
|
623
|
-
await waitFor(() => rendered.getByText('error boundary'))
|
|
624
|
-
await waitFor(() => rendered.getByText('retry'))
|
|
625
|
-
succeed = true
|
|
626
|
-
fireEvent.click(rendered.getByText('retry'))
|
|
627
|
-
await waitFor(() => rendered.getByText('data'))
|
|
742
|
+
|
|
743
|
+
await waitFor(() => rendered.getByText('error boundary'))
|
|
744
|
+
await waitFor(() => rendered.getByText('retry'))
|
|
745
|
+
succeed = true
|
|
746
|
+
fireEvent.click(rendered.getByText('retry'))
|
|
747
|
+
await waitFor(() => rendered.getByText('data'))
|
|
748
|
+
})
|
|
628
749
|
})
|
|
629
750
|
})
|