Apa perbedaan antara shim dan polyfill?

406

Keduanya tampaknya digunakan dalam lingkaran pengembangan web, lihat misalnya HTML5 Cross Browser Polyfills , yang mengatakan:

Jadi di sini kita mengumpulkan semua shims, fallback, dan polyfill ...

Atau, ada proyek es5-shim .

Dalam proyek saya saat ini, kami menggunakan sejumlah ini, dan saya ingin menempelkan semuanya di direktori yang sama. Jadi, apa yang harus saya sebut direktori ini --- shims, atau polyfills?

Domenik
sumber
6
buka kembali: Saya kira "apa yang harus saya sebut direktori ini" bisa berbasis pendapat, tetapi sebenarnya tidak diberi konteks yang lebih besar dari pertanyaan - juga bukan merupakan aspek yang paling penting dari pertanyaan ini. Semua jawaban di sini tampaknya sesuai, dan ada penggunaan fakta, referensi, dan keahlian khusus yang signifikan.
Nobar

Jawaban:

386
  • Sebuah shim adalah setiap bagian dari kode yang melakukan intersepsi dari panggilan API dan menyediakan lapisan abstraksi. Itu tidak selalu terbatas pada aplikasi web atau HTML5 / CSS3.

  • Sebuah polyfill adalah jenis shim yang retrofits warisan browser dengan HTML5 modern / CSS3 fitur biasanya menggunakan Javascript atau Flash.

Menjawab pertanyaan spesifik Anda, hubungi direktori shimsAnda jika Anda ingin menyimpan direktori generik.

Arsalan Ahmed
sumber
234

Shim

Jika Anda terbiasa dengan pola adaptor, maka Anda tahu apa itu shim. Shims memotong panggilan API dan membuat lapisan abstrak antara pemanggil dan target. Biasanya shims digunakan untuk kompabilitas mundur. Misalnya paket es5-shim npm akan membiarkan Anda menulis sintaks ECMAScript 5 (ES5) dan tidak peduli apakah browser menjalankan ES5 atau tidak. Ambil Date.now sebagai contoh. Ini adalah fungsi baru di ES5 di mana sintaks di ES3 akan menjadi Date baru (). GetTime () . Jika Anda menggunakan es5-shim Anda dapat menulis Date.now dan jika browser yang Anda jalankan mendukung ES5 itu hanya akan berjalan. Namun, jika browser menjalankan mesin ES3 es5-shim akan mencegat panggilan ke Date.nowdan cukup kembalikan Date (). getTime () sebagai gantinya. Intersepsi ini disebut shimming. Kode sumber yang relevan dari es5-shim terlihat seperti ini:

if (!Date.now) {
    Date.now = function now() {
        return new Date().getTime();
    };
}

Polyfill

Polyfilling sebenarnya hanya versi khusus shimming. Polyfill adalah tentang mengimplementasikan fitur-fitur yang hilang dalam API, sedangkan shim tidak harus sebanyak mengimplementasikan fitur-fitur yang hilang seperti halnya memperbaiki fitur. Saya tahu ini tampaknya terlalu samar, tetapi di mana shims digunakan sebagai istilah yang lebih luas, polyfill digunakan untuk menggambarkan shims yang memberikan kompabilitas ke belakang untuk browser yang lebih lama. Jadi, sementara shims digunakan untuk menutupi dosa-dosa lama, polyfill digunakan untuk mengembalikan perangkat tambahan di masa mendatang. Sebagai contoh tidak ada dukungan untuk sessionStorage di IE7, tetapi polyfill dalam paket npm penyimpanan sesi akan menambahkan fitur ini di IE7 (dan lebih lama) dengan menggunakan teknik seperti menyimpan data di properti nama jendela atau dengan menggunakan cookie.

