useSuspenseQuery
I was interested in how nested React <Suspense/>
and TanStack useSuspenseQuery worked together. The small app below is a visualization of various combinations of <Suspense/>
and TanStack Query.
The source code is available at GitHub. Using the custom <DelayedQuery/>
component it is easy to compose different loading scenarios to see how they behave. Give it a try, edit and run the code at StackBlitz.
Nested shows 3 nested <Suspense/>
, and within each <Suspense/>
a useSuspenseQuery
is run. The fetches run in serial. The loading state for the first query is shown, then when that is loaded the loading state for the second query and then when that is loaded the loading state for the third query is shown.
Parallel shows a <Suspense/>
containing 3 useSuspenseQuery
, with 2 fetches taking 1 second and 1 fetch taking 2 seconds. A single loading state is shown until the last query finishes after 2 seconds.
Cached shows two variations. The first variation Fast load first show a <Suspense/>
containing 3 useSuspenseQuery
as in the Parallel example but in this case all the queries use the same cache key. They are making the same request and can make use of the cache. The first request will take 4 seconds, the second will take 10 seconds and the third will take 10 seconds. A single loading state is shown until the first 4 second request completes, the other queries don’t attempt to make a query but instead wait for the first query to run that has the same cache key and use the cached result. All results are displayed after 4 seconds.
The second variation Slow load first is the same as Fast load first but the order of the queries is changed, in this case the first request will take 10 seconds, the second request will take 4 seconds and the third request will take 10 seconds. A single loading state is shown until the first 10 second request completes, the other queries don’t attempt to make a query but instead wait for the first query to run that has the same cache key and use the cached result. All results are displayed after 10 seconds.