Veröffentlicht am 13. November 2018

Optimizely Casper verbessert durch Self-Hosting die Leistung seiner Site um 36%.

In diesem Beitrag des Kunden Kyle Rush, VP of Engineering bei Casper und ehemaliger stellvertretender CTO der Hillary For America-Kampagne, sehen wir aus erster Hand, wie sein Team die Site-Leistung von casper.com drastisch verbessert hat. Mithilfe einer neuen Empfehlung von Optimizely, die flexiblere Implementierungsoptionen für Kunden durch Optimizely Web fördert, konnten Rush und

Kyle Rush
von Kyle Rush
shape, polygon

In diesem Beitrag des Kunden Kyle Rush, VP of Engineering bei Casper und ehemaliger stellvertretender CTO der Hillary For America-Kampagne, sehen wir aus erster Hand, wie sein Team die Site-Leistung von casper.com dramatisch verbessert hat. Mit einer neuen Empfehlung von Optimizely, die flexiblere Implementierungsoptionen für Kunden durch Optimizely Web fördert, konnten Rush und sein Team das Erlebnis für die Kunden exponentiell steigern, indem sie die Ladezeiten beschleunigten. Eine frühere Version dieses Artikels wurde auf Medium veröffentlicht .

Wir haben vor kurzem eine Änderung bei casper.com vorgenommen, bei der Optimizely von unserem eigenen Server statt von ihrem Server geladen wurde. Durch diese Änderung konnten wir die Renderzeit um 1,7 Sekunden verkürzen:

chart, line chart

Messung auf Desktop Chrome mit 3G-Netzwerkverbindung

Wir verwenden das clientseitige JavaScript von Optimizely, um A/B-Tests auf casper.com durchzuführen. Sobald die JavaScript-Datei heruntergeladen und ausgeführt wurde, ändert sie das Dokument für 50% unserer Website-Besucher, um zu messen, wie sie auf die Änderung reagieren. Um den kleinstmöglichen Flash of Unstyled Content (FOUC) zu gewährleisten, laden wir Optimizely vor allem anderen, und zwar in einer blockierenden Weise.

Wie nicht anders zu erwarten, hat das Laden des JavaScript-Snippets auf diese Weise negative Auswirkungen auf die Web-Performance unserer Website. Das ist ein Kompromiss, mit dem wir lange Zeit gerungen haben. Sollten wir den Erfolgsmethoden für die Web-Performance folgen und das Optimizely-JavaScript asynchron laden, oder sollten wir dem folgen, was traditionell als Best Practice für das Experimentieren gilt, und es als erstes Asset blockierend laden? Beide Ansätze haben ihre Vor- und Nachteile.

In einem unserer Gespräche zur Überprüfung der Web-Performance beschlossen wir, mit Techniken zu experimentieren, um das Performance-Problem zu lösen. Unsere erste Idee war, Optimizely aus dem <head> herauszunehmen und/oder das <script>-Tag mit dem Attribut async zu versehen, damit es das Rendern nicht blockiert und asynchron geladen wird. Unser Product Management Team wies darauf hin, dass der daraus resultierende FOUC-Effekt ( Flash of Unstyled Content ) ein schlechtes Erlebnis für den Kunden wäre. Unser Daten- und Analyseteam wies darauf hin, dass die Datenintegrität wahrscheinlich beeinträchtigt würde, wenn das JavaScript später im Prozess geladen wird.

Das nächstbeste, was uns einfiel, war, das Optimizely-Snippet selbst zu hosten. Optimizely hat sogar einen Artikel in der Wissensdatenbank, der dazu ermutigt. Normalerweise geben Softwareunternehmen wie Optimizely Ihnen eine URL einer JavaScript-Datei (die sie hosten). Das Problem ist, dass dies eine neue DNS-Suche, eine neue HTTP-Verbindung und einen neuen SSL-Handshake mit dem Server des Anbieters verursacht. Ein weiterer Nachteil dieser Art des Ladens ist, dass Sie die Möglichkeit verpassen, das Asset mit HTTP2-Multiplexing bereitzustellen, einer wesentlich effizienteren Art der Kommunikation zwischen einem Browser und einem Server. Wie Sie auf dem Screenshot unten sehen können, verursachte dies bei einem unserer Leistungstests eine Latenz von 39 ms für die DNS-Suche, 54 ms für den Aufbau einer Serververbindung und 135 ms für den SSL-Handshake. Hinzu kommt eine Latenzzeit von 175 ms beim Warten auf das erste Byte, die entfallen würde, wenn wir HTTP2-Multiplexing verwenden könnten.graphical user interface, text, application

