Ottimizzazione delle prestazioni UI
1) Cosa conta «veloce»
TTFB (tempo fino al primo byte) è la risposta rapida del server/CDN.
LCP (Largest Continful Paint) - Il contenuto principale è apparso rapidamente.
INP (Interaction to Next Paint) - Reattività durante l'interazione.
CLS (Cumulative Layout Maiusc) - Nessun tremore nell'interfaccia.
TTI (Time to Interactive) - Quando tutto è già in linea.
Le indicazioni consigliate sono LCP 2. 5 c, INP a 200 mc, CLS a 0. 1 (per il 75 ° percento degli utenti reali).
2) Processo: misurare, trovare le strette, fissare i budget
1. Misura: RUM (utenti reali, percento per paese/rete/device) + sintetico (Lighthouse/browser).
2. Trova il profilatore Performance (attività lunghe> 50 ms, layout thrashing, render superflui).
3. Fissa: budget (peso JS/CSS/caratteri, LCP/INP) e linee rosse in CI.
3) Rete e download delle risorse
3. 1 HTTP e priorità
Abilita HTTP/2/3, compressione Brotli.
«precisnect» ai domini critici; «dns-prefetch» ai domini secondari.
«pratoad» per le risorse critiche (immagine eroe, carattere principale).
"fetchpriority =" high/low "e" priority "i suggerimenti in cui è supportato.
3. 2 Cache
La statica con l'hashtag del file è «Cache-Control: public, max-age = 31536000, immutabile».
HTML - TTL + stale-while-revalidate breve tramite CDN.
ETAG/Last-Modified e Service Worker per visite offline/ripetute.
4) Codice più piccolo, più tardi, «più semplice»
4. 1 Assieme
Tree-shaking, minify (в т.ч. dead-code-elim).
Code-splitting per percorsi/widget, importazione dinamica.
Evitare i pacchetti pesanti globali nel bandle base (moment → Intl/Day. js).
4. 2 Rendering e consegna HTML
SSR/ISR/strage - Dare prima l'ossatura e il contenuto principale.
Partial/Islands hydration - Idratare solo le aree interattive.
Defer è tutto non critico: '<script type = "module" defer> ".
4. 3 Reazioni specifiche (se usate React)
`React. lazy' + 'Rispense', per widget pigri.
«startTransition» e «useDeferredValue» per i filtri e le ricerche pesanti.
RSC (Server Components) - Calcoli sul server, meno JS sul client.
Selettori in state (zustand/redux) - Consente di firmare il componente in sezioni anziché l'intero store.
5) Render e stato dove «frena»
5. 1 Isolamento dei retander
Frazionate i componenti più grandi, memate («memo», «useMemo», «useCallback»).
Le chiavi degli elenchi sono stabili; non creare nuove funzioni/oggetti nelle dispense senza necessità.
Evitare il contesto globale per i dati che cambiano di frequente: utilizzare selettori o pneumatici per eventi.
5. 2 Virtualizzazione e grandi elenchi
Fogli/tabelle virtualizzazione (render window).
Paginazione/infinit scroll con backpressure (non caricare subito 100k righe).
Inizializzazione ritardata di widget pesanti fuori dal wiport.
5. 3 Layout & paint
content-visibility: auto; per le sezioni nascoste (il browser non rende l'invisibile).
contain e «contain-intrinsic-size» per le quote prevedibili.
Evitare frequenti letture-record layout (layout thrashing); raggruppare le misure.
usate il dosato (altrimenti memoria/livelli in eccesso).
6) Immagini e grafici
Formati: AVIF/ WebP (fallback su PNG/JPEG).
Approccio Responsive: 'srcset' +' sizes', per la retina.
loading =» lazy» per immagini non eroiche; priority/proload - solo per il candidato LCP.
I playsholder a dimensioni fisse non hanno → CLS.
Canves/liste: offscreen-canwas e Web Worker per i calcoli; Il batching dei ritagli.
7) Caratteri e testo
Una o due variabili font invece di molti disegni.
"font-display: swap '/' optional ', pratoad per lo stile principale.
«size-adjust» per ridurre il «salto» durante la sostituzione del carattere.
Caratteri fallback locali con metriche simili.
8) CSS e animazioni
CSS inline critico (<14-20 kB), il resto è rimandato.
Elimina gli stili non utilizzati (Purge/CSSTree).
Animazioni se possibile su form/opacity; rispettare'preferers-reduced-motion '.
Evitare cascate profonde e selettori esplosivi.
9) Web Workers, flusso e attività difficili
Tutte le CPU pesanti sono in Worker (parsing, ordinamento, aggregazione, ML).
API di streaming («ReadableStream», «fetch» con flussi) per risposte lunghe.
Frammentare le attività con «requestIdleCallback »/microtaschi per mantenere la sensibilità.
10) Stabilità layout (CLS)
Riservare spazio all'elemento LCP (immagine/widget).
Non inserire banner/nastri senza dimensioni fisse.
Tultipi/toast asimmetrici - non muovere i contenuti; Usa livelli/portali.
11) Esempi di snippet
Carattere critico e immagine LCP
html
<link rel="preload" href="/fonts/Inter. var. woff2" as="font" type="font/woff2" crossorigin>
<link rel="preload" as="image" href="/hero. avif" imagesrcset="/hero. avif 1x, /hero@2x. avif 2x" fetchpriority="high">
Inizializzazione del widget pigro e sicuro
js const Widget = React. lazy(() => import('./Widget'));
function Section() {
const inView = useInViewport('#sec');
return <div id="sec">{inView? <React. Suspense fallback={null}><Widget/></React. Suspense>: null}</div>;
}
Stabilizzazione layout
css
.hero {
content-visibility: auto;
contain: layout paint;
contain-intrinsic-size: 720px 320px ;/LCP reserve/
}
12) Controllo delle regressioni e budget
Bundle-budget: comune JS-N kB, CSS-M kB, iniziale-chunk K kB.
Web-Vitals in CI (emulati) + RUM-alert (su percentili).
Analisi bandle: source-map-explorer/analizzatore in PR.
Performance-benchmark dei componenti (render 10k feature, tempo di reazione).
13) Anti-pattern
Carica «tutto e subito»: grafici, editor, mappe nella prima schermata.
Una grande statua globale, con → a cascata.
Immagini a 2-4 x dalla dimensione desiderata, senza «srcset/sizes».
Cicli sincroni lunghi sul flusso principale.
«outline: none» e i trucchi di castoma senza ottimizzazione interferiscono con gli indicatori di rendering.
Animazioni per «top/left» (rompono il layout e richiamano il reflow).
14) Assegno-foglio schermo
- LCP ≤ 2. 5 c su 3G/mobile, CLS ≤ 0. 1, INP da 200 ms
- Risorse critiche: proload/priorità; il resto è defer/lazy
- Bandle: code-split, nessuna dipendenza in eccesso
- Virtualizzazione di elenchi/tabelle, inizializzazione ritardata di widget pesanti
- Immagini: AVIF/WebP, 'srcset/sizes', 'loading =' lazy '
- Caratteri: variabile + 'font-display', proload solo quello desiderato
- CSS: inline critica, Purge, content-visibility e contain'se appropriato
- Workers/idle per calcoli pesanti
- Budget e Web-Vitals sono collegati a dashboard/alert
15) Piano di implementazione (3 iterazioni)
Iterazione 1 - Vittorie veloci (1-2 settimane)
Abilita Brotli/HTTP-2/3, CDN. Risorse CSS e pratoad LCP critiche.
Portare i widget pesanti all'import dinamico.
Immagini + «srcset». Caratteri: 'font-display: swap'.
Iterazione 2 - Miglioramenti strutturali (3-4 settimane)
Code-split lungo le rotte, analisi del bandle, rimozione dei pesanti.
Virtualizzazione di elenchi, content-visibility, contain-intrinsic-size.
Implementare SSR/streaming/isole (se rilevante).
RUM con Web-Vitals, budget in CI.
Iterazione 3 - Scala e stabilità (continua)
Workers/offscreen-canwas, calcoli batching, startTransition/deferredValue.
Perf Check-in regolare, regressioni auto, addestramento team.
16) Mini FAQ
Cosa accelera di più sul mobile?
Riduce l'immagine iniziale JS, SSR/streaming e ottimizza l'immagine LCP.
C'è sempre bisogno di SSR?
No, no. Se la pagina è dinamicamente interattiva e non è memorizzata correttamente - islands/partial hydration può essere migliore.
Perché l'INP è cattivo con una banda leggera?
Probabilmente operazioni di lunga durata (ordinamento, grafica) sul flusso principale - portate in Worker e frazionate le attività.
Totale
L'UI veloce è un insieme di discipline: priorità di rete e cache, bandi più piccoli e più recenti, render prevedibile senza sbalzi, immagini e caratteri a basso costo e controllo costante delle metriche nel mondo reale. Immettere i budget, automatizzare i controlli e insegnare al team a pensare alla velocità di ogni passo, in modo che l'interfaccia rimanga veloce oggi e tra un anno.