How to invalidate query made by trpc inside a RSC

In the root page which is a server component, I have fetched some data like this
const posts = await api.posts.list({});
const posts = await api.posts.list({});
And I have passed the posts into another component that is a client component, so when we update a post from that client component how can we invalidate the posts in the root page important notes - I have used create-t3-app - in the root page I have used api imported from @/trpc/server - in the client component I have used api imported from @/trpc/react
6 Replies
Juraj98
Juraj986mo ago
If you're loading the posts using only trpc/server, there is no cache to invalidate. The data is returned as is, server rendered, and never refetched (unless you refresh the page). If you want to do data invalidation, you'll have to use trpc/react's useQuery. And if you want to use the data loaded on server, pass the posts to the client component and use them as initialData. So it'd look something like this:
export default async function Page() {
const posts = await api.posts.list({});

return <ClientComponent initialData={posts} />;
}
export default async function Page() {
const posts = await api.posts.list({});

return <ClientComponent initialData={posts} />;
}
"use client";

export default function ClientComponent({ initialData }) {
const posts = api.posts.list.useQuery(
{},
{ initialData },
);

return <div>...</div>;
}
"use client";

export default function ClientComponent({ initialData }) {
const posts = api.posts.list.useQuery(
{},
{ initialData },
);

return <div>...</div>;
}
And if you want to invalidate them, you can use trpc/react's api.useUtils() hook:
const utils = api.useUtils();

utils.posts.list.invalidate({});
const utils = api.useUtils();

utils.posts.list.invalidate({});
Also, if you're mutating the data and want to update the ones you have in your cache, you might want to optimistically update them instead of refetching. You can do that using utils.posts.list.setData().
deviana
devianaOP6mo ago
Thank you so much for your help I have tried router.refresh() and it works fine I don't know if this approach better than the other one you have mentioned But it definitly requires much less code to write
Juraj98
Juraj986mo ago
Really depends on what you're doing. But advantage of optimistic updates is that you don't need to query the data again. (Unless they could be changed externally or by other users. Then it depends too.)
deviana
devianaOP6mo ago
Also I want to mention that unstable_cache supposed to solve the problem but it didn't because in @/trpc/server we need the headers
Juraj98
Juraj986mo ago
I'm not sure what you mean, but I don't see how unstable_cache is related.
deviana
devianaOP6mo ago
unstable_cache may be similar to use query where you can attach a tag to the callback and you can revalidate it when needed
Want results from more Discord servers?
Add your server