Der erste sieht nach einer einfachen Optimierung aus, die meiner Meinung nach sinnvoll ist. @david und @eviltrout haben Zeit damit verbracht, diesen Bereich zu optimieren, daher bin ich sehr gespannt, was sie dazu sagen.
Der zweite fühlt sich langfristig etwas fragiler an. Ich verstehe den Wunsch zu optimieren vollkommen, aber er macht mir ein wenig Sorgen, da er ein Bereich sein wird, den wir pflegen müssen.
Hallo @rrit - danke für die PRs. Die erste klingt nach einer guten Verbesserung. Konntest du die Auswirkungen auf die Leistung messen? Wie viel Zeit spart sie?
Wie @sam sagte, ist die Wartbarkeit der zweiten etwas besorgniserregend. Sieht so aus, als wäre sie kopiert und eingefügt aus dem Ember-Quellcode? Hast du etwas geändert, um die Leistung zu verbessern?
Z. B. löst renderTopicListItem letztendlich viele Aufrufe von _getPath aus (weitere 50-100 ms Einsparung): Firefox Profiler (Callstack gefiltert nach _getPath innerhalb von renderTopicListItem)
Vielleicht sind die aufwändigen Aufrufe von _getPath etwas, das in Ember.js und nicht in Discourse optimiert werden sollte.
Und werfen Sie einen Blick auf den Firefox Profiler, um Einblicke in die JavaScript-Ausführung zu erhalten:
Leider konnte ich diese große Geschwindigkeitssteigerung nicht reproduzieren. Unter Firefox und Chrome (macOS) sehe ich keine messbare Verbesserung. Chrome benötigt etwa 23 ms für renderTopicListItem. Firefox 30 ms. Auf einem älteren Android-Gerät (Pixel 3) sehe ich etwa 108 ms. Die Zahlen scheinen sich vor/nach der Änderung nicht zu ändern.
Übrigens habe ich diese Zahlen mit der Performance API gemessen. Ich habe performance.mark("rtli-start") am Anfang von renderTopicListItem und dann performance.measure("rtli", "rtli-start") am Ende hinzugefügt.
Dann lade ich den Browser neu mit geschlossenen Entwicklertools und deaktivierten Browser-Plugins (Entwicklertools und Browser-Plugins können die Rendering-Leistung erheblich beeinträchtigen). Dann, nach Abschluss des Ladens, öffne ich die Entwicklertools und führe dies aus, um die Messungen zusammenzufassen:
performance.getEntriesByName("rtli").reduce((v, m) => v + m.duration, 0);
Wir werden diese Änderung auf jeden Fall zusammenführen – es ist eindeutig eine bessere Implementierung. Aber ich bin mir nicht sicher, ob sie uns einen sichtbaren Unterschied in der Rendering-Leistung bringen wird
Ich kann die Leistungsvorteile immer noch mit der Performance API im Firefox-Privatmodus (Linux) reproduzieren.
Testen von http://localhost:4200/latest
Die Zeit, die in renderTopicListItem verbracht wird, ist von ca. 290 ms auf ca. 190 ms gesunken.
Meine Discourse-Testinstanz hat viele Themen mit vielen Antworten und vielen verschiedenen Autoren – Daten, die aus einer produktiven Instanz gezogen wurden. Dies führt zu vielen zu rendernden Elementen.
Vielleicht ist das der Unterschied in unseren Benchmarks?
Vorab-Rendering von Inhalten unterhalb des sichtbaren Bereichs
Discourse rendert 30 Themen auf der Seite „latest“ vor. Dann wird der Inhalt zum ersten Mal angezeigt (FCP). Oberhalb des sichtbaren Bereichs sind nur ca. 12 Themen sichtbar.
Dasselbe gilt für eine Themen-Seite: 20 Beiträge werden vorab gerendert, aber maximal 6 einzeilige Beiträge sind oberhalb des sichtbaren Bereichs sichtbar.
Dies könnte ein weiterer Optimierungspunkt für FCP sein.
Könnten Sie bitte die Firefox- und Betriebssystemversion mitteilen? Die 290-ms-Zahl ist fast dreimal langsamer als bei einem Android-Gerät von 2018, was etwas überraschend ist.
Das könnte einige der Unterschiede erklären, ja. In meinem Fall habe ich sie mit Live-Daten von Meta ausgeführt:
bin/ember-cli --environment production --proxy https://meta.discourse.org
Ja, das ist eine mögliche Verbesserung. Wir müssen jedoch sehr vorsichtig sein, dass das Layout und/oder das Scrollen nicht springt (z. B. wenn der Benutzer die Seite aktualisiert, während er bereits zur Hälfte nach unten gescrollt ist). Die Definition von „unterhalb des sichtbaren Bereichs“ variiert auch je nach Gerät/Browser/Theme.
Discourse Build Error
Error [ERR_TLS_CERT_ALTNAME_INVALID]: Hostname/IP stimmt nicht mit den alternativen Namen des Zertifikats überein:
Host: localhost. ist nicht in den alternativen Namen des Zertifikats enthalten: DNS:*.cdck-prod-meta.discourse.cloud
Discourse Build Error
Error [ERR_TLS_CERT_ALTNAME_INVALID]: Hostname/IP stimmt nicht mit den alternativen Namen des Zertifikats überein:
Host: meta.discourse.org. ist nicht in den alternativen Namen des Zertifikats enthalten: DNS:*.cdck-prod-meta.discourse.cloud