Apa sebenarnya Penggantian Modul Panas di Webpack?

245

Saya telah membaca beberapa halaman tentang Penggantian Modul Panas di Webpack.
Bahkan ada aplikasi sampel yang menggunakannya .

Saya sudah membaca semua ini dan masih belum mengerti.

Apa yang bisa saya lakukan dengannya?

  1. Apakah itu seharusnya hanya digunakan dalam pengembangan dan bukan dalam produksi?
  2. Apakah ini seperti LiveReload, tetapi Anda harus mengelolanya sendiri?
  3. Apakah WebpackDevServer terintegrasi dengan LiveReload dalam beberapa cara?

Misalkan saya ingin memperbarui CSS saya (satu stylesheet) dan modul JS ketika saya menyimpannya ke disk, tanpa memuat ulang halaman dan tanpa menggunakan plugin seperti LiveReload. Apakah ini sesuatu yang Hot Module Replacement dapat membantu saya? Pekerjaan apa yang harus saya lakukan, dan apa yang sudah disediakan HMR?

Dan Abramov
sumber
HMR dengan Webpack hampir sebagus ini: medium.com/@the1mills/…
Alexander Mills

Jawaban:

407

Pertama saya ingin mencatat bahwa Hot Module Replacement (HMR) masih merupakan fitur eksperimental.

HMR adalah cara bertukar modul dalam aplikasi yang sedang berjalan (dan menambah / menghapus modul). Anda pada dasarnya dapat memperbarui modul yang diubah tanpa memuat ulang satu halaman penuh.

Dokumentasi

Prasyarat:

Ini tidak terlalu banyak untuk HMR, tetapi di sini adalah tautannya:

Saya akan menambahkan jawaban ini ke dokumentasi.

Bagaimana cara kerjanya?

Dari tampilan aplikasi

Kode aplikasi meminta runtime HMR untuk memeriksa pembaruan. Runtime HMR mengunduh pembaruan (async) dan memberi tahu kode aplikasi bahwa pembaruan tersedia. Kode aplikasi meminta runtime HMR untuk menerapkan pembaruan. Runtime HMR menerapkan pembaruan (sinkronisasi). Kode aplikasi mungkin atau mungkin tidak memerlukan interaksi pengguna dalam proses ini (Anda memutuskan).

Dari tampilan compiler (webpack)

Selain aset normal, kompiler perlu memancarkan "Pembaruan" untuk memungkinkan pembaruan dari versi sebelumnya ke versi ini. "Pembaruan" berisi dua bagian:

  1. manifes pembaruan (json)
  2. satu atau beberapa potongan pembaruan (js)

Manifes berisi hash kompilasi baru dan daftar semua potongan pembaruan (2).

Potongan pembaruan berisi kode untuk semua modul yang diperbarui dalam potongan ini (atau bendera jika modul dihapus).

Kompilator juga memastikan bahwa modul dan id chunk konsisten antara build ini. Ini menggunakan file json "catatan" untuk menyimpannya di antara build (atau menyimpannya di memori).

Dari tampilan modul

HMR adalah fitur opt-in, sehingga hanya memengaruhi modul yang berisi kode HMR. Dokumentasi menjelaskan API yang tersedia dalam modul. Secara umum, pengembang modul menulis penangan yang dipanggil ketika ketergantungan modul ini diperbarui. Mereka juga dapat menulis handler yang dipanggil saat modul ini diperbarui.

Dalam kebanyakan kasus, itu tidak wajib untuk menulis kode HMR di setiap modul. Jika modul tidak memiliki penangan HMR, pembaruan akan muncul. Ini berarti penangan tunggal dapat menangani pembaruan untuk pohon modul lengkap. Jika satu modul di pohon ini diperbarui, pohon modul lengkap dimuat kembali (hanya dimuat ulang, tidak ditransfer).

Dari tampilan runtime HMR (teknis)

Kode tambahan dikeluarkan untuk runtime sistem modul untuk melacak modul parentsdan children.

Di sisi manajemen, runtime mendukung dua metode: checkdan apply.

A checkmelakukan permintaan HTTP ke manifes pembaruan. Ketika permintaan ini gagal, tidak ada pembaruan yang tersedia. Selain itu daftar potongan yang diperbarui dibandingkan dengan daftar potongan yang saat ini dimuat. Untuk setiap potongan yang dimuat, potongan pembaruan yang sesuai diunduh. Semua pembaruan modul disimpan dalam runtime sebagai pembaruan. Runtime beralih ke readystatus, artinya pembaruan telah diunduh dan siap untuk diterapkan.

Untuk setiap permintaan potongan baru dalam status siap, potongan pembaruan juga diunduh.

The applyMetode bendera semua diperbarui modul sebagai tidak valid. Untuk setiap modul yang tidak valid, perlu ada handler pembaruan dalam modul atau handler pembaruan di setiap orangtua. Lepaskan gelembung yang tidak valid dan tandai semua orang tua juga tidak valid. Proses ini berlanjut sampai tidak ada lagi "gelembung" terjadi. Jika gelembung sampai ke titik masuk, proses gagal.

Sekarang semua modul yang tidak valid dibuang (buang pengendali) dan dibongkar. Kemudian hash saat ini diperbarui dan semua penangan "terima" dipanggil. Runtime beralih kembali ke idlekeadaan dan semuanya berlanjut seperti biasa.

