Context provider -- server side?
Answered
Transvaal lion posted this in #help-forum
Transvaal lionOP
Hey -- just wanted to ask on top of this https://nextjs-forum.com/post/1142406350228422696
I have a client component navbar with a cart and state, and outside the navbar I have items that you can add to your cart. Items are server components, add to cart button is a client component. I was trying to figure out how exactly I can update the cart using the add to cart button, without making the entire website client-sided by having the state on the root, parent of the navbar and the items.
I stumbled upon useContext and thought it could be the solution to this:
I have a client component navbar with a cart and state, and outside the navbar I have items that you can add to your cart. Items are server components, add to cart button is a client component. I was trying to figure out how exactly I can update the cart using the add to cart button, without making the entire website client-sided by having the state on the root, parent of the navbar and the items.
I stumbled upon useContext and thought it could be the solution to this:
If I have a ContextProvider using react useContext hook, and wrap the entire website in these, will the children still be server-rendered? Is it possible to have server components with client components that access the contextprovider? Or in a more visual way, is the following possible?
<ContextProvider>
<Navbar>
<SomeServerComponent />
<Cart /> //a client component that uses useContext
</Navbar>
<ServerComponent>
<AddToCartButton /> //a client component that also uses useContext to update cart?
</ServerComponent>
</ContextProvider>Answered by Asian black bear
Server componenents can be
{children} of client components, they only cannot be imported into the source files of a client component.8 Replies
European sprat
Context / state only works in client components. If you're clicking a button in a client component and that makes some request which updates data on your server and you then want a server component which displays that data to update, you'll need to use router.refresh() in the client component or revalidatePath/tag
@European sprat Context / state only works in client components. If you're clicking a button in a client component and that makes some request which updates data on your server and you then want a server component which displays that data to update, you'll need to use router.refresh() in the client component or revalidatePath/tag
Transvaal lionOP
Yes, but what if I want to have two client components (an add to cart button and a cart, for example) inside a parent server component and want to be able to click a button to update cart contents?
Can I have the ContextProvider wrap the whole thing? Would that render everything as client components?
@Transvaal lion Yes, but what if I want to have two client components (an add to cart button and a cart, for example) inside a parent server component and want to be able to click a button to update cart contents?
Asian black bear
Server componenents can be
{children} of client components, they only cannot be imported into the source files of a client component.Answer
Asian black bear
the context would still be on the client side, but it kind of silently passes over server components (which obviously can not see the data inside of the context)
This document tells you exactly how to do it: https://nextjs.org/docs/getting-started/react-essentials#context
European sprat
Can also see it in action in Vercel's app playground: https://app-router.vercel.app/context
Transvaal lionOP
Awesome, thank you both lots ðŸ™ðŸ™ðŸ™