use-swr-infinite-preload.test.tsx
Overview
This file contains a comprehensive test suite for verifying the behavior of the preload functionality in conjunction with the useSWRInfinite React hook from the SWR library. SWR (stale-while-revalidate) is a React Hooks library for data fetching and caching.
The tests focus on ensuring that preloading data with preload behaves correctly when used with useSWRInfinite, which supports infinite loading of paginated data. The suite covers scenarios including:
Basic preloading correctness and data consistency.
Avoiding redundant preloads.
Preloading inside React effects.
Interaction with
suspensemode and deduplication.Handling errors during preload.
Preloading multiple pages and parallel requests.
Passing serialized keys to the fetcher.
By thoroughly testing these cases, the file ensures that the preload mechanism integrates smoothly with infinite loading patterns and other SWR features.
File Structure and Key Functions
This file is a pure test file and does not export any functions or classes. It imports utilities and React testing helpers to simulate and assert different behaviors.
Imports:
act,fireEvent,screenfrom@testing-library/react: For rendering and interacting with React components in tests.React hooks and components:
useEffect,useState,Suspense,Profiler.preloadfromswr: A function to preload data into SWR cache.useSWRInfinitefromswr/infinite: Hook to fetch paginated data infinitely.Custom utilities from
./utils:createKey,createResponse,renderWithConfig,sleep.
Test Suite: useSWRInfinite - preload
The entire file is wrapped inside a describe block named "useSWRInfinite - preload", grouping all test cases related to this behavior.
Helper Function
const getKeyFunction = (key: string) => (index: number) => `page-${index}-${key}`
Purpose: Returns a function that generates unique keys per page index, formatted as
"page-{index}-{key}".Usage: Used as the key function for
useSWRInfiniteto fetch data page-by-page.
Test Cases and Their Details:
1. preloading useSWRInfinite should produce the same result
Purpose: Verifies that preloading a page key results in the SWR hook having data immediately.
Implementation:
Create a key and a fetcher that returns
"foo".Preload the first page's key.
Render a component using
useSWRInfinite.Assert that the data is loaded (
data:truemeans an array exists).
Example Usage:
preload(getKey(0), fetcher)
renderWithConfig(<Page />)
await screen.findByText('data:true')
2. preload the fetcher function
Purpose: Ensures the fetcher function is called once during preload and not again during render.
Checks: Number of calls to fetcher before and after rendering.
Example:
preload(getKey(0), fetcher)
expect(fetcher).toBeCalledTimes(1)
renderWithConfig(<Page />)
await screen.findByText('data:foo')
expect(fetcher).toBeCalledTimes(1)
3. should avoid preloading the resource multiple times
Purpose: Preloading the same key multiple times calls the fetcher only once.
Effect: Prevents redundant network calls.
Key point: Multiple
preloadcalls with same key are deduplicated.
4. should be able to preload resources in effects
Purpose: Tests preloading inside a React
useEffecthook.Scenario: Preload runs on mount; later component shows data without additional fetch.
Demonstrates: SWR cache is populated by preloading even when done dynamically.
5. preload the fetcher function with the suspense mode
Purpose: Verifies preload works with
suspense: trueoption inuseSWRInfinite.Uses: React
SuspenseandProfilerfor React suspense tracking.Checks: Fetcher called once; Suspense fallback displayed correctly.
6. avoid suspense waterfall by prefetching the resources (Skipped)
Purpose: Tests if preloading multiple resources avoids sequential loading delays (waterfall).
Implementation: Preloads two pages with delays; asserts combined loading time is less than sum.
Skipped: Possibly flaky or incomplete.
7. reset the preload result when the preload function gets an error
Purpose: Tests error handling in preload.
Scenario: First preload attempt errors; on render, SWR detects error.
Then: Upon mutate (revalidate), SWR fetches fresh data (not cached preload error).
Key point: Preload cache resets on error.
8. dedupe requests during preloading
Purpose: Tests request deduplication during preload and subsequent renders.
Scenario: Fetcher has delay; multiple renders and preloads should not trigger duplicate calls.
Includes: Using React Profiler to track renders.
9. should pass serialize key to fetcher
Purpose: Ensures
preloadpasses the exact serialized key to the fetcher.Scenario: Preload called with a function returning the key.
Checks: The fetcher is called with the string key, not function.
10. should not break parallel option
Purpose: Tests SWRInfinite's
paralleloption with preloading.Scenario: Multiple pages fetched in parallel with different delays.
Checks: Data is fetched correctly and in parallel, total delay equals longest fetch.
11. should be able to preload multiple page
Purpose: Tests preloading multiple pages individually before rendering.
Scenario: Preload pages 0,1,2 separately and verify data concatenation.
Ensures: Partial preloads work as expected to build infinite list.
Important Implementation Details
Preload Function: From SWR, it caches data before component mount, allowing instant data availability.
useSWRInfinite: Provides pagination by accepting a
getKeyfunction that returns keys for each page index.Deduplication: Repeated preload calls for the same key are deduplicated to avoid multiple fetches.
Suspense Mode: Tested to ensure preload integrates with React Suspense correctly.
Error Handling: Preload cache resets on error to avoid stale error states.
Parallel Fetching: SWRInfinite's parallel fetch option works with preload, speeding up loading of multiple pages.
Interaction with Other Parts of the System
Utilities (
createKey,createResponse,renderWithConfig,sleep): Used to generate unique keys, mock responses with optional delays, render components within proper SWR config context, and simulate async timing.SWR Core: Uses
preloadanduseSWRInfinitefrom SWR library to manage caching and fetching.React Testing Library: Simulates user interactions and asserts UI changes.
React
SuspenseandProfiler: Used to test suspense-related behavior and rendering profiling.
Usage Examples
Basic preload usage with useSWRInfinite
const getKey = (index) => `page-${index}-myKey`
const fetcher = (key) => fetchDataForKey(key)
preload(getKey(0), fetcher)
function Page() {
const { data } = useSWRInfinite(getKey, fetcher)
return <div>data: {data ? 'loaded' : 'loading'}</div>
}
Preload in effect
useEffect(() => {
preload(getKey(0), fetcher)
}, [])
Mermaid Diagram: Flowchart of Test Suite Structure
flowchart TD
A[useSWRInfinite - preload Tests]
A --> B1[Basic preload correctness]
A --> B2[Fetcher call count tests]
A --> B3[Multiple preload deduplication]
A --> B4[Preload inside useEffect]
A --> B5[SWR suspense mode preload]
A --> B6[Waterfall avoidance (skipped)]
A --> B7[Error handling during preload]
A --> B8[Request deduplication during preload]
A --> B9[Serialized key passed to fetcher]
A --> B10[Parallel fetching option test]
A --> B11[Multiple page preloading]
B1 --> C1[Preload key, render, assert data]
B2 --> C2[Check fetcher call counts]
B3 --> C3[Preload same key multiple times]
B4 --> C4[Preload in useEffect, user interaction]
B5 --> C5[Suspense + Profiler integration]
B7 --> C7[Preload error, mutate, revalidate]
B8 --> C8[Delayed fetcher, multiple renders]
B9 --> C9[Preload with function key]
B10 --> C10[Parallel requests with delays]
B11 --> C11[Preload multiple pages separately]
Summary
This test file rigorously verifies the integration of preload with useSWRInfinite in various realistic scenarios, ensuring fast, deduplicated, and correctly handled data fetching for infinite paginated resources in React applications using SWR. It covers preload correctness, error handling, suspense compatibility, and parallel fetching, providing a robust foundation for SWR infinite loading functionality.