swr icon indicating copy to clipboard operation
swr copied to clipboard

useSWR('key', fetcher) calls fetcher non-deterministically even when `key` is in the fallback

Open AndrewRayCode opened this issue 2 months ago • 0 comments

Bug report

Description / Observed Behavior

<SWRConfig value={{ fallback: { a: 'b'} }}>

Combined with an inner component of

const { data } = `useSWR('a', () => { console.log('I should never be called'); });

Causes I should never be called to be logged. Note this is non-deterministic, the first few times this is called, it returns the fallback data. A requestAnimationFrame kicks off later which checks for the fallback data, and fails to find it, calling the fetcher.

Expected Behavior

Fallback data should never be re-fetched unless mutated.

Repro Steps / Code Example

This is a debugger screenshot from my app.

Screen Shot 2024-04-05 at 5 13 00 PM

useSWR is doing something incredibly tricky with destructuring, at a glance I don't understand the logic. What I want to point out in the screenshot is that PRELOAD is destructured to an empty object, while you can clearly see in the console that SWRGlobalState has the fallback data there ({ key: {'shader' => {...}, 'assets' => {...} }). This is the data in my app provided to <SWRConfig value={{ fallback: ... }}> in server side props. In this screenshot, key is 'assets', which is defined in the fallback data.

So useSWR() has the data properly in its cache, but it appears to discard it. It then calls the fetcher function.

Additional Context

"swr": "^2.2.5",

I'm doing SSR with Next.js to improve page load speeds. useSWR triggering a client fetch is defeating the purpose of this.

AndrewRayCode avatar Apr 06 '24 00:04 AndrewRayCode