Supercharge your SEO game in 2020 - powered by getStaticProps
Tags: react, tutorial, webdev, javascript
Published: 2020-04-29 16:25:21

This is mainly useful for websites that use React/NextJS with a CMS (Content Management System) integration. No matter, whether it's WordPress, Contentful, Prismic or any other CMS. This concept is highly relevant for companies that require non-engineers to update the content easily. Whether, it's a change in the content, A/B testing or conversion-rate-optimization related. There are many reasons why the content of a website gets updated quite often throughout the year. 

Right now, the content will be loaded from the CMS when a visitor gets to your website. If you have quite some content, it will take time to first load it, then process the JavaScript and ultimately render it. This will have an impact on your page-speed and therefore your SEO. 
Especially with requests that carry a ton of extra 'weight' such as WordPress, this is quite a problem when trying to achieve a 'perfect' performance score. 

Long story short, welcome to `getStaticProps` powered by NextJS. If you have worked with NextJS in the past, you are most likely familiar with `getInitialProps`. It's a lifecycle method that allows loading the content prior to rendering. There are ways to cache those pages but it can become quite tricky and messy. 

`getStaticProps` is part of their latest release version [9.3](https://nextjs.org/blog/next-9-3) and offers **_Next-gen Static Site Generation (SSG)_** Support. 

Sounds very fancy, cool, amaze-balls and quite frankly. It is pretty amazing. 

## Coding Example
When looking at a typical file-based structure that NextJS has implemented your page will look like this:
```
// You can use any data fetching library
import fetch from 'node-fetch'

// posts will be populated at build time by getStaticProps()
function Blog({ posts }) {
  return (
    <ul>
      {posts.map(post => (
        <li>{post.title}</li>
      ))}
    </ul>
  )
}

// This function gets called at build time in the Node.js environment.
// It won't be called on client-side, so you can even do
// direct database queries. See the "Technical details" section.
export async function getStaticProps() {
  // Call an external API endpoint to get posts.
  const res = await fetch('https://.../posts')
  const posts = await res.json()

  // By returning { props: posts }, the Blog component
  // will receive `posts` as a prop at build time
  return {
    props: {
      posts
    }
  }
}

export default Blog
```

As you can tell instead of being a lifecycle method getStaticProps is a function that's getting exported. 

Furthermore, please note that getInitialProps will not be discontinued for now but the team recommends leveraging the new methods.

- `getStaticProps` Fetch during build build time
- `getServerSideProps` Fetch when requested & before rendering (previously - `getInitialProps`)
- `getStaticPaths` specifically used to pre-render dynamic routes such as blogs.

## Mixed Content Dynamic + Static

Often times you might want to mix those two use cases. You want to leverage `getStaticProps` for landing pages but rather keep fetching the content upon a user request for use cases such as blogs and resources since those are getting updated rather often. This is not a problem. Feel free to use either one from page to page. 

## Custom src Folder 

Are you leveraging a custom `src` folder? This is quite usual for larger projects to have the ability to have more structure. Just export that method in addition to your component and you are good to go as well. Just make sure to add the export. 

### Before
```
import { Home } from '../src/pages'

export default { Home, getStaticProps };
```

### After
```
export { Home as default, getStaticProps } from '../src/pages'
```

## _app.js Concept
This is probably the most difficult topic to find solid information and guides. First of all, this feature is not fully supported by NextJS yet. This is on purpose for right now. Therefore, if you are looking for `getStaticProps` within `_app.js` you won't have any luck.

**BUT** there is a way to solve this - consider it as a well working workaround. I haven't seen any issues or downsides with this approach. 

Within your `_app.js` leverage the lifecycle method `getInitialProps` and within that method check whether the component has the method `getStaticProps` or `getServerSideProps` and act accordingly.

Here's an example:
```
MyApp.getInitialProps = async ({ Component, ctx }) => {
  try {
    // Retrieve content documents
    let pageProps = {};
    let navContent = {};
    let contactContent = {};

    navContent = await Client.getSingle('nav_bar');
    contactContent = await Client.getSingle('contact_form');
    if (Component.getServerSideProps) {
      pageProps = await Component.getServerSideProps(ctx);
      return {
        navContent: navContent.data,
        contactContent: contactContent.data,
        pageProps
      };
    }

    return {
      navContent: navContent.data,
      contactContent: contactContent.data
    };
  } catch (error) {
    console.error(error);
    return error;
  }
};
```

As you can see we are checking for `getServerSideProps` and only then return `pageProps`. Meanwhile, we are still returning the `navBar` content centrally. This is something that you can fetch statically as well.  

_________________________________________________________________________

This post was originally published [here](https://fullerstack.io/supercharge-your-seo-game-in-2020-powered-by-getstaticprops/).