React SSR with Next.js #2. Prefetching the data with getInitialProps

JavaScript Node.js

Today we expand our knowledge to build pages that are more complex and utilize more features from the Next.js framework. In this article, we learn how to fetch initial data for our components on the server side. This way, we can take even more work off the client side.

Fetching data

First, let’s display some data that we fetch from a REST API.

/pages/index.js

/components/Posts/index.js

In the above code, we fetch a list of posts and then display them. Let’s see how it turns out!

As you can see in the DevTools, the posts don’t render on the server. The above happens because the   function runs only at the browser. For similar functionality, we need to use the  .

getInitialProps

The  function runs both on the server and in the client. It is static and should return a promise. Anything that promise resolves becomes initial props of our component.

If you would like to know more about promises, check out Explaining promises and callbacks while implementing a sorting algorithm

There is just one small issue with the code above. As we’ve noted in the previous part of this series, our code runs in two different environments. We need to remember that the Fetch API does not exist in the Node.js environment.

There are a few ways in which we can approach it. If we still want to use Fetch API in our client-side code, we can use a package called isomorphic-unfetch. When you are in the browser, it uses the unfetch polyfill. If your code runs in Node.js, it switches to node-fetch.

A popular approach to   is to use async/await. Let’s combine it with  .

If you want to know more about async/await, take a look at Explaining async/await. Creating dummy promises

Let’s check out the server response now.

As presented in the DevTools, this time the server responds with fully rendered posts. The above happens because the Next.js framework waits for the   to resolve before rendering and sending the response.

The context within getInitialProps

The  receives a context object with properties:

  • query – query section of URL (parsed as an object)
  • asPath – the URL as a whole
  • pathname – the path section of URL
  • err – error object, if any occurs

If the   function runs on the server, it also contains:

  • req – HTTP request object
  • res – HTTP response object\

We can, for example, use it to limit the number of posts that we want to render.

In the example above, if we dont provide  , the   returns the original array

CSS support

So far we’ve only dealt with HTML and JS without any styling. With the Next.js framework, we can include CSS in our projects in a few different ways. The first one would be using the styled-jsx library because it comes with the Next.js framework.

It isn’t very powerful though and doesn’t support features like nesting.

Using sass or css

Another approach that we could take would be to import   or   files. To do that, we need additional plugins. We use   files in this example.

To incorporate it into our project, we need to create a   file.

next.config.js

/components/Posts/index.js

/components/Posts/style.scss

The Next.js framework automatically adds our files to the output HTML. In the production build, all scss files have a hash in the filename. Thanks to that we prevent the browser from caching if there is a new version of the stylesheets.

We can also use CSS modules if we prefer to, but we need to pass additional configuration to the   function.

next.config.js

Summary

In this article, we’ve covered how to prefetch the data using  . The examples that we’ve used show that doing it the right way can improve the performance of our application because the data is fetched on the server. That means that the browser does not have to do it and rerender the view.

Series Navigation<< React SSR with Next.js #1. Concept of Server Side Rendering & basics of routing
Subscribe
Notify of
guest
1 Comment
Oldest
Newest Most Voted
Inline Feedbacks
View all comments
mike
mike
4 years ago

Thanks for the good information. I am just thinking about using next.js. Two questions:

• Can one still use componentDidMount to fetch data on the client side or is that now bad practice?
• Can one use next.js to generate static pages, but still have a dynamic page? I’m assuming it must be possible with configuration on the server side — where the ‘static’ pages are delivered as is.

thanks