potongan pembaruan yang dihasilkan

Apa yang bisa saya lakukan dengannya?

Anda dapat menggunakannya dalam pengembangan sebagai pengganti LiveReload. Sebenarnya webpack-dev-server mendukung mode panas yang mencoba memperbarui dengan HMR sebelum mencoba memuat ulang seluruh halaman. Anda hanya perlu menambahkan webpack/hot/dev-servertitik masuk dan memanggil server-dev dengan --hot.

Anda juga dapat menggunakannya dalam produksi sebagai mekanisme pembaruan. Di sini Anda perlu menulis kode manajemen Anda sendiri yang mengintegrasikan HMR dengan aplikasi Anda.

Beberapa loader sudah menghasilkan modul yang bisa diperbarui-panas. mis. style-loaderDapat menukar stylesheet. Anda tidak perlu melakukan sesuatu yang istimewa.

Misalkan saya ingin memperbarui CSS saya (satu stylesheet) dan modul JS ketika saya menyimpannya ke disk, tanpa memuat ulang halaman dan tanpa menggunakan plugin seperti LiveReload. Apakah ini sesuatu yang Hot Module Replacement dapat membantu saya?

Iya

Pekerjaan apa yang harus saya lakukan, dan apa yang sudah disediakan HMR?

Ini adalah sedikit contoh: https://webpack.js.org/guides/hot-module-replacement/

Modul hanya dapat diperbarui jika Anda "menerimanya". Jadi, Anda perlu module.hot.acceptmodul di orang tua atau orang tua dari orang tua ... misalnya Router adalah tempat yang bagus, atau subview.

Jika Anda hanya ingin menggunakannya dengan webpack-dev-server, tambahkan saja webpack/hot/dev-serversebagai titik masuk. Jika tidak, Anda memerlukan kode manajemen HMR yang memanggil checkdan apply.

Opini: Apa yang membuatnya sangat keren?

  • Ini LiveReload tetapi untuk setiap jenis modul.
  • Anda dapat menggunakannya dalam produksi.
  • Pembaruan menghormati Pemecahan Kode Anda dan hanya mengunduh pembaruan untuk bagian yang digunakan dari aplikasi Anda.
  • Anda dapat menggunakannya untuk bagian dari aplikasi Anda dan itu tidak mempengaruhi modul lain
  • Jika HMR dinonaktifkan, semua kode HMR dihapus oleh kompiler (bungkus dalam if(module.hot)).

Peringatan

  • Ini eksperimental dan tidak diuji dengan baik.
  • Harapkan beberapa bug.
  • Secara teoritis dapat digunakan dalam produksi, tetapi mungkin terlalu dini untuk menggunakannya untuk sesuatu yang serius.
  • ID modul harus dilacak di antara kompilasi sehingga Anda harus menyimpannya ( records).
  • Pengoptimal tidak dapat lagi mengoptimalkan ID modul setelah kompilasi pertama. Sedikit berdampak pada ukuran bundel.
  • Kode runtime HMR meningkatkan ukuran bundel.
  • Untuk penggunaan produksi, pengujian tambahan diperlukan untuk menguji penangan HMR. Ini bisa sangat sulit.
Tobias K.
sumber
145
Satu jawaban yang sangat sulit.
Dan Abramov
13
Terima kasih sekali lagi untuk penjelasannya, saya membuat video yang menunjukkan kekuatan HMR untuk mengedit langsung aplikasi Bereaksi.
Dan Abramov
1
cukup keren ... Saya berpikir tentang membuat loader reaksi yang menambahkan pemuatan HMR dan async untuk bereaksi komponen.
Tobias K.
4
Saya menyalin jawaban ini ke dalam dokumentasi: webpack.github.io/docs/hot-module-replacement-with-webpack.html
Tobias K.
2
Anda dapat menangkap kesalahan dalam modul yang diperbarui, ketika Anda membungkus requiredi dalam handler pembaruan HMR di blok try-catch.
Tobias K.
10

Jawaban yang diterima tetap menjelaskan semuanya dengan benar, uraian berikut membantu memahami apa itu HMR dengan cepat.

Penggantian Hot Module adalah salah satu teknik terbaru dalam pengembangan javascript yang menarik perhatian pengembang. Ini membantu pengembangan dengan mengurangi jumlah refresh halaman dengan mengganti modul dengan perubahan saat runtime.

Saat mencari tentang HMR saya menemukan sebuah artikel yang menjelaskan konsep di internet Anda bisa mendapatkannya dari sini dan menambahkan gambar GIF yang menjelaskan konsep tersebut tanpa banyak penjelasan.

Ini sedang bekerja - perhatikan bahwa timer tidak mereset ke 0 seperti setelah halaman dimuat ulang, dan css juga mengubah penyegaran otomatis. Modul Hot Penggantian GIF

Webpack membantu mencapai HMR. Anda dapat menemukan dokumen di sini

Ini membantu untuk mencapai yang berikut

  • Pertahankan status aplikasi yang hilang saat memuat ulang penuh.

  • Hemat waktu pengembangan yang berharga dengan hanya memperbarui apa yang berubah.

  • Tweak styling lebih cepat - hampir sebanding dengan mengubah gaya di debugger browser.

Berikut ini adalah panduan webpack untuk mencapai HMR

samuelj90
sumber