23. Feb 2023Frontend

Optimalizace aplikací React SPA v benchmarkových nástrojích

V tomto článku představím řešení, která mohou pomoct s optimalizací SPA (single page app), a jsou postavená především na frameworku React. Aplikování jednotlivých postupů pomáhá zrychlit načítání, zvýšit výkon a získat vyšší skóre v benchmarkových nástrojích. V první části se budu věnovat kompresi souborů, webovým fontům a CSS.

Ján CvenčekFrontend Develooper

Níže uvedené tipy byly aplikované na aplikaci React vytvořenou pomocí nástroje Create React App (CRA), která používá webpack v4. CRA má předkonfigurováno několik technik pro zlepšení výkonnosti a rychlosti aplikace. Pokud chcete upravit konfiguraci webpacku v CRA bez provedení příkazu eject, je třeba použít knihovnu, jako je craco nebo customize-cra. Produkční build aplikace se zobrazuje pomocí webového serveru Nginx.

K měření výsledků z hlediska výkonnosti a rychlosti byly použité nástroje:

Ve výstupech nástroje samy navrhují řešení, jak jednotlivé problémy odstranit.

ℹ Následující postupy nejsou jedinými způsoby řešení reportovaného problému z nástrojů, několik z nich má alternativu.

Komprese

Kompresi souborů obsluhovaných webovým serverem je možné aplikovat buď na straně serveru, nebo staticky během procesu vytváření buildů.

Compress-create-react-app

Pro statickou kompresi lze použít knihovnu compress-create-react-app jako build skript přes npm. Provádí kompresi gzip i Brotli pro soubory html, css a js. V případě, že komprese není dostatečná nebo konfigurace není vhodná, je možné použít jeden z níže uvedených postupů.

Gzip

Metoda komprese je méně náročná na CPU, ale velikost komprimovaných souborů je ve srovnání s Brotli větší. Jednotlivé metody lze podle potřeby rozšířit o další přepínače/parametry.

Statická komprese

Tu lze provést pomocí systémové utility gzip (ve Windows je třeba ji doinstalovat) gzip -r -f -k. Protože utilita není předinstalovánapro různé platformy, je vhodnější použít compression-webpack-plugin.

Live komprese – Nginx

Zapíná se v konfiguraci pro Nginx.

Brotli

Výkonnější metoda než gzip na úkor CPU.

⚠ Podporováno pouze přes HTTPS

Statická komprese

S využitím compression-webpack-plugin

Live komprese – Nginx

Zapíná se v konfiguraci pro Nginx, který musí mít nainstalovaný modul pro Brotli. Pro Docker můžete použít např. image fholzer/nginx-brotli

Imagemin

Nástroj pro kompresi obrázků. Existuje několik pluginů pro různé formáty. Každý z nich má víc parametrů, které umožňují nastavit plugin podle potřeby. Jednotlivé pluginy i s odkazy najdete v tabulce. Podporuje bezeztrátovou (kvalita obrazu po kompresi odpovídá originálu) nebo ztrátovou kompresi. Ztrátová komprese je efektivnější z hlediska úspory velikosti na úkor kvality.

Formát   Plugin so stratovou kompresiouPlugin s bezstratovou kompresiou
JPEGimagemin-mozjpegimagemin-jpegtran
PNGimagemin-pngquantimagemin-optipng
GIFimagemin-giflossyimagemin-gifsicle
SVGimagemin-svgo 
WebPimagemin-webp 

Příklad komprese PNG přes GULP

npm install gulp gulp-imagemin --save-dev

Bezeztrátová komprese (imagemin-optipng)

npm install imagemin-pngquant --save-dev

Ztrátová komprese (imagemin-pngquant)

npm install imagemin-optipng--save-dev‍
 

Webové fonty

Zajistěte, aby byl text během načítání webových fontů viditelný. Fonty bývají často velké soubory, jejichž načítání chvíli trvá. Některé prohlížeče text skryjí, dokud se písmo nenačte, což způsobí záblesk neviditelného textu (FOIT) –Lighthouse metrika.

Řešení – přidat do @font-face deklaraci atributu font-display: 

CSS

Před zobrazením stránky musí prohlížeč stáhnout a analyzovat soubory CSS, což z CSS dělá zdroj blokující vykreslování. Pokud jsou soubory CSS rozsáhlé nebo nejsou dobré síťové podmínky, mohou požadavky na soubory CSS výrazně prodloužit dobu potřebnou k vykreslení webové stránky.

Pokud Lighthouse report hlásí problém First Contentful Paint (FCP) – „Eliminate render-blocking resource“, je dobré zkusit extrahovat kritické (jsou aktuálně potřebné pro zobrazení) a nekritické styly CSS. Po optimalizaci se synchronně načítají pouze kritické styly, zatímco nekritické styly se načítají neblokujícím způsobem.

Možné řešení – html-critical-webpack-plugin

Plugin používá knihovnu puppeteer s headless prohlížečem Chromium/Chrome – je nutné se ujistit, aby prostředí, ve kterém PROD build poběží, má nainstalované potřebné závislosti

html-critical-webpack-plugin analyzuje kritické styly CSS a načítá je do <style></style> v tagu <head> v HTML, čímž eliminuje nutnost provádět další požadavek na jejich načtení.

Plugin se doporučuje používat pouze v produkčním buildu

Další tipy pro optimalizaci najdete v druhé části, kde se dozvíte, jak provádět dynamické importy, refaktoring nebo odstraňování nepoužívaného kódu.

Pripravený na výzvu? Pridaj sa k nám do Frontend tímu

Ján CvenčekFrontend Develooper