2 poin oleh GN⁺ 2024-04-15 | 1 komentar | Bagikan ke WhatsApp

Batasan WebAssembly dan pentingnya Tree-shaking

  • WebAssembly, meski mendapat banyak perhatian dan ekspektasi, hanya meraih keberhasilan yang terbatas di web

    • Ada contoh sukses seperti Photoshop, tetapi secara umum tidak banyak proyek yang memanfaatkan WebAssembly
    • Terutama untuk aplikasi yang banyak menggunakan DOM, WebAssembly tidak cocok
    • Salah satu penyebab utamanya adalah perbedaan model pemrograman antara JavaScript dan WebAssembly
  • WebAssembly belum banyak berhasil di luar bahasa seperti C atau Rust

    • Bahasa seperti C# memiliki ketidaknyamanan karena harus menyediakan runtime seperti garbage collector bersama-sama
    • Namun, fitur baru WebAssembly yang mendukung reference types dan garbage collection akan segera diperkenalkan, sehingga situasinya diharapkan membaik

Kemampuan optimalisasi kode compiler adalah kunci keberhasilan WebAssembly

  • Agar WebAssembly berhasil di web, compiler harus mampu menghasilkan kode yang kecil dan efisien

    • Penting untuk mempertahankan ukuran file yang kecil, hanya beberapa kilobyte
    • Jika tidak, mau tak mau harus bergantung pada hype atau basis pengguna tertentu
  • Di dunia JavaScript, optimalisasi ukuran kode dilakukan melalui bundler dan sejenisnya

    • Tree-shaking adalah teknik untuk hanya menyertakan fungsi dan tipe data yang benar-benar digunakan dalam program
  • Tree-shaking adalah metafora yang kurang tepat dari sudut pandang hortikultural maupun algoritmik, tetapi istilah ini sudah digunakan secara luas

Kondisi Tree-shaking di bahasa lain

  • Pada bahasa dengan runtime yang berat seperti Go atau Python, Tree-shaking masih belum dioptimalkan

    • Bahkan program Go paling sederhana pun, jika dikompilasi ke WebAssembly, menghasilkan ukuran lebih dari 2MB
    • Pyodide untuk Python juga mengharuskan pengunduhan file sekitar 20MB
  • Di lingkungan server, ukuran biner yang besar bukan masalah besar

    • Untuk lingkungan terbatas seperti mobile, toolchain yang lebih ringan seperti MicroPython dan TinyGo juga dikembangkan secara terpisah
  • Implementasi bahasa untuk lingkungan web mau tidak mau akan berbeda dari implementasi yang sudah ada

    • Karena berinteraksi dengan DOM itu sendiri merupakan lingkungan yang tidak biasa
    • Dalam kasus ClojureScript, perbedaannya dengan Clojure didokumentasikan secara terpisah

Diskusi tentang algoritme Tree-shaking

  • Compiler Hoot Scheme yang sedang dikembangkan penulis saat ini menghasilkan kode Wasm berukuran sekitar 70KB

    • Menyertakan hanya definisi fungsi (procedure) relatif mudah
    • Namun, ada beberapa titik sulit seperti di bawah ini
  • Dalam model evaluasi letrec*, binding bersifat rekursif sekaligus berurutan sehingga sulit dianalisis oleh compiler

    • Untuk record type, callback vtable membuat banyak kode tetap dipertahankan
  • Jika menggunakan fungsi dengan polimorfisme tinggi seperti display, banyak kode terkait ikut disertakan

    • Lebih baik menggunakan fungsi yang lebih spesifik seperti write-string
  • Untuk Tree-shaking yang optimal, diperlukan flow analysis

    • Jika diketahui bahwa argumen bitvector tidak pernah diberikan ke display, kode terkait dapat dihapus
  • Di Python, hal ini lebih sulit karena ada dispatch dinamis dan fitur dinamis seperti __getattr__

    • Struktur modul Python juga menjadi faktor yang membuat Tree-shaking lebih kompleks

Ringkasan

  • Dukungan GC memungkinkan pemrograman DOM di WebAssembly dengan bahasa selain JavaScript
  • Namun, untuk membuat ukuran hasil akhir cukup kecil, dibutuhkan investasi yang besar pada toolchain tiap bahasa
  • Diperlukan pengembangan toolchain terpisah yang menerapkan algoritme Tree-shaking serta optimalisasi standard library

