The difference between Gatsby and Next.js

When it comes to server-side-rendering with React, there are two main frameworks to consider: Gatsby and Next.js, but what are their differences? Which one should you choose and when?

The difference between Gatsby and Next.js

Both gatsby and next.js are frameworks which aim primarily at adding server-side-rendering (SSR) to react applications. Due to their similarities it can be difficult to know when to choose which framework and how they're different.

Static vs Dynamic SSR

Static and dynamic SSR is what the difference basically comes down to. Gatsby is focused on static SSR, while Next.js initially only offered dynamic SSR but now also supports static SSR.

In static SSR creates a prerendered version of the application at build time, whereas dynamic SSR does this at runtime for a request.

To give you an idea of these terms let's quickly walk through the steps of building and serving a modern JAM stack page.

Once the site is finished coding, we need to build or compile or bundle it into something that is optimized and usable for a web browser. This is the build step. Our pages are then served by a web server. Browsers call the server to request our site. At this point in time, we know who wants to view our website now. This is where dynamic SSR would now create the final prerendered site before sending it off to the client. In contrast, static SSR does not need to perform any additional processing and instead immediately answers with the result of it's previous build step.

The difference between these two approaches has a strong impact on how complex it is to serve a site. A static site is basically nothing more than a bunch of files somewhere on a disc that are requested by a browser. Therefore, serving them is much simpler and any simple web server, even CDNs can serve a complete static site. This is quite an advantage when it comes to performance, since the computational cost of serving such a site is nearly zero.

In contrast, dynamic SSR needs to be done on the server, while the site is served. Therefore, an application that is able to do this needs to run on the server and a large number of requests requires some significant work on the application server, making dynamic SSR approaches more difficult to scale. This is the price you will have to pay for the additional flexibility of dynamic SSR.

Static SSR - Where Gatsby Shines

static SSR

Gatsby does exactly one thing, and it does it really well. Creating static sites. When it comes to taking content from various sources and generating a static site, Gatsby really shines.

The commitment to static SSR really shows in the whole Gatsby ecosystem. Templates are mostly focused on use cases of static sites, plugins are mostly about sourcing data for static sites, CMSes and image optimization is completely done during build time.

The fact that Gatsby is often used to replace the frontend of a Wordpress site, while sometimes still using Wordpress as a headless CMS, is one of the most typical use cases for Gatsby.

However, these days, Next.js also has good support for static SSR. In theory it would be equivalent to Gatsby. In practice things are more difficult. Oftentimes you will find that certain things only work for dynamic pages. After spending a little time with Next.js for static sites you will realize, that the baked in image component does not work for static sites and things like generating a sitemap for a static site can be challenging. There also isn't that much support to pull data from a CMS, since Next.js typically sources data from a much wider range of sources.

Dynamic Content - Where Next.js might be your only option

dynamic SSR

Sometimes it is the case, that the underlying data of a website changes very frequently or the content to be shown depends on dynamic factors related to the request itself. This could include a client's location, whether a user is logged in and in a broad perspective also time.

In such cases it is often either impractical or impossible to rebuild the whole site with a static approach to always be up to date. Next.js and dynamic SSR provides the solution to this problem. Making it possible to take a request and render a site specifically for this point in time and this specific client requesting it.

Dynamic SSR is something that is practically impossible with Gatsby. However, there is one thing we have to keep in mind and people often forget about it: Gatsby is not completely off the table if we have dynamic content in our sites.

Next.js is the only option if we have dynamic content that needs to be served via SSR. If we do not need SSR for something on our site, we can often just use a plain React approach with client side rendering in such cases. A typical example is content that is just shown to users which are logged in. Your favorite search engine crawler will never see your site as a logged in user, making it much less of an SEO issue. Additionally, users that are logged in have already visited your site and will typically do so frequently, which means that they already have content and assets of your site in their browser cache, making the initial site performance much less of an issue.

Additionally if content changes are not very frequent and the time between a content change and the change being reflected on the page is not critical, there's always the option to rebuild a gatsby page.