Search code examples
javascriptreactjsnext.jsstatic-site-generation

How does NextJS with SSG and client-side navigation work?


Beginner to NextJS here and can't seem to find a direct answer to this question...

Does NextJS with SSG and client-side navigation require a server to send pre-rendered html to the client for every client-side navigation request? A request here would be a user navigating to another page within the same application.

Simple example:

Let's say I have a NextJS app with 3 simple pages (aka 3 .js files in the pages folder each exporting a React component). These pages are linked using the "link" component and I choose to do static site generation for all 3 pages. I then host this site on some web server. When a user first visits the site, I understand that the pre-rendered html (and any client-side javascript) has to be sent from the server to the client. However the following is unclear:

What happens after the initial request when the user navigates to another page in my simple app? Does this involve another round trip to the server to get the html for that page (pre-fetched or otherwise)? Or was all of the html and javascript for all pages bundled and sent in the user's initial request?

If the former is true (a server round trip will be made), will I need to specifically use client-side rendering techniques in NextJS to make the app a "true" SPA?


Solution

  • Next serves a SPA, but it does not serve the entire application at once. It will not serve the html / css / js bundle for a route if it is not needed yet. It will however prefetch the bundle for a route if a link is visible in the viewport. From https://nextjs.org/docs/api-reference/next/link

    prefetch - Prefetch the page in the background. Defaults to true. Any <Link /> that is in the viewport (initially or through scroll) will be preloaded. Prefetch can be disabled by passing prefetch={false}. When prefetch is set to false, prefetching will still occur on hover. Pages using Static Generation will preload JSON files with the data for faster page transitions. Prefetching is only enabled in production.

    Once the bundle for that route is received, it will not request it again (assuming this is a static route, ie. not using getServerSideProps), so navigating away from and back to this route will be faster after the first load / prefetch.

    If you want to prefetch your routes manually you can use router.prefetch: https://nextjs.org/docs/api-reference/next/router#routerprefetch

    Once all of your routes have been fetched, the application will act as a standard SPA, since your client now has the entire application bundle.