Dalam modul sebelumnya, beberapa teori di balik jalur rendering kritis telah dieksplorasi, dan bagaimana resource yang memblokir rendering dan memblokir parser dapat menunda rendering awal halaman. Setelah memahami beberapa teori di baliknya, Anda siap mempelajari beberapa teknik untuk mengoptimalkan jalur rendering penting.
Saat halaman dimuat, banyak resource yang dirujuk dalam HTML-nya yang memberikan tampilan dan tata letak halaman melalui CSS, serta interaktivitasnya melalui JavaScript. Dalam modul ini, sejumlah konsep penting terkait resource ini dan pengaruhnya terhadap waktu pemuatan halaman akan dibahas.
Pemblokiran render
Seperti yang dibahas dalam modul sebelumnya, CSS adalah aset pemblokiran render, karena memblokir browser untuk merender konten apa pun hingga CSS Object Model (CSSOM) dibuat. Browser memblokir rendering untuk mencegah Flash of Unstyled Content (FOUC), yang tidak diinginkan dari sudut pandang pengalaman pengguna.
Pada video sebelumnya, ada FOUC singkat yang menampilkan halaman tanpa gaya visual apa pun. Selanjutnya, semua gaya diterapkan setelah CSS halaman selesai dimuat dari jaringan, dan versi halaman yang tidak memiliki gaya langsung diganti dengan versi yang memiliki gaya.
Secara umum, FOUC adalah sesuatu yang biasanya tidak Anda lihat, tetapi konsepnya penting untuk dipahami agar Anda tahu mengapa browser memblokir rendering halaman hingga CSS didownload dan diterapkan ke halaman. Pemblokiran rendering tidak selalu tidak diinginkan, tetapi Anda sebaiknya meminimalkan durasinya dengan mengoptimalkan CSS.
Pemblokiran parser
Resource yang memblokir parser mengganggu parser HTML, seperti elemen <script>
tanpa atribut async
atau defer
. Saat parser menemukan elemen
<script>
, browser perlu mengevaluasi dan menjalankan skrip sebelum
melanjutkan penguraian HTML lainnya. Hal ini sudah didesain seperti itu, karena skrip dapat mengubah atau mengakses DOM selama waktu saat DOM masih dibuat.
<!-- This is a parser-blocking script: -->
<script src="/script.js"></script>
Saat menggunakan file JavaScript eksternal (tanpa async
atau defer
), parser
diblokir sejak file ditemukan hingga didownload, diuraikan, dan
dieksekusi. Saat menggunakan JavaScript sebaris, parser juga diblokir hingga
skrip sebaris diuraikan dan dieksekusi.
Pemindai pramuat
Pemindai pra-muat adalah pengoptimalan browser dalam bentuk parser HTML
sekunder yang memindai respons HTML mentah untuk menemukan dan mengambil
resource secara spekulatif sebelum parser HTML utama menemukannya. Misalnya, pemindai pramuat akan memungkinkan browser mulai mendownload resource yang ditentukan dalam elemen <img>
, meskipun parser HTML diblokir saat mengambil dan memproses resource seperti CSS dan JavaScript.
Untuk memanfaatkan pemindai pramuat, resource penting harus disertakan dalam markup HTML yang dikirim oleh server. Pola pemuatan resource berikut tidak dapat ditemukan oleh pemindai pramuat:
- Gambar dimuat oleh CSS menggunakan properti
background-image
. Referensi gambar ini ada di CSS, dan tidak dapat ditemukan oleh pemindai pramuat. - Skrip yang dimuat secara dinamis dalam bentuk markup elemen
<script>
yang disisipkan ke dalam DOM menggunakan JavaScript atau modul yang dimuat menggunakanimport()
dinamis. - HTML dirender di klien menggunakan JavaScript. Markup tersebut terdapat dalam string di resource JavaScript, dan tidak dapat ditemukan oleh pemindai pemuatan awal.
- Pernyataan
@import
CSS.
Pola pemuatan resource ini semuanya adalah resource yang ditemukan terlambat, sehingga
tidak diuntungkan dari pemindai pra-muat. Hindari sebisa mungkin. Namun, jika tidak mungkin menghindari pola tersebut, Anda dapat menggunakan petunjuk
preload
untuk menghindari penundaan penemuan resource.
CSS
CSS menentukan presentasi dan tata letak halaman. Seperti yang dijelaskan sebelumnya, CSS adalah aset pemblokiran render, jadi mengoptimalkan CSS dapat memberikan dampak yang cukup besar pada waktu pemuatan halaman secara keseluruhan.
Minifikasi
Meminifikasi file CSS akan mengurangi ukuran file aset CSS, sehingga lebih cepat didownload. Hal ini dilakukan terutama dengan menghapus konten dari file CSS sumber seperti spasi dan karakter tidak terlihat lainnya, serta menampilkan hasilnya ke file yang baru dioptimalkan:
/* Unminified CSS: */
/* Heading 1 */
h1 {
font-size: 2em;
color: #000000;
}
/* Heading 2 */
h2 {
font-size: 1.5em;
color: #000000;
}
/* Minified CSS: */
h1,h2{color:#000}h1{font-size:2em}h2{font-size:1.5em}
Dalam bentuknya yang paling dasar, minifikasi CSS adalah pengoptimalan efektif yang dapat meningkatkan FCP situs Anda, dan bahkan LCP dalam beberapa kasus. Alat seperti bundler dapat melakukan pengoptimalan ini secara otomatis untuk Anda dalam build produksi.
Menghapus CSS yang tidak digunakan
Sebelum merender konten apa pun, browser perlu mendownload dan mengurai semua stylesheet. Waktu yang diperlukan untuk menyelesaikan penguraian juga mencakup gaya yang tidak digunakan di halaman saat ini. Jika Anda menggunakan bundler yang menggabungkan semua resource CSS ke dalam satu file, pengguna Anda kemungkinan mendownload lebih banyak CSS daripada yang diperlukan untuk merender halaman saat ini.
Untuk menemukan CSS yang tidak digunakan untuk halaman saat ini, gunakan alat Cakupan di Chrome DevTools.

Menghapus CSS yang tidak digunakan memiliki efek ganda: selain mengurangi waktu download, Anda mengoptimalkan konstruksi pohon render, karena browser perlu memproses lebih sedikit aturan CSS.
Hindari deklarasi CSS @import
Meskipun mungkin tampak praktis, Anda harus menghindari deklarasi @import
di CSS:
/* Don't do this: */
@import url('style.css');
Mirip dengan cara kerja elemen <link>
di HTML, deklarasi @import
di CSS memungkinkan Anda mengimpor resource CSS eksternal dari dalam lembar gaya. Perbedaan
utama antara kedua pendekatan ini adalah elemen <link>
HTML
merupakan bagian dari respons HTML, dan oleh karena itu ditemukan jauh lebih awal daripada file CSS
yang didownload oleh deklarasi @import
.
Alasannya adalah agar deklarasi @import
dapat ditemukan, file CSS yang memuatnya harus didownload terlebih dahulu. Hal ini
menghasilkan apa yang disebut sebagai rantai permintaan yang—dalam kasus CSS—menunda
berapa lama waktu yang dibutuhkan agar halaman dirender pertama kali. Kekurangan lainnya adalah
stylesheet yang dimuat menggunakan deklarasi @import
tidak dapat ditemukan oleh
pemindai pramuat, dan oleh karena itu menjadi resource yang memblokir rendering yang ditemukan terlambat.
<!-- Do this instead: -->
<link rel="stylesheet" href="style.css">
Dalam sebagian besar kasus, Anda dapat mengganti @import
dengan menggunakan elemen
<link rel="stylesheet">
. Elemen <link>
memungkinkan stylesheet didownload secara bersamaan dan mengurangi waktu pemuatan secara keseluruhan, berbeda dengan deklarasi @import
, yang mendownload stylesheet secara berurutan.
CSS penting inline
Waktu yang diperlukan untuk mendownload file CSS dapat meningkatkan FCP halaman. Menyisipkan
gaya penting dalam dokumen <head>
menghilangkan permintaan jaringan untuk
resource CSS, dan—jika dilakukan dengan benar—dapat meningkatkan waktu pemuatan awal saat cache browser pengguna tidak siap. CSS yang tersisa dapat dimuat
secara asinkron, atau ditambahkan di akhir elemen <body>
.
<head>
<title>Page Title</title>
<!-- ... -->
<style>h1,h2{color:#000}h1{font-size:2em}h2{font-size:1.5em}</style>
</head>
<body>
<!-- Other page markup... -->
<link rel="stylesheet" href="non-critical.css">
</body>
Di sisi negatifnya, menyisipkan CSS dalam jumlah besar akan menambahkan lebih banyak byte ke respons HTML awal. Karena resource HTML sering kali tidak dapat di-cache dalam waktu yang lama—atau sama sekali tidak dapat di-cache—artinya CSS inline tidak di-cache untuk halaman berikutnya yang mungkin menggunakan CSS yang sama dalam lembar gaya eksternal. Uji dan ukur performa halaman Anda untuk memastikan kompromi yang dilakukan sepadan dengan upaya yang dikeluarkan.
Demo CSS
JavaScript
JavaScript mendorong sebagian besar interaktivitas di web, tetapi ada biayanya. Mengirim terlalu banyak JavaScript dapat membuat halaman web Anda lambat merespons selama pemuatan halaman, dan bahkan dapat menyebabkan masalah responsivitas yang memperlambat interaksi—keduanya dapat membuat pengguna frustrasi.
JavaScript yang memblokir rendering
Saat memuat elemen <script>
tanpa atribut defer
atau async
, browser akan memblokir penguraian dan rendering hingga skrip didownload, diurai, dan dieksekusi. Demikian pula, skrip inline memblokir parser hingga skrip diuraikan
dan dieksekusi.
async
versus defer
async
dan defer
memungkinkan skrip eksternal dimuat tanpa memblokir parser HTML, sementara skrip (termasuk skrip inline) dengan type="module"
ditangguhkan secara otomatis. Namun, async
dan defer
memiliki beberapa perbedaan yang penting untuk dipahami.
Skrip yang dimuat dengan async
diuraikan dan dieksekusi segera setelah didownload,
sedangkan skrip yang dimuat dengan defer
dieksekusi saat penguraian dokumen HTML
selesai—hal ini terjadi pada saat yang sama dengan peristiwa DOMContentLoaded
browser.
Selain itu, skrip async
dapat dijalankan di luar urutan, sedangkan skrip defer
dijalankan sesuai urutan kemunculannya dalam markup.
Rendering sisi klien
Secara umum, Anda harus menghindari penggunaan JavaScript untuk merender konten penting atau elemen LCP halaman. Hal ini dikenal sebagai rendering sisi klien, dan merupakan teknik yang banyak digunakan dalam Aplikasi Web Satu Halaman (SPA).
Markup yang dirender oleh JavaScript menghindari pemindai pramuat, karena resource yang ada dalam markup yang dirender klien tidak dapat ditemukan olehnya. Hal ini dapat menunda download resource penting, seperti gambar LCP. Browser hanya mulai mendownload gambar LCP setelah skrip dijalankan, dan menambahkan elemen ke DOM. Selanjutnya, skrip hanya dapat dieksekusi setelah ditemukan, didownload, dan diurai. Hal ini dikenal sebagai rantai permintaan penting dan harus dihindari.
Selain itu, merender markup menggunakan JavaScript lebih cenderung menghasilkan tugas panjang daripada markup yang didownload dari server sebagai respons terhadap permintaan navigasi. Penggunaan rendering HTML sisi klien secara ekstensif dapat berdampak negatif pada latensi interaksi. Hal ini terutama berlaku dalam kasus ketika DOM halaman sangat besar, yang memicu pekerjaan rendering yang signifikan saat JavaScript mengubah DOM.
Minifikasi
Mirip dengan CSS, meminifikasi JavaScript akan mengurangi ukuran file aset skrip. Hal ini dapat menghasilkan download yang lebih cepat, sehingga browser dapat melanjutkan proses parsing dan kompilasi JavaScript dengan lebih cepat.
Selain itu, minifikasi JavaScript selangkah lebih maju daripada minifikasi aset lain, seperti CSS. Saat JavaScript diminifikasi, JavaScript tidak hanya dihapus dari hal-hal seperti spasi, tab, dan komentar, tetapi simbol dalam JavaScript sumber juga dipersingkat. Proses ini terkadang dikenal sebagai uglification. Untuk melihat perbedaannya, ambil kode sumber JavaScript berikut:
// Unuglified JavaScript source code:
export function injectScript () {
const scriptElement = document.createElement('script');
scriptElement.src = '/js/scripts.js';
scriptElement.type = 'module';
document.body.appendChild(scriptElement);
}
Jika kode sumber JavaScript sebelumnya di-uglify, hasilnya mungkin terlihat seperti cuplikan kode berikut:
// Uglified JavaScript production code:
export function injectScript(){const t=document.createElement("script");t.src="/js/scripts.js",t.type="module",document.body.appendChild(t)}
Dalam cuplikan sebelumnya, Anda dapat melihat bahwa variabel yang mudah dibaca
scriptElement
dalam sumber disingkat menjadi t
. Jika diterapkan di banyak koleksi skrip, penghematan yang dihasilkan bisa cukup signifikan, tanpa memengaruhi fitur yang disediakan JavaScript produksi situs.
Jika Anda menggunakan bundler untuk memproses kode sumber situs, uglifikasi sering kali dilakukan secara otomatis untuk build produksi. Pengubah—seperti Terser, misalnya—juga sangat dapat dikonfigurasi, yang memungkinkan Anda mengubah keagresifan algoritma pengubah untuk mencapai penghematan maksimum. Namun, nilai default untuk alat pengacakan biasanya cukup untuk mencapai keseimbangan yang tepat antara ukuran output dan pelestarian kemampuan.
Demo JavaScript
Menguji pengetahuan Anda
Apa cara terbaik untuk memuat beberapa file CSS di browser?
@import
.<link>
.Apa fungsi pemindai pramuat browser?
<link rel="preload">
dalam
resource HTML.
Mengapa browser memblokir penguraian HTML secara default untuk sementara saat mendownload resource JavaScript?
Berikutnya: Membantu browser dengan petunjuk resource
Setelah Anda memahami cara pemuatan resource dalam elemen <head>
dapat memengaruhi pemuatan halaman awal dan berbagai metrik, sekarang saatnya melanjutkan. Pada modul
berikutnya, petunjuk resource akan dibahas, dan bagaimana petunjuk tersebut dapat memberikan petunjuk berharga kepada
browser untuk mulai memuat resource dan membuka koneksi ke server lintas asal
lebih cepat daripada yang dilakukan browser tanpa petunjuk tersebut.