Adding a wrapper component to your Next.js app
How to use a wrapper component and add a common sidebar or header to it
All the pages on your site look more or less the same. There’s a chrome, a common base layer, and you just want to change what’s inside.
There’s a nav bar, a sidebar, and then the actual content.
How do you build such system in Next.js?
There are 2 ways. One is using a Higher Order Component, by creating a components/Layout.js component:
export default Page => {
return () => (
<div>
<nav>
<ul>....</ul>
</nav>
<main>
<Page />
</main>
</div>
)
}
In there we can import separate components for heading and/or sidebar, and we can also add all the CSS we need.
And you use it in every page like this:
import withLayout from '../components/Layout.js'
const Page = () => <p>Here's a page!</p>
export default withLayout(Page)
But I found this works only for simple cases, where you don’t need to call getInitialProps() on a page.
Why?
Because getInitialProps() gets only called on the page component. But if we export the Higher Order Component withLayout() from a page, Page.getInitialProps() is not called. withLayout.getInitialProps() would.
To avoid unnecessarily complicating our codebase, the alternative approach is to use props:
export default props => (
<div>
<nav>
<ul>....</ul>
</nav>
<main>
{props.content}
</main>
</div>
)
and in our pages now we use it like this:
import Layout from '../components/Layout.js'
const Page = () => (
<Layout content={(
<p>Here's a page!</p>
)} />
)
This approach lets us use getInitialProps() from within our page component, with the only downside of having to write the component JSX inside the content prop:
import Layout from '../components/Layout.js'
const Page = () => (
<Layout content={(
<p>Here's a page!</p>
)} />
)
Page.getInitialProps = ({ query }) => {
//...
} download all my books for free
- javascript handbook
- typescript handbook
- css handbook
- node.js handbook
- astro handbook
- html handbook
- next.js pages router handbook
- alpine.js handbook
- htmx handbook
- react handbook
- sql handbook
- git cheat sheet
- laravel handbook
- express handbook
- swift handbook
- go handbook
- php handbook
- python handbook
- cli handbook
- c handbook
subscribe to my newsletter to get them
Terms: by subscribing to the newsletter you agree the following terms and conditions and privacy policy. The aim of the newsletter is to keep you up to date about new tutorials, new book releases or courses organized by Flavio. If you wish to unsubscribe from the newsletter, you can click the unsubscribe link that's present at the bottom of each email, anytime. I will not communicate/spread/publish or otherwise give away your address. Your email address is the only personal information collected, and it's only collected for the primary purpose of keeping you informed through the newsletter. It's stored in a secure server based in the EU. You can contact Flavio by emailing flavio@flaviocopes.com. These terms and conditions are governed by the laws in force in Italy and you unconditionally submit to the jurisdiction of the courts of Italy.