Kjetil Klaussen
sumber
107
Jadi, sementara shims digunakan untuk menutupi dosa-dosa lama, polyfill digunakan untuk mengembalikan perangkat tambahan di masa mendatang. Ini meringkas segalanya bagiku. Terima kasih atas penjelasan yang jelas.
JohnnyQ
Jawaban ini sangat membantu, terima kasih. Tapi menurut saya kedua istilah itu sering tidak digunakan secara tepat di web, termasuk es5-shim. Saya pikir es5-shim adalah campuran antara shims dan polyfill menurut definisi Anda.
Matt Browne
WOW -> Jadi sementara shims digunakan untuk menutupi dosa-dosa lama, polyfill digunakan untuk mengembalikan perangkat tambahan di masa mendatang. <- Banyak terima kasih!
zeppelin
3
Tanggal-Contoh terlihat seperti Polyfill bagi saya. Mengapa saya pikir itu adalah Polyfill? Karena Date.now adalah panggilan asli. Polyfill akan menambahkan fitur itu dengan API yang sama mulus ke Browser. Shim hadir dengan API baru seperti: MyShim.Date.now(); Tolong perbaiki saya jika saya salah.
TatzyXY
99

Dari apa yang saya mengerti:

Polyfill adalah kode yang mendeteksi jika API "yang diharapkan" tidak ada dan mengimplementasikannya secara manual. Misalnya

if (!Function.prototype.bind) { Function.prototype.bind = ...; }

Shim adalah kode yang memotong panggilan API yang ada dan mengimplementasikan perilaku yang berbeda. Idenya di sini adalah untuk menormalkan API tertentu di berbagai lingkungan yang berbeda. Jadi, jika dua browser menerapkan API yang sama secara berbeda, Anda bisa mencegat panggilan API di salah satu browser itu dan membuat perilakunya selaras dengan browser lainnya. Atau, jika browser memiliki bug di salah satu API-nya, Anda bisa kembali mencegat panggilan ke API itu, dan kemudian menghindari bug tersebut.

Šime Vidas
sumber
66

Mengutip Axel Rauschmayer dari bukunya Speaking JavaScript :

  • Shim adalah perpustakaan yang membawa API baru ke lingkungan yang lebih lama, hanya menggunakan sarana lingkungan itu.
  • Polyfill adalah shim untuk API browser. Biasanya memeriksa apakah browser mendukung API. Jika tidak, polyfill akan menginstal implementasinya sendiri. Itu memungkinkan Anda untuk menggunakan API dalam kedua kasus tersebut. Istilah polyfill berasal dari produk perbaikan rumah; menurut Remy Sharp :

    Polyfilla adalah produk Inggris yang dikenal sebagai Spackling Paste di AS. Dengan mengingat hal itu: anggap browser sebagai dinding dengan retakan di dalamnya. [Polyfill] ini membantu menghaluskan retakan dan memberi kami dinding peramban yang bagus untuk bekerja.

Bergi
sumber
9

Shim. Shim adalah perpustakaan yang membawa API baru ke lingkungan yang lebih lama, hanya menggunakan sarana lingkungan itu.

Polyfill. Pada Oktober 2010, Remy Sharp membuat blog tentang istilah "polyfill" [via Rick Waldron]:

Sebuah polyfill adalah bagian dari kode (atau plugin) yang menyediakan teknologi yang Anda, pengembang, harapkan dari browser untuk berikan secara asli. Meratakan lanskap API jika Anda mau.

Sagittarius
sumber
8

Artikel fantastis yang ditulis tentang ini dari beberapa tahun yang lalu menjelaskan ini dengan baik:

Apa itu Polyfill?

Dalam artikel tersebut, (2) sangat kontras seperti:

Shim: sepotong kode yang dapat Anda tambahkan (yaitu JavaScript) yang akan memperbaiki beberapa fungsi, tetapi paling sering memiliki API itu sendiri .

Polyfill: sesuatu yang bisa Anda singgahi (yaitu JavaScript) dan itu akan bekerja secara diam-diam untuk meniru API browser yang ada yang tidak didukung.

atconway
sumber
1
Saya pikir ini adalah representasi yang menyesatkan dari penggunaan umum dan apa yang sebenarnya dikatakan Remy Sharp dalam posting blog yang Anda tautkan. Shim paling sering digunakan secara sinonim dengan polyfill saat ini (lihat khususnya es5-shim dan es6-shim ) dan Remy secara khusus mengatakan bahwa baginya kata 'shim' disinggung dengan API kustom (dibandingkan dengan shim.gif). Dia sangat tidak mendikte bahwa kata-kata digunakan dengan cara ini, dan dengan mengatakan "kepada saya" dia diam-diam mengakui bahwa penggunaannya tidak universal.
Mark Amery