@@ -219,4 +219,136 @@ describe('useInfiniteQuery', () => {
219219 rendered . getByText ( 'Page 1: 2' ) ,
220220 ] )
221221 } )
222+
223+ it ( 'should build fresh cursors on refetch' , async ( ) => {
224+ const genItems = size => [ ...new Array ( size ) ] . fill ( null ) . map ( ( _ , d ) => d )
225+ const items = genItems ( 15 )
226+ const limit = 3
227+
228+ const fetchItems = async ( cursor = 0 , ts ) => {
229+ await sleep ( 10 )
230+ return {
231+ nextId : cursor + limit ,
232+ items : items . slice ( cursor , cursor + limit ) ,
233+ ts,
234+ }
235+ }
236+
237+ function Page ( ) {
238+ const fetchCountRef = React . useRef ( 0 )
239+ const {
240+ status,
241+ data,
242+ error,
243+ isFetchingMore,
244+ fetchMore,
245+ canFetchMore,
246+ refetch,
247+ } = useInfiniteQuery (
248+ 'items' ,
249+ ( key , nextId = 0 ) => fetchItems ( nextId , fetchCountRef . current ++ ) ,
250+ {
251+ getFetchMore : ( lastGroup , allGroups ) => lastGroup . nextId ,
252+ }
253+ )
254+
255+ return (
256+ < div >
257+ < h1 > Pagination</ h1 >
258+ { status === 'loading' ? (
259+ 'Loading...'
260+ ) : status === 'error' ? (
261+ < span > Error: { error . message } </ span >
262+ ) : (
263+ < >
264+ < div > Data:</ div >
265+ { data . map ( ( page , i ) => (
266+ < div key = { i } >
267+ < div >
268+ Page { i } : { page . ts }
269+ </ div >
270+ < div key = { i } >
271+ { page . items . map ( item => (
272+ < p key = { item } > Item: { item } </ p >
273+ ) ) }
274+ </ div >
275+ </ div >
276+ ) ) }
277+ < div >
278+ < button
279+ onClick = { ( ) => fetchMore ( ) }
280+ disabled = { ! canFetchMore || isFetchingMore }
281+ >
282+ { isFetchingMore
283+ ? 'Loading more...'
284+ : canFetchMore
285+ ? 'Load More'
286+ : 'Nothing more to load' }
287+ </ button >
288+ < button onClick = { ( ) => refetch ( ) } > Refetch</ button >
289+ < button
290+ onClick = { ( ) => {
291+ // Imagine that this mutation happens somewhere else
292+ // makes an actual network request
293+ // and calls refetchQueries in an onSuccess
294+ items . splice ( 4 , 1 )
295+ queryCache . refetchQueries ( 'items' )
296+ } }
297+ >
298+ Remove item
299+ </ button >
300+ </ div >
301+ < div > { ! isFetchingMore ? 'Background Updating...' : null } </ div >
302+ </ >
303+ ) }
304+ </ div >
305+ )
306+ }
307+
308+ const rendered = render ( < Page /> )
309+
310+ rendered . getByText ( 'Loading...' )
311+
312+ await rendered . findByText ( 'Item: 2' )
313+ await rendered . findByText ( 'Page 0: 0' )
314+
315+ fireEvent . click ( rendered . getByText ( 'Load More' ) )
316+
317+ await rendered . findByText ( 'Loading more...' )
318+ await rendered . findByText ( 'Item: 5' )
319+ await rendered . findByText ( 'Page 0: 0' )
320+ await rendered . findByText ( 'Page 1: 1' )
321+
322+ fireEvent . click ( rendered . getByText ( 'Load More' ) )
323+
324+ await rendered . findByText ( 'Loading more...' )
325+ await rendered . findByText ( 'Item: 8' )
326+ await rendered . findByText ( 'Page 0: 0' )
327+ await rendered . findByText ( 'Page 1: 1' )
328+ await rendered . findByText ( 'Page 2: 2' )
329+
330+ fireEvent . click ( rendered . getByText ( 'Refetch' ) )
331+
332+ await rendered . findByText ( 'Background Updating...' )
333+ await rendered . findByText ( 'Item: 8' )
334+ await rendered . findByText ( 'Page 0: 3' )
335+ await rendered . findByText ( 'Page 1: 4' )
336+ await rendered . findByText ( 'Page 2: 5' )
337+
338+ // ensure that Item: 4 is rendered before removing it
339+ expect ( rendered . queryAllByText ( 'Item: 4' ) ) . toHaveLength ( 1 )
340+
341+ // remove Item: 4
342+ fireEvent . click ( rendered . getByText ( 'Remove item' ) )
343+
344+ await rendered . findByText ( 'Background Updating...' )
345+ // ensure that an additional item is rendered (it means that cursors were properly rebuilt)
346+ await rendered . findByText ( 'Item: 9' )
347+ await rendered . findByText ( 'Page 0: 6' )
348+ await rendered . findByText ( 'Page 1: 7' )
349+ await rendered . findByText ( 'Page 2: 8' )
350+
351+ // ensure that Item: 4 is no longer rendered
352+ expect ( rendered . queryAllByText ( 'Item: 4' ) ) . toHaveLength ( 0 )
353+ } )
222354} )
0 commit comments