TL;DR: Extensions API telah diupdate untuk mendukung navigasi pramuat dan back/forward cache. Lihat detailnya di bawah ini.
Chrome telah bekerja keras untuk membuat navigasi menjadi cepat. Teknologi Navigasi Instan seperti Cache Mundur/Maju (dikirim di desktop di Chrome 96) dan Aturan Spekulasi (dikirim di Chrome 103) meningkatkan pengalaman versi sebelumnya dan yang lebih baru. Dalam postingan ini, kita akan mempelajari update yang kami buat pada API ekstensi browser untuk mengakomodasi alur kerja baru ini.
Memahami jenis-jenis halaman
Sebelum diperkenalkan dengan Back/Forward Cache dan pra-rendering, setiap tab hanya memiliki satu halaman aktif. Ini selalu yang terlihat. Jika pengguna kembali ke halaman sebelumnya, halaman aktif akan dihancurkan (Halaman B) dan halaman sebelumnya dalam histori akan sepenuhnya dibuat ulang (Halaman A). Ekstensi tidak perlu khawatir tentang bagian mana dari halaman siklus proses karena hanya ada satu untuk tab, yaitu status aktif/terlihat.
Dengan Back/Forward Cache dan pra-rendering, tidak ada lagi hubungan one-to-one antara tab dan halaman. Sekarang, setiap tab sebenarnya menyimpan beberapa halaman dan transisi halaman antar-status, bukan dihancurkan dan direkonstruksi.
Misalnya, halaman dapat memulai proses pra-rendering (tidak terlihat), beralih ke halaman aktif (terlihat) saat pengguna mengklik link, lalu disimpan di Cache Back/Forward (tidak terlihat) saat pengguna membuka halaman lain, semuanya tanpa halaman dihancurkan. Nanti dalam artikel ini, kita akan melihat properti baru yang diekspos untuk membantu ekstensi memahami halaman status.
Perhatikan bahwa tab dapat memiliki serangkaian halaman pra-rendering (bukan hanya satu), satu halaman aktif (terlihat), dan serangkaian halaman yang disimpan dalam cache Mundur/Maju.
Apa saja yang berubah bagi developer ekstensi?
IDBingkai == 0
Di Chromium, kami menyebut bingkai paling atas/utama sebagai bingkai paling luar.
Penulis ekstensi yang mengasumsikan frameId
dari frame terluar adalah 0 (praktik terbaik sebelumnya) mungkin memiliki masalah.
Karena tab kini dapat memiliki beberapa frame terluar (halaman yang dipra-render dan di-cache), asumsi bahwa ada satu frame terluar untuk sebuah tab tidak benar. frameId == 0
akan terus terus mewakili
frame terluar halaman aktif, tetapi frame terluar
halaman lain di tab yang sama tidak akan nol. Kolom baru frameType telah
ditambahkan untuk memperbaiki masalah ini. Lihat bagian “Bagaimana cara menentukan apakah frame adalah frame terluar?”
dari postingan ini.
Siklus proses frame versus dokumen
Konsep lain yang bermasalah dengan ekstensi adalah siklus proses frame. Frame menghosting dokumen (yang terkait dengan commit URL). Dokumen dapat berubah (misalnya dengan menavigasi) tetapi frameId tidak akan berubah, sehingga sulit untuk mengaitkan sesuatu yang terjadi dalam dokumen tertentu hanya dengan frameIds. Kami memperkenalkan konsep documentId yang merupakan ID unik untuk setiap dokumen. Jika sebuah {i>frame<i} dinavigasi dan membuka dokumen baru, ID akan berubah. Kolom ini berguna untuk menentukan kapan halaman mengubah status siklus prosesnya (antara pra-rendering/aktif/di-cache) karena kolom tersebut tetap sama.
Peristiwa navigasi web
Peristiwa di namespace chrome.webNavigation
dapat diaktifkan beberapa kali di halaman yang sama, bergantung pada siklus prosesnya. Lihat bagian
“Bagaimana cara mengetahui siklus proses yang dilalui halaman?”
dan “Bagaimana cara menentukan kapan halaman bertransisi?”.
Bagaimana cara mengetahui siklus proses halaman?
Jenis DocumentLifecycle
telah ditambahkan ke sejumlah API ekstensi tempat frameId
sebelumnya tersedia. Jika jenis DocumentLifecycle
ada pada peristiwa
(seperti onCommitted
),
nilainya adalah status saat peristiwa dibuat. Anda selalu dapat mengkueri
informasi dari metode WebNavigation
getFrame()
dan getAllFrames()
, tetapi menggunakan nilai dari peristiwa akan selalu lebih disarankan. Jika Anda menggunakan salah satu metode, perhatikan bahwa status frame dapat berubah antara saat peristiwa dihasilkan dan saat promise yang ditampilkan oleh kedua metode tersebut diselesaikan.
DocumentLifecycle
memiliki nilai berikut:
"prerender
" : Saat ini tidak ditampilkan kepada pengguna, tetapi sedang disiapkan untuk mungkin ditampilkan kepada pengguna."active"
: Saat ini ditampilkan kepada pengguna."cached"
: Disimpan di Back/Forward Cache."pending_deletion"
: Dokumen sedang dihancurkan.
Bagaimana cara menentukan apakah {i>frame<i} adalah {i>frame<i} terluar?
Sebelumnya, ekstensi mungkin telah memeriksa apakah frameId == 0
akan menentukan
apakah peristiwa yang terjadi adalah untuk frame terluar atau bukan. Dengan beberapa halaman di tab, sekarang kita memiliki beberapa frame terluar, sehingga definisi frameId bermasalah. Anda tidak akan pernah menerima peristiwa terkait frame yang di-cache Mundur/Maju. Namun, untuk frame pra-rendering, frameId
akan
bukan nol untuk frame terluar. Jadi, menggunakan frameId == 0
sebagai sinyal untuk
menentukan apakah frame terluarnya salah.
Untuk membantu hal ini, kami memperkenalkan jenis baru yang disebut
FrameType
sehingga menentukan apakah frame tersebut memang frame terluar sekarang menjadi mudah.
FrameType
memiliki nilai berikut:
"outermost_frame"
: Biasanya disebut sebagai frame paling atas. Perlu diperhatikan bahwa ada beberapa di antaranya. Misalnya, jika Anda memiliki halaman pra-rendering dan cache, masing-masing memiliki frame terluar yang dapat disebut frame paling atas."fenced_frame"
: Disediakan untuk penggunaan pada masa mendatang."sub_frame"
: Biasanya berupa iframe.
Kita dapat menggabungkan DocumentLifecycle
dengan FrameType
dan menentukan apakah frame adalah
frame terluar yang aktif. Contoh:
js
tab.documentLifecycle == “active” && frameType == “outermost_frame”
Bagaimana cara menyelesaikan masalah waktu penggunaan dengan frame?
Seperti yang kami katakan di atas, frame menghosting dokumen dan frame tersebut dapat membuka dokumen
baru, tetapi frameId
tidak akan berubah. Hal ini akan menimbulkan masalah saat Anda
menerima peristiwa hanya dengan frameId
. Jika Anda mencari URL frame, URL tersebut mungkin berbeda dengan saat peristiwa terjadi, ini disebut masalah waktu penggunaan.
Untuk mengatasinya, kami memperkenalkan documentId
(dan parentDocumentId
).
Metode webNavigation.getFrame()
kini menjadikan frameId
opsional jika documentId
disediakan. documentId
akan berubah setiap kali frame dinavigasi.
Bagaimana cara menentukan kapan transisi halaman?
Ada sinyal eksplisit untuk menentukan kapan halaman bertransisi antar-status.
Mari kita lihat peristiwa WebNavigation
.
Untuk navigasi pertama di halaman mana pun, Anda akan melihat empat peristiwa dalam urutan yang tercantum di bawah ini. Perhatikan bahwa keempat peristiwa ini dapat terjadi dengan
status DocumentLifecycle
menjadi "prerender"
atau "active"
.
onBeforeNavigate
onCommitted
onDOMContentLoaded
onCompleted
Hal ini diilustrasikan dalam diagram di bawah yang menunjukkan perubahan
documentId
menjadi "xyz"
saat halaman pra-rendering menjadi halaman aktif.
Saat halaman bertransisi dari Cache Back/Forward atau pra-rendering ke
status aktif, akan ada tiga peristiwa lagi (tetapi DocumentLifecyle
menjadi "active"
).
onBeforeNavigate
onCommitted
onCompleted
documentId
akan tetap sama seperti di acara asli. Hal ini
diilustrasikan di atas saat documentId
== xyz diaktifkan. Perhatikan bahwa
peristiwa navigasi yang sama diaktifkan, kecuali untuk peristiwa onDOMContentLoaded
karena halaman sudah dimuat.
Jika ada komentar atau pertanyaan, jangan ragu untuk bertanya di grup chromium-extensions.