Angular-Renaissance Teil 1: Server-Side Rendering und Hydration

Seite 2: Das Ende der Destructive Hydration

Inhaltsverzeichnis

Vor Version 16 beherrschte Angular zwar SSR, allerdings durch @nguniversal, das nicht Bestandteil des Angular-Repositorys war. Die Drittbibliothek war zwischen einem offiziell unterstützten und einem Community-Projekt einzuordnen.

Die darin eingebaute Hydration war "destructive". Das bedeutet, dass der geladene JavaScript-Code sich nicht mit Event Handlern bei den bereits gerenderten DOM-Elementen registrierte ("einnistete"), sondern das Framework kurzerhand alle DOM-Elemente löschte und das Rendering von Neuem begann. Aus diesem Grund existiert beim Aufbau von alten Angular-Anwendungen eine Phase, in der die bereits gerenderte Seite kurz weiß wird.

Im Vergleich zu anderen Frameworks hatte Angular auf dem Gebiet der Hydration etwas das Nachsehen. Das ändert sich aktuell. Mit Version 17 ist die "non-destructive" Hydration stabil, und nicht @nguniversal liefert SSR, sondern hochoffiziell @angular/ssr. Beim Neuerstellen mittels npm init @angular wird standardmäßig bereits der ApplicationBuilder eingesetzt. Dieser basiert auf esbuild und beherrscht SSR.

Bei einem Update von einer früheren Version kann man SSR mit dem Befehl ng add @angular/ssr nachinstallieren. In meinem Versuch hat das recht gut funktioniert, es waren jedoch einige manuelle Eingriffe im Bereich der bootstrapApplication-Methode notwendig. Sie sollten allerdings keine großen Probleme verursachen.

Neben einer Standard-Hydration bringt der neue ApplicationBuilder auch eine Prerendering-Option mit, die unter dem Namen Static Site Generation (SSG) bekannt ist. Hier iteriert Angular während des Builds über sämtliche Routen und generiert diese Routen vor. Dadurch ist die Auslieferung zur Laufzeit noch einmal signifikant schneller. Es muss am Server nichts mehr gerendert werden.

Für Seiten mit sich stetig wandelndem Inhalt ist SSG jedoch nicht optimal. Man möchte möglicherweise statisch bereits die neuesten News ausliefern, statt erst mittels Hydration die Daten zu beziehen. Dazu kommt noch, dass die Http Requests, die auf dem Server liefen, gecacht sind. Sollte also auf dem Client ein Request an ein Backend gehen, so erhält der Browser die alte und initiale Antwort. Das ist für eine Website mit aktuellen Inhalten somit keine Lösung.

Prerendering ist demnach nicht immer das geeignetste Mittel. Aus diesem Grund kann man es auch über die angular.json deaktivieren. Bei dem Anwendungsfall mit der Newsseite sollte man zudem das Caching der Http Requests ausschalten.

Bei Angular hat das Thema Hydration einen hohen Stellenwert. So soll in zukünftigen Versionen aktiviertes SSR die Standardeinstellung werden.

Doch damit nicht genug: Das Angular-Team hat sich Unterstützung vom Entwicklungsteam des zweiten hauseigenen Frontend-Frameworks Wiz geholt. Wiz ist nicht Open Source und Google setzt es vor allem für schwergewichtige Anwendungen wie Google Photos ein.

Dieses Framework ist mit sehr weit fortgeschrittenen Hydration-Technologien ausgestattet, wie sie vom Open-Source-Framework Qwik bekannt sind. Dadurch entstehen Bundles, die sich nach den Event Handlern aufteilen. Eine Hydration im eigentlichen Sinne findet nicht statt. Erst bei Ausführung des Event Handlers wird der JavaScript-Code geladen. Diese Technik ist auch unter den Begriffen Resumability oder Progressive Hydration bekannt.

Darstellung der Resumability/Progressive Hydration

(Bild: Rainer Hahnekamp)

Sollte das Angular-Team es schaffen, diese Technologie in sein Framework einzuführen, würde es sich aus einer SSR-Perspektive auf die vorderen Ränge katapultieren und die anderen großen Frameworks technisch hinter sich lassen.

Hydration und Signale sind in ihren Grundfunktionalitäten vorhanden und stabil. Nun liegt es beim Angular-Team, darauf aufzubauen.