11import type { RenderOptions } from "@testing-library/react" ;
2- import { screen } from "@testing-library/react" ;
32import {
43 createRenderStream ,
54 useTrackRenders ,
65} from "@testing-library/react-render-stream" ;
7- import { userEvent } from "@testing-library/user-event" ;
86import React , { Suspense } from "react" ;
7+ import { flushSync } from "react-dom" ;
98import { ErrorBoundary } from "react-error-boundary" ;
109
1110import type { DataState , ErrorLike , OperationVariables } from "@apollo/client" ;
@@ -47,24 +46,26 @@ export async function renderUseBackgroundQuery<
4746 return null ;
4847 }
4948
49+ let currentRefetch ! : useBackgroundQuery . Result < TData , TVariables > [ "refetch" ] ;
50+
5051 function App ( { props } : { props : Props | undefined } ) {
5152 useTrackRenders ( { name : "useBackgroundQuery" } ) ;
5253 const [ queryRef , { refetch } ] = renderHook ( props as any ) ;
5354
55+ currentRefetch = refetch ;
56+
5457 return (
5558 < Suspense fallback = { < SuspenseFallback /> } >
5659 < ErrorBoundary
5760 FallbackComponent = { ErrorFallback }
5861 onError = { ( error ) => replaceSnapshot ( { error } ) }
5962 >
6063 { queryRef && < UseReadQuery queryRef = { queryRef } /> }
61- < button onClick = { ( ) => refetch ( ) } > refetch</ button >
6264 </ ErrorBoundary >
6365 </ Suspense >
6466 ) ;
6567 }
6668
67- const user = userEvent . setup ( ) ;
6869 const { render, takeRender, replaceSnapshot } = createRenderStream <
6970 useReadQuery . Result < TData , TStates > | { error : ErrorLike }
7071 > ( ) ;
@@ -75,11 +76,13 @@ export async function renderUseBackgroundQuery<
7576 return utils . rerender ( < App props = { props } /> ) ;
7677 }
7778
78- // refetch needs to be run in an event handler in order for React 18 to commit
79- // the suspense fallback
80- async function refetch ( ) {
81- await user . click ( screen . getByText ( "refetch" ) ) ;
82- }
79+ // React 18 skips committing the suspense fallback when refetch is triggered
80+ // as a default-priority update, so the fallback render is missed and tests
81+ // may fail. flushSync forces a synchronous commit so the fallback renders in
82+ // both React 18 and 19, while returning the refetch promise.
83+ const refetch : typeof currentRefetch = ( ...args ) => {
84+ return flushSync ( ( ) => currentRefetch ( ...args ) ) ;
85+ } ;
8386
8487 return { takeRender, rerender, refetch } ;
8588}
0 commit comments