Angular SSR for an e-commerce application

Development of the aXpel shop

In this post, I describe my experiences in developing the aXpel Shops with Angular SSR (Server Side Rendering). The main focus is on how Angular SSR can be used to achieve very fast page views, which play an important role in e-commerce and for search engine optimisation (SEO).

Author: Roberto De Simone
Date: 21/07/2024
Updated: 03/11/2024

Image symbolising lightning-fast speed in a futuristic world

Image ‘lightning fast’ created with DALL-E 3

On this page

Why Angular SSR

Angular is primarily known as a JavaScript framework for creating web apps. Web apps are interactive websites that require a high level of JavaScript in order to solve problems. Web apps are also referred to as Single Page Applications (SPA). With these, the entire application is loaded into the browser as a JavaScript bundle when the URL is called up. The page is then built in the browser - HTML is created from the JavaScript bundle. Calling up the first page therefore takes a little longer, after which a well-developed Angular application is lightning fast and offers a very good user experience. Search engine optimisation (SEO) does not usually play a role in single-page applications.

However, if you want to develop a web application with Angular in which SEO plays a central role, Angular SSR comes into play.

With Angular SSR, the page is first built (rendered) on the server when a URL is called up. The JavaScript, which is executed in the browser during an SPA, is executed on the server and the page is created on the server. The page is then transmitted to the browser together with the JavaScript bundle. The JavaScript bundle is executed again in the browser and the page is created a second time. This process is called hydration (the problems associated with this process will be discussed repeatedly below). In the past, the DOM was completely deleted in the browser during the hydration process and then rebuilt. Since Angular 16, parts of the DOM are retained if the server code and browser code generate the identical result. This process (partial hydration) is now being continuously improved with new Angular versions, which has a positive impact on the Core Web Vitals values (more on this in the next section).

Rendering the page on the server has two advantages:

  1. The page can be crawled better by bots (SEO)
  2. The user sees the result of the page views more quickly (Core Web Vitals)

Angular SSR and Core Web Vitals

Angular SSR has been around for many years. However, it has so far played a somewhat subordinate role in the Angular team. This is also reflected in the fact that the documentation only comprises one page and that there are numerous open issues in GitHub. Nevertheless, it actually served its purpose until Core Web Vitals became a ranking factor for search engine optimization.

Essentially, Google uses the Core Web Vitals values to determine the speed of a page. To achieve high Core Web Vitals values, the user must immediately see the page they are viewing in full and it should also be immediately interactive.

This is not easy to achieve with the process of how Angular builds a page.

As described above, the page is built twice:

  1. On the server
  2. On the browser

If there is a difference between the DOM of the page on the server and the DOM in the browser, this leads to a layout shift. Core Web Vitals considers a layout shift to be an incomplete page, which leads to poor values. As a developer, you must ensure that the code is implemented in such a way that no layout shifts occur - the DOM must be identical in both cases.

The importance of a CDN and caching the HTML page

So that a page rendered on the server can be transmitted to the user quickly, it must of course also be built up quickly on the server. The more JavaScript that has to be executed, the slower the page is built. Adding additional libraries, such as Angular Material, also slows down the execution speed. However, you don’t want to do without useful libraries either.

Diagram of how an Angular page is cached in the CDN and REDIS cache in the Google Cloud

In addition to optimising the code with Lazy Loading (only the code that is currently needed to build the page is executed and transmitted), I believe that for a ‘large’ Angular application, fast transmission of the pages can only be achieved by caching the HTML pages. By caching the HTML, the JavaScript no longer needs to be executed. The page is already rendered and available in the cache. This can be done with the help of a CDN (Content Delivery Network) and by caching in REDIS. The excellent ISR library from Enea Jahollari is available for the latter! In addition, the assets (JavaScript, CSS, images) must be cached in the CDN.

Another strategy is to prerender the pages. This means that the pages are already created when the application is published. However, this strategy only makes sense if the content is largely static. Such a strategy is less practicable for an e-commerce solution with changing products and prices.

Optimising images

