Next.js - Incremental Static Regeneration(ISR)



Next.js ISR

Incremental Static Regeneration (ISR) is a feature in Next.js by which the static pages can be updated after deployment, without requiring a full rebuild. This means that pages can be statically generated at build time and then incrementally updated as needed while the application is running.

How it works?

  • Initially, all the pages are pre-rendered at build time.
  • When a user requests a page, Next.js checks if the page has expired (based on a revalidation time)
  • If the page has expired, Next.js generates a new version in the background while still serving the old version to users.
  • Once the new version is generated, the old version is deleted and the new version is served to the user on subsequent requests.

Example of ISR in Next.js

In the following example, we will create a page that fetches data from an API and displays it on the page. Here we set revalidate: 10, this ensures that the page updates at most every 10 seconds when a new request comes in.

// File: pages/index.js

import { useEffect } from 'react';
import { getServerSideProps } from 'next';

export async function getStaticProps() {
    const data = await fetchData(); // Fetch data from API 
  
    return {
      props: { data },
      revalidate: 10, // Regenerate the page every 10 seconds
    };
  }

  export default function Home({ data }) {
    return (
        <div>
            <h1>Home Page</h1>
            <p>This is the home page.</p>
            <div>{JSON.stringify(data)}</div>
        </div>
    );
}

Output

ISR Example

Revalidation On-demand

On-demand revalidation is a technique used to revalidate the cache based on an event. This is used to ensure that the cache is up-to-date and that the data is not stale. In the code below, we have a page that fetches posts from an API endpoint. We have a button that revalidates the cache when clicked. The code snippet below shows how to use the revalidatePath function to revalidate the cache.

import { revalidatePath } from 'next/cache'

interface Post {
  id: number
  title: string
  body: string
}

async function getData() {
  const res = await fetch('https://jsonplaceholder.typicode.com/posts?_limit=3', {
    cache: 'no-cache'
  })

  const posts: Post[] = await res.json()
  
  return {
    timestamp: new Date().toISOString(),
    posts,
    message: 'Posts will update when revalidated'
  }
}

async function handleRevalidate() {
  'use server'
  revalidatePath('/')
}

export default async function Home() {
  const data = await getData()
  
  return (
    <main>
      <h1>Path Revalidation Demo</h1>
      
      <div>
        <p>Last Updated: {data.timestamp}</p>
        <p>{data.message}</p>
        
        <div>
          {data.posts.map(post => (
            <div key={post.id}>
              <h2>{post.title}</h2>
            </div>
          ))}
        </div>
      </div>
      
      <form action={handleRevalidate}>
        <button type="submit">
          Fetch New Posts
        </button>
      </form>
    </main>
  )
}

Output

The image below shows the output of the code snippet above. When we click the button, the cache of the home page is revalidated, and new post is loaded.

Next.js Path Revalidation

Time-based Revalidation

Time-based revalidation is a technique used to revalidate the cache after a specific time period. This is used to ensure that the cache is up-to-date and that the data is not stale. In the code snippet below, we have a page that revalidates every 5 seconds.

export const revalidate = 5 // revalidate every 5 seconds

async function getData() {
  // Simulate API call
  return {
    timestamp: new Date().toISOString(),
    randomValue: Math.random(),
    message: 'This page revalidates every 5 seconds'
  }
}

export default async function Page() {
  const data = await getData()
  
  return (
    <main>
        <h1>5 Second Revalidation</h1>
        <p>Timestamp: {data.timestamp}</p>
        <p>Random Value: {data.randomValue}</p>
        <p>{data.message}</p>
        <p>
            Next revalidation will occur 5 seconds after the last 
            revalidation
        </p>
    </main>
  )
}

Output

The image below shows output of the code snippet above. When we continuously refresh the page, we can see that the page revalidated (the new random number generated) only after every 5 seconds.

Next.js Time-based Revalidation
Advertisements