swr
swr copied to clipboard
Mutate's async function data is set to `undefined` with `getServerSideProps` and no revalidation
Bug report
Description / Observed Behavior
Mutate Based on Current Data Docs
mutate
's async function data is set to undefined
when used with Next.js getServerSideProps
fallback and revalidateIfStale: false
even though the fallback works fine and data from the server is rendered right away.
Expected Behavior
mutate
async callback has data from the server w/o refetching on the client
Repro Steps / Code Example
Click do mutate
button. Check that local items
output is undefined
Go to About page and back to Home page. Click do mutate
button: local items
output is updated as swr
data was updated on the client.
Setting revalidateIfStale
to true
fixes the issue as the data being refetched on the client.
Additional Context
SWR version 2.1.1
Thanks for your detailed reproduction !
Since the fallback
data are not persisted in cache
, mutate
is not able to access it directly. This is a expected behavior.
You can use useSWRConfig
to access fallback
data as a workaroud
const { fallback } = useSWRConfig();
Would you mind to share your intention and actual use case for the pattern used in this example ? It would be helpful for us to build a better developer experience in the future.
I have a page with saved items. Each item can be removed from the list. The page is rendered on the server initially. And I use mutate with async function to get access to the data.
The only way to fix it is to set revalidateIfStale: true
, but in this case, the same data is fetched on the client on the first render. which is fine as a workaround, but seems weird given that I already have the data from the server in the fallback
.
And I've extracted a generic hook for those saved items and hidden items with the same logic.
And it's used in different places (like the page itself, widgets, and other places). And the mutate
itself is passed as an argument to some other function. So passing data from the fallback
property is not that convenient when I have multiple places where the hook is used given that the data is already in (but not cached).
@promer94 hi mem , i got the trouble with call swr from client after get init data from server my logic is
export const useUserProfile = () => { const endPoint =
/api/profile?epath=${EProfilePath.GET_PROFILE}; console.log(endPoint); return useSWR<TProfileRes>(
/api/profile?epath=${EProfilePath.GET_PROFILE}`, fetcher, { revalidateIfStale: true });
};
export const useSSRUserProfile = ({ fallbackData }: { fallbackData?: TProfileRes }) =>
useSWR<TProfileRes>(/api/profile?epath=${EProfilePath.GET_PROFILE}
, fetcher, {
fallbackData,
});`