Ein letzter Vorteil des eigenen Hostings der Datei ist, dass wir mehr Kontrolle über den Edge- (CDN) und Client-Cache (Browser) haben würden. Wir können den Edge-Cache von Optimizely nicht kontrollieren, aber wir können den Client-Cache kontrollieren. Es gibt eine Einstellung, mit der Sie den Cache-Kontrollwert konfigurieren können, der bei uns auf 2 Minuten eingestellt war. Dies ist für uns eine ideale Einstellung, wenn die Datei von Optimizely gehostet wird.

Um unsere Theorie zu testen, dass selbst gehostetes Hosting besser ist, haben wir den Inhalt der Optimizely-Javascript-Datei manuell kopiert, eine Version auf unserem Server gespeichert und den Verweis in Staging so ersetzt, dass er auf unsere selbst gehostete Version der Datei zeigt. Die Ergebnisse waren nicht spektakulär. Sie waren so enttäuschend, dass einer unserer Datenanalysten meinte, es lohne sich nicht, 200 ms von der Start-Renderzeit abzuziehen. Und wir stimmten ihm zu!

table

Wir haben trotzdem weitergemacht, weil wir der Meinung waren, dass unsere Staging-Umgebung kein guter Ort ist, um diese Art von Leistungsänderung zu testen. In unserer Staging-Umgebung fehlt eine Menge JavaScript von Drittanbietern, das nur in der Produktion läuft. Also haben wir einen Produktionstest entwickelt, bei dem die Datenanalysten 3 Tage lang keine Änderungen an Optimizely vornehmen sollten, während wir die statische, selbst gehostete Version von Optimizely bereitstellten.

chart

Der Rückgang ist der Zeitraum, in dem die selbst gehostete Version von Optimizely in Produktion war (gemessen auf dem Chrome-Desktop, über eine Kabelnetzverbindung - zu der Zeit haben wir die Leistung nicht bei 3G-Netzwerkgeschwindigkeiten gemessen, weshalb die Grafik am Anfang des Artikels einen größeren Effekt hat, aber 3G ist jetzt unsere Standard-Netzwerkgeschwindigkeit für Messungen).

In der obigen Grafik können Sie einen Rückgang der Start-Rendering-Zeit in dem Zeitraum erkennen, in dem unsere selbst gehostete, statische Version des Optimizely-Snippets in der Produktion aktiv war. Durch das eigene Hosten sank die Start-Rendering-Zeit erheblich, da wir die DNS-Suche, die Optimizely-Serververbindung, den SSL-Handshake und die Zeit bis zum ersten Byte eliminiert und H2-Multiplexing aktiviert haben.

Wir waren jedoch noch nicht ganz bereit, diese Änderung dauerhaft vorzunehmen. Optimizely funktioniert so, dass bei einer Änderung an einem Experiment das JavaScript-Snippet auf dem Optimizely-Server aktualisiert wird. Die Änderung kann das Starten/Pausieren eines Experiments, die Änderung eines Experiments usw. sein. Jede Änderung erzeugt eine neue Version der JavaScript-Datei. Da wir in der Produktion nur eine statische Kopie der JavaScript-Datei geladen haben, die wir manuell kopiert haben, konnten wir sie nicht für immer dort belassen, da wir nie in der Lage gewesen wären, Experimente zu starten/pausieren. Außerdem wäre es für unsere Softwareingenieure ein zu großer Aufwand, die neue Datei bei jeder Änderung manuell zu kopieren. Nachdem wir also die Vorteile dieses Ansatzes erkannt hatten, mussten wir herausfinden, wie wir die neueste Version des Optimizely Snippets dynamisch von unseren eigenen Servern laden konnten.

diagram

Zu diesem Zweck haben wir einen AWS Lambda erstellt, der alle 60 Sekunden ausgeführt wird. Wenn er läuft, sendet er eine Anfrage an optimizely.com nach der JavaScript-Datei. Es erstellt einen Hash der Datei und überprüft in S3, ob sich der Hash geändert hat (wir speichern den Hash der letzten Ausführung in einer Datei in S3). Wenn sich der Hash geändert hat, speichert er die neue JavaScript-Datei in S3 mit einem Teil des Hashs im Dateinamen (Beispiel: snippet-c36d504bc3c26479f1181e6119617a64.js). Als nächstes sendet der Lambda den Hash an ein Wörterbuch auf unserem Fastly Edge Server. Hier kommt die Magie ins Spiel. Wir haben unsere Edge-Server mit einer Kombination aus einem Edge Side Include (ESI) und einem Edge-Wörterbuch konfiguriert, um den neuesten Optimizely JavaScript-Dateinamen dynamisch in den HTML-Code jeder von den Edge-Servern ausgelieferten Seite einzufügen. Auf diese Weise können wir den Verweis auf die Optimizely-Datei auf dem Edge-Server aktualisieren, anstatt die Website jedes Mal neu bereitstellen zu müssen, wenn sich die Datei ändert.