In addition to caching, image optimization is an important component for good Core Web Vitals values. Images must be provided in optimal sizes and with optimal compression. Angular provides a directive for image optimisation for this purpose.

The importance of a small JavaScript bundle

The main problem in achieving good Core Web Vitals values is the time it takes to interact with the application. To achieve this, the JavaScript bundle must be loaded and processed as quickly as possible. A small JavaScript bundle shortens the loading and processing time. The loading time can be further optimised by caching the JavaScript bundle in the CDN. A slow network and weak mobile devices are the bottleneck.

Chrome development tools to improve the Core Web Vitals values

When optimising the application for Core Web Vitals, it is important that the points criticised in the Lighthouse Reports of the Chrome development tools are rectified as far as possible. It is also important to know that you can get the true Core Web Vitals values from Google Search Console and see how fast the page really is for users. Pagespeed Insights is only meaningful to a limited extent, as the values are calculated with a heavily throttled network and a weak mobile device. Angular SSR is not suitable for such constellations, at least not yet.

Core Web Vitals and Soft Navigation

After the JavaScript of an Angular application has been executed in the browser (hydration), the entire application is loaded and there are no more complete page views on the server. Navigation to another URL is then instantly, which naturally leads to a very good user experience. This type of navigation is also known as soft navigation.

Unfortunately, Core Web Vitals only takes soft navigation into account to a limited extent, but this has been recognised and is to be changed.

How relevant are the Core Web Vitals values for SEO

As written, the Core Web Vitals values are one of many ranking factors. Google loves fast pages, but good, helpful content that is clearly structured and accessible is still far more important. It is even more important that the page has authority on a topic and is well visited in order to achieve a top position in the search results. Extensive content and backlinks are more than helpful for this.

The future of Angular SSR with Zoneless and Event Replay

Core Web Vitals has disrupted the entire JavaScript framework landscape. Rendering on the server and minimising the JavaScript that is initially transmitted to the browser has become drastically more important. Fortunately, Angular has not escaped this trend. Angular is also referred to as an Angular renaissance. The merging of Angular with Google’s internal JavaScript framework Wiz, which is used for high-speed applications, also shows that a change is taking place.

Angular applications previously used the Zone.js library to detect changes to data. Zone.js uses wrappers of the native DOM events and XHR calls to detect when something has changed in the data. However, this is associated with JavaScript and several query cycles. In zoneless applications, changes are only made when Angular receives a notification that something has changed. This is where signals come into play, which tell Angular that changes need to be made. Signals are wrappers around values that indicate when a value has changed. In other words, the developer of zoneless applications is responsible for notifying Angular that a change has taken place.

Event Replay is another concept that will lead to a reduction in JavaScript. This is currently still in an experimental phase. More information can be found on the Angular blog.

Zoneless applications and other innovative concepts should significantly improve the execution speed of an Angular application, which will also lead to faster page loading on the server.

Final considerations

Thanks to aggressive caching, the Core Web Vitals values of the aXpel shop’s URLs in the Google Search Console are all in the green for both mobile and desktop.

The effort for all the optimisations and caching is high.

With Angular SSR, you also have to bear in mind that the user only ever calls up one URL from the server for a session. All other page changes are soft navigations. This means that you have to use a service to ensure that all relevant URLs reach the REDIS cache or the CDN, as you do not know which URL the user uses to access the Angular app (e.g. product that is googled).

Ideally, a page should already be fast enough without caching the HTML. The CDN is then an additional bonus.

Despite all the future improvements in Angular, which I am looking forward to, and the very good user experience of an Angular application, I am not sure whether a multipage framework is not the better choice for SEO-relevant applications. With such a framework, the JavaScript bundle can be kept to a minimum and fast pages can be created without hacks. The fact that the complete page is loaded from the server (or CDN) with every navigation means that it can be automatically transferred to the CDN. Another interesting development in Chrome is the speculative caching of URLs. Starting from the first page loaded, further pages are loaded in the background and saved in the browser cache. As with an SPA, further URL calls are then lightning-fast.

However, I would not want to miss the excellent developer experience in Angular in the future.