Pada Mei 2022, tim Aurora dan Angular mengumumkan bahwa mereka akan berkolaborasi dalam perintah gambar untuk Angular. Perintah ini baru saja dirilis untuk pratinjau developer sebagai bagian dari Angular v14.2. Postingan ini membahas bagaimana perintah gambar baru, NgOptimizedImage
, mendukung pengoptimalan gambar di Angular.
Latar belakang
Gambar adalah komponen umum dan penting dari pengalaman pengguna web, dengan 99,9% halaman web menghasilkan permintaan untuk satu atau beberapa gambar. Gambar juga merupakan kontributor yang paling signifikan terhadap berat halaman, dengan rata-rata 982 kilobyte per halaman.
Karena jumlah dan ukurannya yang terus bertambah, gambar dapat menghambat performa halaman web dan memengaruhi metrik Data Web Inti. Untuk 79,4% halaman desktop, gambarnya dianggap sebagai elemen Largest Contentful Paint (LCP) pada tahun 2021. Oleh karena itu, pencarian gambar yang dioptimalkan telah menjadi upaya yang konstan bagi banyak dari kita.
Tim Aurora meyakini manfaat framework untuk memberikan solusi siap pakai untuk tantangan umum developer. Upaya pertama mereka ke ruang pengoptimalan gambar adalah komponen gambar Next.js. Mereka menganggap komponen ini sebagai ajang pengujian apakah meningkatkan pengalaman developer (DX) pengoptimalan gambar dapat menghasilkan performa yang memuaskan untuk lebih banyak aplikasi yang menggunakan framework.
Kumpulan hasil pertama dari pengguna Next.js Leboncoin sangat menggembirakan. Leboncoin mengalami peningkatan LCP yang signifikan (dari 2,4 detik menjadi 1,7 detik) setelah mereka mulai menggunakan next/image
. Adopsi next/image
selanjutnya dalam komunitas berperan dalam peningkatan origin Next.js yang memenuhi nilai minimum LCP. Tak lama kemudian ada permintaan untuk fitur serupa di framework lain, salah satunya Angular.
Oleh karena itu, Aurora berkonsultasi dengan Angular dan Nuxt untuk membuat prototipe komponen gambar bagi framework ini. Komponen image Nuxt dirilis tahun lalu. Sekarang perintah gambar Angular (NgOptimizedImage
) telah dirilis untuk memberikan setelan default pengoptimalan gambar ke Angular.
Opportunity
Angular adalah salah satu framework JavaScript terkemuka yang digunakan oleh developer saat ini. URL ini digunakan oleh lebih dari 50 ribu origin yang di-crawl oleh HTTPArchive di perangkat seluler dan menawarkan hampir 3 juta download mingguan di NPM.
Dengan melihat skor Data Web Inti, persentase asal Angular yang memenuhi nilai minimum LCP "baik" masih memerlukan perbaikan. Hanya 18,74% situs Angular yang memiliki LCP yang baik di perangkat seluler pada Juni 2022. Karena gambar adalah elemen LCP untuk lebih dari 70% halaman web di perangkat seluler dan desktop, gambar LCP yang tidak dioptimalkan dapat menjadi salah satu penyebab utama LCP yang lebih buruk di situs Angular.
Perintah gambar Angular dirancang untuk membantu meningkatkan jumlah ini.
MVP untuk perintah NgOptimizedImage
MVP perintah gambar Angular dibuat berdasarkan pelajaran dari komponen gambar yang telah dibuat Aurora hingga saat ini sambil mengadaptasikan desain dengan pengalaman rendering sisi klien Angular. Banyak masalah pengoptimalan gambar standar telah diatasi dengan:
- Memberikan default yang kuat.
- Menampilkan error atau peringatan untuk memastikan kesesuaian dengan praktik terbaik.
Sorotan desain adalah sebagai berikut:
Pemuatan lambat cerdas
Gambar yang tidak terlihat oleh pengguna saat halaman dimuat (misalnya, gambar paruh bawah atau gambar carousel tersembunyi) idealnya harus dimuat dengan lambat. Pemuatan lambat akan mengosongkan resource browser untuk memuat teks, media, atau skrip penting lainnya. Sebagian besar gambar tidak penting dan harus dimuat lambat, tetapi hanya 7,8% halaman yang menggunakan pemuatan lambat native pada tahun 2021.
Perintah gambar Angular memuat gambar yang tidak penting secara default dan hanya memuat gambar yang ditandai khusus sebagai
priority
dengan segera. Hal ini memastikan sebagian besar gambar menampilkan perilaku pemuatan yang optimal.Penentuan prioritas gambar kritis
Menambahkan petunjuk resource (misalnya,
preload
ataupreconnect
) untuk memprioritaskan pemuatan gambar penting adalah praktik terbaik yang direkomendasikan. Namun, sebagian besar aplikasi tidak menggunakannya. Menurut Web Almanac tahun 2021, hanya 12,7% halaman seluler yang menggunakan petunjuk preconnect dan hanya 22,1% halaman seluler yang menggunakan petunjuk pramuat.Perintah gambar bertindak di dua sisi saat gambar ditandai sebagai prioritas.
- Ini menetapkan prioritas pengambilan gambar ke
"high"
sehingga browser mengetahui bahwa browser harus mendownload gambar dengan prioritas tinggi. - Dalam mode pengembangan, pemeriksaan runtime mengonfirmasi bahwa petunjuk resource
preconnect
telah disertakan yang sesuai dengan asal gambar.
Dalam mode pengembangan, perintah ini juga menggunakan PerformanceObserver API untuk memverifikasi bahwa gambar LCP telah ditandai
priority
seperti yang diharapkan. Jika tidak ditandaipriority
, error akan muncul, yang memerintahkan developer untuk menambahkan atributpriority
ke gambar LCP.Pada akhirnya, kombinasi otomatisasi dan kesesuaian ini memastikan bahwa gambar LCP memiliki petunjuk
preconnect
, nilai atributfetchpriority
high
, dan tidak dimuat dengan lambat.- Ini menetapkan prioritas pengambilan gambar ke
Konfigurasi yang dioptimalkan untuk alat gambar populer
Sebaiknya aplikasi Angular menggunakan CDN gambar, yang sering menyediakan layanan pengoptimalan secara default.
Perintah ini mendorong penggunaan CDN gambar dengan memberikan pengalaman developer (DX) yang sangat menarik untuk mengonfigurasinya di aplikasi. Perintah ini mendukung API loader yang memungkinkan Anda menentukan penyedia CDN dan URL dasar dalam konfigurasi. Setelah dikonfigurasi, Anda hanya perlu menentukan nama aset dalam markup. Misalnya,
// in module providers: provideImgixLoader('https://mysite.net/assets/') // in markup <img ngSrc="image.png" > <img ngSrc="image2.png" >
Ini sama dengan menyertakan tag gambar berikut dan mengurangi yang harus disertakan developer markup untuk setiap gambar.
<img src="https://mysite.net/assets/image.png"> <img src="https://mysite.net/assets/image2.png">
Perintah gambar menyediakan loader bawaan dengan konfigurasi optimal untuk CDN gambar yang paling populer. Loader ini akan memformat URL gambar secara otomatis untuk memastikan bahwa format gambar dan setelan kompresi yang direkomendasikan digunakan untuk setiap CDN.
Error dan peringatan bawaan
Selain pengoptimalan bawaan di atas, perintah ini juga memiliki pemeriksaan bawaan untuk memastikan bahwa developer telah mengikuti praktik terbaik yang direkomendasikan dalam markup gambar. Perintah gambar melakukan pemeriksaan berikut.
Gambar tidak berukuran: Perintah gambar menampilkan error jika markup gambar tidak menentukan lebar dan tinggi yang eksplisit. Gambar yang tidak berukuran dapat menyebabkan pergeseran tata letak, yang memengaruhi metrik Pergeseran Tata Letak Kumulatif (CLS) halaman. Praktik terbaik yang direkomendasikan untuk mencegah hal ini adalah gambar harus memiliki atribut
width
danheight
yang ditentukan.Rasio aspek: Perintah gambar menampilkan error untuk memberi tahu developer jika rasio aspek
width
:height
yang ditentukan di HTML tidak mendekati rasio aspek sebenarnya dari gambar yang dirender. Hal ini dapat menyebabkan gambar terlihat terdistorsi di layar. Hal ini dapat terjadi jika- Anda tidak sengaja menentukan dimensi (lebar atau tinggi) atau
- Jika Anda telah menentukan satu dimensi berdasarkan persentase di CSS, tetapi tidak menentukan dimensi lainnya (misalnya,
width: 100%
memerlukanheight: auto
untuk memastikan gambar tumbuh di kedua dimensi).
Gambar besar: Jika gambar tidak menentukan
srcset
dan gambar intrinsik secara signifikan lebih besar daripada gambar yang dirender, perintah akan menampilkan peringatan yang menyarankan penggunaan atributsrcset
dansizes
.Kepadatan gambar: Perintah ini akan menampilkan error jika Anda mencoba menyertakan gambar dalam
srcset
dengan kepadatan piksel lebih dari3x
. Deskripsi yang lebih tinggi dari2x
umumnya tidak direkomendasikan karena memiliki konsekuensi yang tidak diinginkan, yaitu memaksa perangkat seluler beresolusi tinggi mendownload gambar yang besar. Selain itu, mata manusia sebenarnya tidak dapat menunjukkan banyak perbedaan di atas 2x.
Tantangan
Menyesuaikan strategi pengoptimalan gambar agar berfungsi dalam framework sisi klien merupakan tantangan utama saat mendesain NgOptimizedImage
. Pengalaman rendering default di Next.js adalah Rendering Sisi Server (SSR) atau Pembuatan Situs Statis (SSG), sedangkan yang ada di Angular adalah Rendering Sisi Klien (CSR). Meskipun Angular mendukung library SSR - angular/universal - sebagian besar aplikasi Angular (~60%) menggunakan CSR.
Perintah gambar sepenuhnya dibuat untuk CSR agar selaras dengan kasus penggunaan umum di aplikasi Angular. Hal ini menetapkan kendala tambahan, dan tim harus memikirkan kembali cara membangun pengoptimalan khusus untuk aplikasi CSR.
Beberapa tantangan yang dihadapi adalah sebagai berikut:
Petunjuk referensi pendukung
Pramuat aset penting membantu browser menemukannya lebih awal. Namun, menyertakan petunjuk resource dalam aplikasi Angular rumit karena:
Penambahan Manual: Developer sulit menambahkan petunjuk resource
preload
secara manual. Angular menggunakan satu file index.html bersama untuk seluruh project atau untuk semua rute di situs. Dengan demikian,<head>
dokumen sama untuk setiap rute (setidaknya pada waktu inferensi). Menambahkan petunjukpreload
ke<head>
berarti resource akan dipramuat untuk semua rute bahkan saat tidak diperlukan. Oleh karena itu, penambahan petunjukpreload
secara manual tidak direkomendasikan.Penambahan otomatis selama render: Menggunakan framework untuk menambahkan petunjuk pramuat ke bagian head dokumen selama rendering dalam aplikasi CSR tidak membantu. Karena rendering terjadi setelah JavaScript didownload dan dijalankan,
<head>
akan terlambat dirender menjadi nilai apa pun.Untuk versi pertama perintah ini, kombinasi petunjuk
preconnect
dan petunjukfetchpriority
berfungsi untuk memprioritaskan gambar sebagai penggantipreload
. Namun, saat ini Aurora bekerja sama dengan tim Angular CLI untuk mengaktifkan injeksi otomatis petunjuk resource pada waktu build. Nantikan kabar terbarunya.Mengoptimalkan ukuran dan format gambar di server
Karena aplikasi Angular biasanya dirender sisi klien, gambar pada sistem file tidak dapat dikompresi pada waktu permintaan dan ditayangkan sebagaimana adanya. Oleh karena itu, sebaiknya gunakan CDN gambar untuk mengompresi gambar dan mengonversinya menjadi format modern seperti WebP atau AVIF sesuai permintaan.
Meskipun perintah tersebut tidak memberlakukan penggunaan CDN gambar, sangat disarankan untuk menggunakannya dengan perintah dan loader bawaannya untuk memastikan bahwa opsi konfigurasi yang benar digunakan.
Dampak
Demo berikut menunjukkan perbedaan yang dapat dihasilkan perintah gambar Angular terhadap performa gambar. Laporan ini membandingkan dua situs:
Website One: Menggunakan elemen <img>
native dengan gambar yang disajikan melalui Imgix CDN (dengan opsi konfigurasi default).
Situs Dua: Gunakan perintah gambar untuk semua gambar. Hal ini juga mencakup pengoptimalan yang direkomendasikan secara langsung oleh peringatan atau error yang ditampilkan oleh perintah.
Tim ini bekerja sama dengan partner untuk memvalidasi dampak performa perintah gambar pada aplikasi Angular perusahaan yang sebenarnya.
Salah satu partner tersebut adalah Land's End. Diharapkan bahwa situs mereka akan menjadi kasus pengujian yang baik untuk hasil yang dapat dilihat oleh aplikasi nyata.
Pengujian lab Lighthouse dilakukan di lingkungan UM (Uji Mutu) mereka sebelum dan sesudah menggunakan perintah gambar. Di desktop, LCP mediannya menurun dari 12,0 detik menjadi 3,0 detik, dengan peningkatan LCP sebesar 75%. Di perangkat seluler, median LCP menurun dari 20,2 dtk menjadi 12,0 dtk (peningkatan 40,6%).
Roadmap Masa Mendatang
Ini adalah bagian pertama desain untuk perintah gambar Angular. Ada banyak fitur lain yang direncanakan untuk versi mendatang, termasuk:
Dukungan yang lebih baik untuk gambar responsif:
NgOptimizedImage
saat ini mendukung penggunaansrcset
, tetapi atributsrcset
dansizes
harus disediakan secara manual untuk setiap gambar. Di masa mendatang, perintah tersebut dapat membuat atributsrcset
dansizes
secara otomatis.Injeksi otomatis petunjuk resource
Anda mungkin dapat berintegrasi dengan Angular CLI untuk menghasilkan tag prakoneksi dan pramuat untuk gambar LCP yang penting.
Dukungan untuk SSR Angular
Versi MVP dirancang dengan mempertimbangkan batasan CSR Angular, tetapi juga penting untuk mengeksplorasi solusi pengoptimalan gambar untuk Angular SSR (angular/universal).
Peningkatan pengalaman developer
NgOptimizedImage
mengharuskan atributwidth
danheight
ditentukan untuk setiap gambar. Namun, menentukan nilai ini untuk setiap gambar mungkin melelahkan bagi sebagian developer. Ada potensi untuk meningkatkan pengalaman developer di sini pada iterasi berikutnya sebagai berikut:- Mendukung mode tambahan (mirip dengan opsi tata letak gambar "
fill
" di Next.js) yang tidak memerlukan lebar/tinggi eksplisit untuk ditentukan. - Menggunakan integrasi CLI untuk menyetel lebar dan tinggi gambar lokal secara otomatis dengan menentukan dimensi gambar yang sebenarnya.
- Mendukung mode tambahan (mirip dengan opsi tata letak gambar "
Kesimpulan
Perintah gambar Angular akan tersedia untuk developer secara bertahap, dimulai dengan versi pratinjau developer di v14.2.0. Cobalah NgOptimizedImage
dan berikan masukan.
Dengan ucapan terima kasih khusus kepada Katie Hempenius dan Alex Castle atas kontribusinya.