Hier ist ein Screenshot von WebPageTest, der die Leistung der neuen Optimizely-Datei misst, die von Casper gehostet wird:

graphical user interface, text, application

Und hier sehen Sie einen Vergleich der Daten, die vor und nach dem Hosten durch WebPageTest gesammelt wurden:

table

Idealerweise würden wir für diese Werte das 95. Perzentil der Real User Monitoring (RUM) Daten präsentieren, aber wir haben dies für casper.com noch nicht vollständig implementiert. Wie bei jeder Leistungsmessung haben wir eine Varianz in den Daten festgestellt, also haben wir die Zahlen bei verschiedenen Perzentilen untersucht, um die Verteilung zu verstehen.

Hier ist ein Wasserfall, der das HTTP2-Multiplexing auf casper.com und die Optimizely-Datei zeigt. Beachten Sie, dass das Herunterladen der Inhalte für die Top 5 Assets bei allen fast zur gleichen Zeit beginnt.

graphical user interface, table

Und schließlich haben wir, wie bereits erwähnt, beim eigenen Hosting mehr Kontrolle über das Caching. Wir haben unsere Edge-Server so konfiguriert, dass die Datei ein ganzes Jahr lang im Edge- und Browser-Cache bleibt. Das ist möglich, weil der Dateiname dem Inhalt eindeutig zugeordnet ist (wir fügen dem Dateinamen einen Teil des Hashes der Datei hinzu) und ersetzen den Verweis auf den Dateinamen, wenn er sich ändert. Wenn wir also keine Änderungen am Optimizely Snippet vornehmen, wird der Browser des Wiederholungsbesuchers nicht einmal eine Anfrage an casper.com für die Datei stellen. Stattdessen holt er die Datei direkt aus dem Cache im Dateisystem des Benutzers. Superschnell!

graphical user interface, text, application, email

Hier sehen Sie den Vorteil, dass die Datei aus dem Browser-Cache bereitgestellt wird:

table

Der Nachteil dieses Ansatzes ist, dass Website-Besucher kein optimales Caching-Erlebnis haben, wenn wir das Optimizely Snippet häufig ändern. Da unser Unternehmen wächst, ist es möglich, dass unsere Datenanalysten mehr A/B-Tests durchführen werden, die häufige Änderungen an der Datei erfordern. Dies könnte dazu führen, dass Website-Besucher während ihres Besuchs auf casper.com mehrere Versionen der Datei herunterladen müssen. Wir verfolgen jede Änderung der JavaScript-Datei in einem benutzerdefinierten Dashboard von DataDog:

chart, bar chart

In diesem Diagramm sehen wir, dass sich das Snippet am Donnerstag, den 23., in einem Zeitraum von 3 Stunden etwa 25 Mal geändert hat. Es ist unwahrscheinlich, dass eine große Anzahl von Besuchern bei dieser Änderungshäufigkeit mehrere Versionen des Snippets herunterlädt, da unsere durchschnittliche Besuchsdauer nicht sehr lang ist. Alles in allem sind wir der Meinung, dass das Selbst-Hosten mehr Vorteile als Nachteile hat.

An diesem Projekt haben unsere Software-Ingenieure, Product Manager, Site-Zuverlässigkeitsingenieure und Datenanalysten etwa einen Monat lang gearbeitet. Es war ein großartiges Beispiel dafür, wie einige leistungsorientierte Mitarbeiter des Casper Tech-Teams ein Problem erkannten, eine elegante Lösung fanden, diese in die Produktion überführten und damit einen großen Beitrag für unsere Kunden leisteten.


Wenn Sie mehr darüber erfahren möchten, wie Sie das Optimizely Snippet selbst hosten können, sehen Sie sich diese Anleitungen für einige der beliebtesten CDNs an:

Wenn Sie mehr über die Erfolgsmethoden von Optimizely für die Performance Ihrer Site erfahren möchten, besuchen Sie unsere Knowledge Base, um sicherzustellen, dass Sie unsere Empfehlungen nutzen.