Opini GN⁺

  • Dengan dukungan GC di WebAssembly, kini berbagai bahasa bisa digunakan untuk pengembangan web, tetapi tampaknya masih banyak kesulitan jika ingin langsung membawa toolchain bahasa yang sudah ada. Sepertinya perlu dikembangkan implementasi bahasa dan teknik optimalisasi yang khusus untuk lingkungan web.

  • Agar Tree-shaking bekerja baik pada bahasa dengan dynamic typing, tampaknya static analysis adalah hal yang wajib. Namun, bahasa seperti Python memiliki banyak fitur dinamis sehingga sepertinya tidak mudah. Bisa jadi, membuat bahasa baru sejak awal yang lebih ramah terhadap static analysis juga merupakan salah satu pendekatan.

  • Proyek eksperimental seperti Hoot atau TinyGo tampaknya bisa menjadi referensi yang baik. Namun, untuk menerapkan proyek semacam ini ke produk nyata, mungkin masih terlalu dini. Sepertinya perbaikannya memang harus dilakukan secara bertahap.

  • Jika proyek tidak terlalu sensitif terhadap performa dan yang lebih penting adalah kecepatan pengembangan, sesuatu seperti Pyodide mungkin layak dicoba. Namun, jika produknya mengutamakan pengalaman pengguna, untuk saat ini JavaScript tampaknya masih menjadi pilihan terbaik.

  • Bisa juga dibayangkan WebAssembly sendiri memiliki fitur seperti Tree-shaking. Namun, hal itu tentu tidak mudah karena kebutuhan tiap bahasa berbeda-beda. Di sisi lain, jika muncul bahasa yang sangat mendukung Tree-shaking, mungkin justru lebih menguntungkan untuk menulis kode dalam bahasa tersebut. Menarik untuk melihat bagaimana pembagian peran antara WebAssembly dan bahasa pemrograman akan berkembang.

1 komentar

 
GN⁺ 2024-04-15
Opini Hacker News

Ringkasnya sebagai berikut:

  • Dalam proyek OpenEtG, dilakukan upaya berikut untuk menjaga ukuran biner WASM yang ditulis dengan Rust tetap di bawah 400KB
    • menggunakan aritmetika fixed-point alih-alih float
    • menggunakan Vec alih-alih HashMap
    • meminimalkan penggunaan string
    • menggunakan allocator kecil (talc)
    • meminimalkan dependensi (hanya menggunakan rand dan fxhash)
    • menghindari keragaman generik
    • merancang algoritme dengan mempertimbangkan ukuran
  • Tree-shaking adalah istilah yang keliru, dan di kompiler Virgil ini disebut Reachability Analysis. Selama proses kompilasi, penelusuran dilakukan dari entry point main, dan hanya kode yang dapat dijangkau yang dimasukkan ke biner akhir.
  • Berkat WasmGC, Java dan Kotlin dapat menghasilkan biner WASM kecil sekitar 2-3KB. Namun, pemilihan API perlu dilakukan dengan hati-hati.
  • Manipulasi DOM dengan WASM masih tetap bergantung pada JS.
  • Istilah Tree Shaking muncul karena Dead Code Elimination sudah ada sejak lama.
  • Masalah ukuran kode pada WASM muncul karena runtime bahasa dan pustaka standar semuanya harus dibundel.
  • Untuk mengatasinya, shared library dan dynamic linking bisa dipertimbangkan.
    • Pyodide adalah contoh representatif yang mendukung dynamic linking
    • jika browser memuat lebih dulu runtime bahasa yang populer, halaman web dapat berbagi runtime tersebut
  • Bahasa Zig cocok untuk menghasilkan biner WASM kecil. Namun, jika ukurannya di bawah 100KB, ukuran bukan faktor yang penting.
  • GC bawaan tidak penting untuk semua aplikasi, dan lebih baik membuat web app tanpa GC.
  • Faktor keberhasilan aplikasi yang menggunakan WASM tetaplah peningkatan performa.
  • Pemrograman DOM dalam bahasa selain JS sudah lama dilakukan melalui bahasa compile-to-JS seperti ClojureScript, TypeScript, dan ReasonML.
  • Melalui asm.js dan emscripten, bahasa berbasis C juga sudah dikompilasi dan digunakan di web sebelum WASM.
  • Google Maps dan Google Earth adalah contoh aplikasi representatif yang menggunakan WASM.