Abstract

Next. Js is a production-oriented React framework with zero configuration and API routing features that allow developers to focus on application pages, components, and logic. The SSG and SSR hybrid modes and powerful incremental static generation feature allow for optimized load speed and SEO from birth. The Next. Js framework is therefore ideal for the development of applications such as website home pages, blogs, news, e-commerce, etc.

In addition to a purely static homepage, all scenarios involve the need for dynamic data acquisition, such as articles, news, product information, etc., so how to update data without sacrificing user experience and SEO is a problem that every Next. Js developer needs to face.

The Data Fetching section of the official documentation provides a method for Fetching Data from next.js. This paper will introduce three methods of obtaining dynamic data by using next.js based on actual requirements, and analyze the applicable scenarios of each method to see how to use next.js to achieve maximum “dynamic and static combination”. Since the official documentation of next.js is good enough, this article does not cover any information other than Data Fetching. Beginners are advised to read this article after reading Pages and Data Fetching at least.

Method 1: Server-side Rendering (SSR)

Server-side rendering means that after a user requests a page, the server first obtains dynamic data and then generates page data and returns it to the front end for display. This is contrary to the most common way of one-page application, which first renders the page and then updates the part with Ajax request. Its advantages are that it is crawler friendly, SEO beneficial, and the server side tends to process requests much faster than the client side, resulting in faster page rendering to the user.

Next.js provides the getServerSideProps method to implement dynamic data update based on SSR. The basic usage is as follows:

function Page({ data }) {
  // Render data...
}

// This gets called on every request
export async function getServerSideProps() {
  // Fetch data from external API
  const res = await fetch(`https://... /data`)
  const data = await res.json()

  // Pass data to the page via props
  return { props: { data } }
}

export default Page
Copy the code

The props property returned by the getServerSideProps method is passed in as the initial props of the page component, so that the page is updated each time it is rendered.

Note that the SSR approach does not reduce the number of requests, as front-end Ajax rendering still sends dynamic data requests every time the page is refreshed. Therefore, SSR is more suitable for scenarios with high requirements on real-time data, such as real-time data statistics and real-time scores. What if I only update the author once a month? Isn’t using SSR a waste of server performance?

Approach 2: Pre-render at build time (SSG)

SSG happens at build time, meaning that the Next. Js application gets dynamic data once at build time and then generates a static page file based on that data. The application is completely static at run time. The reason I want to classify this completely static runtime approach as a dynamic approach to data retrieval has to do with the deployment of next.js. The author’s own Vercel is an excellent platform for deploying Next. Js applications, and the platform of choice for many Next. Js applications. The deployment process is insensitive to the client, so it is essentially a dynamic run-time update experience for the client, perfectly suited to the needs of the author of the previous month.

Next.js provides the getStaticProps method to implement SSG on a page. The basic usage is as follows:

// 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 on server-side.
// 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.
  // You can use any data fetching library
  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
Copy the code

The usage is basically the same as getServerSideProps, except that the internal running mechanism is different.

So what if you don’t want to waste server performance, but you have some real time requirements? You can’t deploy every few hours or minutes, can you?

Method 3: Incremental Static Regeneration

Here comes the most powerful feature of next.js. Incremental static is generated at build time, on the basis of pre-rendered support for page setup expired inspection intervals, at most, in an interval can obtain a latest data, if there is a change will generate a new static page file data, and if the new page generation and data failure also don’t have to worry about, Next. Js will retain the old page caching, This enables dynamic static file generation. The advantages of static files are retained while giving consideration to timeliness.

The incremental static generation feature can be turned on simply by adding a revalidate field to the return object of getStaticProps to indicate the expiration detection interval. However, since there may be new or invalid routes, you should also add getStaticPaths to tell next.js which route pages should be prerendered, as shown in the following example:

function Blog({ posts }) {
  return (
    <ul>
      {posts.map((post) => (
        <li>{post.title}</li>
      ))}
    </ul>)}// This function gets called at build time on server-side.
// It may be called again, on a serverless function, if
// revalidation is enabled and a new request comes in
export async function getStaticProps() {
  const res = await fetch('https://... /posts')
  const posts = await res.json()

  return {
    props: {
      posts,
    },
    // Next.js will attempt to re-generate the page:
    // - When a request comes in
    // - At most once every 10 seconds
    revalidate: 10.// In seconds}}// This function gets called at build time on server-side.
// It may be called again, on a serverless function, if
// the path has not been generated.
export async function getStaticPaths() {
  const res = await fetch('https://... /posts')
  const posts = await res.json()

  // Get the paths we want to pre-render based on posts
  const paths = posts.map((post) = > ({
    params: { id: post.id },
  }))

  // We'll pre-render only these paths at build time.
  // { fallback: blocking } will server-render pages
  // on-demand if the path doesn't exist.
  return { paths, fallback: 'blocking'}}export default Blog
Copy the code

Revalidate: 10 indicates that data will be updated at least once every 10 seconds. Attention should be paid to the 10 seconds with setInterval timer is not a concept, it is throttling the data update request, only a request for 10 seconds after the first page of the trigger updates, if there is no request will not be updated, so if less site visits, this method is almost like pure static file service to save server performance. However, there is a lag of up to 10 seconds for updates, and the larger the revalidate setting, the longer the average lag time will be!

conclusion

This paper introduces three dynamic data acquisition methods provided by Next. Js, which are server side rendering (SSR), build-time pre-rendering (SSG) and incremental static generation (ISR). All three schemes can ensure the page loading speed and SEO advantages of Next. SSR has the highest real-time performance but also consumes the most performance. SSG has minimal strain on the server but is also less flexible in updating data; ISR can use expiration detection interval to find a suitable balance between the first two.

To sum up, ISR is a method that can adapt to most application scenarios, but it should also be remembered that data acquisition is only page-level logic, and we can flexibly use these three methods for different pages. The purpose is to use SSG as much as possible. SSR is used for data with high real-time requirements, and ISR is used for the rest. This maximizes the benefits of Next. Js for any application.