- WebAssembly (Wasm) ยังคงถูกใช้เป็นเทคโนโลยีแกนหลักในผลิตภัณฑ์จริงที่หลากหลาย และมีบทบาทสำคัญใน เกมเอนจิน เครื่องมือออกแบบ และเว็บคอนเทนเนอร์
- ตัวภาษาเองมี โครงสร้างที่แมปกับฮาร์ดแวร์ได้อย่างมีประสิทธิภาพ และถูกออกแบบโดยเน้น ความปลอดภัยและความสามารถในการพกพา
- โมเดลความปลอดภัย เป็นแบบ ‘deny-by-default’ ทำให้ การแยกระดับโปรเซสและความเร็วในการรันสูง เป็นไปได้
- มีการใช้งานในสภาพแวดล้อมหลากหลายผ่าน ระบบนิเวศปลั๊กอินและการรองรับข้ามภาษา แต่ ยังไม่ได้ถูกนำไปใช้ในระดับที่แทนทั้งเบราว์เซอร์ได้
- ปัจจุบัน WebAssembly ถูก ผสานรวมอย่างลึกซึ้งในระดับไลบรารีและรันไทม์ และเป็นเทคโนโลยีที่กำลังพัฒนาอย่างรวดเร็วทั้งด้านมาตรฐานและการขยายความสามารถ
กรณีใช้งานจริง
- WebAssembly รับผิดชอบฟังก์ชันหลักใน Godot, Figma, Stackblitz, Squoosh.app, Zellij, Ruffle
- Godot ใช้สำหรับบิลด์เกมบนเว็บ และ Figma ใช้แปลงโค้ด C++ ให้อยู่ในรูปแบบที่รันในเบราว์เซอร์ได้
- Stackblitz ใช้ Wasm สำหรับเว็บคอนเทนเนอร์ และ Ruffle ใช้ Wasm เป็น Flash emulator
- อย่างไรก็ตาม เว็บไซต์ขนาดใหญ่ที่สร้างทั้งเว็บด้วย Wasm ยังมีน้อยมาก โดยส่วนใหญ่ใช้ในระดับฟังก์ชันเฉพาะ
นิยามของ WebAssembly และความเร็ว
- WebAssembly เป็น ภาษา (language) โดยแนวคิดเรื่องความเร็วไม่ได้อยู่ที่ตัวภาษาเอง แต่ ขึ้นอยู่กับประสิทธิภาพของเอนจิน
- เช่นเดียวกับ JavaScript รันไทม์เอนจิน (V8, SpiderMonkey เป็นต้น) เป็นตัวกำหนดความเร็วในการรัน
- WebAssembly มี โครงสร้างที่แมปกับฮาร์ดแวร์สมัยใหม่ได้อย่างมีประสิทธิภาพ และรองรับได้ทั้งแบบคอมไพล์และอินเทอร์พรีต
โครงสร้างที่แมปได้อย่างมีประสิทธิภาพ
- Wasm เป็น ไบต์โค้ดที่ใกล้เคียงกับภาษาแอสเซมบลี ซึ่งสามารถคอมไพล์ไปยังฮาร์ดแวร์ส่วนใหญ่ได้โดยแทบไม่สูญเสียข้อมูล
- WAT (WebAssembly Text) คือรูปแบบข้อความของ Wasm ซึ่งแทบจะแปลงกันได้แบบ 1:1
- คล้ายกับ JVM bytecode แต่ มี API ขนาดเล็กและรับประกันความปลอดภัยได้เข้มแข็งกว่า
- การเข้าถึงหน่วยความจำเป็นแบบชัดเจน และใช้ได้เฉพาะทรัพยากรที่โฮสต์อนุญาตเท่านั้น
Wasm ในฐานะเป้าหมายการคอมไพล์
- ภาษาหลากหลายอย่าง Rust, C, Zig, Go, Kotlin, Java, C# สามารถคอมไพล์เป็น Wasm ได้
- ภาษาแบบอินเทอร์พรีเตอร์อย่าง Python, PHP, Ruby ก็สามารถรันผ่าน Wasm build ได้เช่นกัน
- เบราว์เซอร์มี Wasm engine มาให้โดยพื้นฐาน และยังมีรันไทม์อิสระอย่าง Wasmtime, WasmEdge, Wasmer
- อาร์ติแฟกต์ Wasm เพียงชิ้นเดียวสามารถ รันได้โดยไม่ผูกกับฮาร์ดแวร์เฉพาะ
โครงสร้างความปลอดภัยและการใช้งาน
- WebAssembly ใช้ โมเดลความปลอดภัยแบบ ‘deny-by-default’ โดยอนุญาตการเข้าถึงภายนอกผ่าน import ที่ประกาศไว้อย่างชัดเจนเท่านั้น
- มี hidden control-flow stack, linear memory และชุดคำสั่งที่จำกัด จึงรับประกันการแยกส่วนได้อย่างแข็งแกร่ง
- Cloudflare ใช้ V8 isolate เพื่อแยกการรันโค้ดที่อิง Wasm และ Fermyon ให้ เวลาเริ่มต้นระดับต่ำกว่ามิลลิวินาที
- Ruffle ใช้ฟื้นฟูคอนเทนต์ Flash อย่างปลอดภัย, Pyodide รัน Python บน Wasm และ Figma รันปลั๊กอินผ่าน QuickJS ที่อิง Wasm
ความสามารถในการพกพาและการฝังตัว
- Wasm runtime มีขนาดเบา และ Zellij, Envoy, Lapce ก็เลือกใช้ Wasm สำหรับระบบปลั๊กอิน
- แม้ในสภาพแวดล้อมที่มี JavaScript engine อยู่แล้ว ก็ยังใช้ไลบรารี Wasm ได้หลากหลาย เช่น การประมวลผลภาพ, OCR, ฟิสิกส์เอนจิน, การเรนเดอร์, media toolkit, ฐานข้อมูล, parser
- ในกรณีส่วนใหญ่ ผู้ใช้ไม่รู้ตัวด้วยซ้ำว่ากำลังใช้ Wasm อยู่ เพราะมันทำงานอย่างโปร่งใสอยู่ภายในไลบรารี
ทบทวนเรื่องความเร็วและขนาด
- เบราว์เซอร์รัน Wasm ผ่านไปป์ไลน์เดียวกับ JS จึง ยังมีข้อจำกัดด้านประสิทธิภาพจากโครงสร้างของเอนจิน
- ประสิทธิภาพที่ได้แตกต่างกันตาม ระบบชนิดข้อมูลของภาษาและระดับการปรับแต่งของคอมไพเลอร์
- ต้นทุนที่ขอบเขตระหว่างโฮสต์กับโปรแกรม และ ขนาดไบนารีที่เพิ่มขึ้น ถูกชี้เป็นข้อเสีย
- มาตรฐาน WASI พยายามบรรเทาปัญหานี้ แต่ การทำมาตรฐานชนิดข้อมูลสตริงยังไม่เสร็จสมบูรณ์
- Zig สร้าง Wasm binary ที่เล็กที่สุด
- ในสภาพแวดล้อมเนทีฟ อาจเกิดประสิทธิภาพลดลงจาก threading, IO และการใช้หน่วยความจำ
แนวโน้มการพัฒนาด้านภาษาและมาตรฐาน
- การทำมาตรฐาน Wasm ดำเนินควบคู่กันโดย W3C Working Group และ Bytecode Alliance
- ฝั่งหลังเป็นผู้นำการพัฒนาเชิงเครื่องมืออย่าง WIT, Component Model
- ข้อเสนอฟีเจอร์ใหม่ถูกนำมาใช้รวดเร็ว และในบางส่วนก็มีข้อถกเถียงเรื่องความเร็วและทิศทาง
- Wasm กำลัง แพร่หลายมากขึ้นในฐานะเทคโนโลยีการผสานภายใน มากกว่าจะมาแทน JavaScript
- เฟรมเวิร์กอย่าง Blazor, Leptos ใช้ Wasm โดยไม่ต้องจัดการ JS โดยตรง
- ปัจจุบัน Wasm ถูก นำไปใช้โดยผู้สร้างไลบรารีเป็นหลัก และนักพัฒนาทั่วไปก็สามารถใช้งานได้โดยไม่จำเป็นต้องรับรู้กลไกภายใน
- สื่อการสอนที่เข้าใจยากถูกมองว่าเป็นอุปสรรคต่อการเรียนรู้ และมีการแนะนำโปรเจกต์การเรียนรู้อย่าง ‘watlings’
1 ความคิดเห็น
ความเห็นจาก Hacker News
ผมคิดว่า Wasm บรรลุเป้าหมายส่วนใหญ่ตอนที่มันถูกสร้างขึ้นมาแล้ว
โดยส่วนตัวผมใช้ Wasm เป็นองค์ประกอบหลักในโปรเจกต์หลายสิบตัว
แม้ JS engine จะเร็วมาก แต่ Wasm ก็ยังให้ระดับการควบคุม CPU ที่สูงกว่าและมีประสิทธิภาพยอดเยี่ยม
เพียงแต่มันยังไปไม่ถึงความคาดหวังว่าจะมาแทนที่ JS+HTML+CSS ได้ทั้งหมด ซึ่งผมมองว่าเหตุผลใหญ่คือการไม่มี DOM binding
ผมก็เคยใช้เฟรมเวิร์ก Wasm อย่าง Yew แต่รู้สึกเหมือนเป็นชั้นที่แปะทับบน JS แบบกระอักกระอ่วน
ยังไม่เคยลอง Blazor แต่ผมก็ยังรู้สึกว่าสะดวกกว่าถ้าเขียนด้วย JS
ถึงอย่างนั้น Wasm ก็ทำงานอยู่เงียบ ๆ ในหลายที่ และผมคิดว่านั่นแหละคือหลักฐานของความสำเร็จที่แท้จริง
ตัวอย่างเช่นฟีเจอร์ปรับความเร็วเสียงในเบราว์เซอร์ ให้ประสิทธิภาพได้ในระดับที่เป็นไปได้ก็ต่อเมื่อรันไลบรารี C++ ผ่าน Wasm
ถ้ามี DOM binding ที่ใช้งานได้จริงเมื่อไร JS จะถูกเบียดออกจากฝั่งฟรอนต์เอนด์ภายใน 10 ปี
C# ทำให้แชร์โค้ดระหว่างแบ็กเอนด์กับฟรอนต์เอนด์ได้ง่าย และRazor templateก็รองรับจาก IDE ได้ดี
แต่ต้องแบกทั้ง .NET CLR และ BCL มาด้วย ทำให้ bundle มีขนาดใหญ่
เพราะเข้าถึง DOM ได้ยาก Blazor จึงมีโครงสร้างที่วางตัวเรนเดอร์ Virtual DOM ขนาดเล็กไว้ฝั่ง JS
ประสิทธิภาพถือว่าโอเค แต่ก็ยังช้ากว่า JS ที่เขียนเองโดยตรง
Bolero ที่ใช้ F# ก็น่าสนใจ แต่โน้มน้าวทีมได้ยาก
ถ้าจะโต้ตอบกับ DOM ก็ต้องมีภาษาในระดับสูงที่เหมาะกับงานนั้น
JS ทำหน้าที่นั้นได้ดีอยู่แล้ว และชุด HTML/CSS/JS ก็กลายเป็นภาษากลางของการพัฒนา UI ไปแล้ว
แม้จะมีความพยายามทิ้งการเรนเดอร์ของเบราว์เซอร์แล้วไปทาง canvas-based แต่ก็ยังเป็นตลาดเฉพาะอยู่ดี
โลกที่แม้แต่เว็บไซต์ง่าย ๆ ก็ยังต้องดาวน์โหลดรันไทม์ขนาดหลาย MBนั้นน่ากลัวมาก
ต้นเหตุของความช้าในความเป็นจริงไม่ใช่ JS แต่คือ DOM เพราะสุดท้ายก็ต้องโต้ตอบกับ DOM อยู่ดี
ผมทำงานกับ WebAssembly มาหลายปี และกำลังจะเปิดตัวเฟรมเวิร์กที่สร้างบน Wasm ในไม่ช้า
ระบบนิเวศพัฒนาเร็วมากแล้วจู่ ๆ ก็ช้าลง พร้อมกับการนำWASIและ Component Model เข้ามาจนเกิดความสับสน
ระดับการรองรับของแต่ละ engine ต่างกันมาก จนต้องไล่ดูทั้งเอกสาร โค้ด และ issue อยู่บ่อยครั้ง
ปัญหาใหญ่สุดคือการรองรับ JS/TS ตอนนี้มันเป็นวิธีรวมระบบที่แทบจะเหมือนการแฮ็ก เลยยังไม่เสถียร
Web Containers ช่วยให้ดีขึ้น แต่ตอนนี้นักพัฒนาจำนวนมากก็ย้ายไป Bun แล้ว
ศักยภาพของ Wasm นั้นมหาศาล
ในทางทฤษฎีมันสามารถเป็น compilation target ร่วมของทุกแพลตฟอร์มได้
แต่ในโลกจริงกลับดูน่าผิดหวังอยู่บ้าง เพราะเหมือนถูกใช้แค่เพื่อทำให้บางฟีเจอร์ของ Figma เร็วขึ้น
โครงสร้างการพัฒนาที่ขับเคลื่อนโดยคณะกรรมการก็เป็นข้อจำกัดที่ทำให้เดินช้า
สมัย Native Client ยังทำแอปความเร็วระดับ native ได้ แต่ตอนนี้ Wasm กลับช้ากว่านั้น
ทั้งที่น่าจะเอาโครงสร้าง JS binding มาใช้กับ Wasm ได้ด้วย ซึ่งน่าเสียดาย
แถม Wasm ก็ไม่ได้เร็วกว่า JS ด้วย
HTML/CSS/JS พิสูจน์ประโยชน์ของตัวเองแล้ว ในขณะที่ Wasm ยังเป็น tech stack ที่คนไม่คุ้นเคย
ระบบนิเวศที่ยึด Docker เป็นศูนย์กลางกำลังฉุดไว้
เครื่องมือ build จำนวนมากในระบบนิเวศ JS เขียนด้วย Rust และบางตัวก็รันในเบราว์เซอร์ผ่าน Wasm
แม้แต่ระบบนิเวศ React หรือ npm ก็ใช้ Wasm อยู่ภายใน
ถ้า Wasm หายไป โลกของ JS frontend จะสั่นสะเทือนอย่างมาก
แต่ native Wasm UI framework ยังไม่พร้อมมากนัก
เพราะยังต้องพึ่ง DOM และ CSS และต้องเข้าถึง browser API ผ่าน JS อยู่ ทำให้ไม่มีประสิทธิภาพ
จะควบคุม DOM ด้วย Rust หรือ Kotlin ก็ได้ แต่ Rust นั้น low-level เกินไปสำหรับงานฟรอนต์เอนด์
ตอนนี้มีการcross-compile ไปมือถือมากขึ้นเรื่อย ๆ และ JetBrains Compose Multiplatform ก็เป็นตัวอย่างหนึ่ง
สิ่งที่ขวางการเติบโตของ Wasm คือtooling
การดีบักยังอยู่ในระดับ
printfและ DWARF plugin ของ Chrome ก็ไม่ได้อัปเดตมานานแล้วขั้นตอนการสร้างไฟล์ .wasm แยกตามภาษาและการตั้งค่า import/export นั้นซับซ้อน
การรองรับ GC ก็ยังไม่สมบูรณ์ ทำให้ระบบนิเวศอย่าง .NET ต้องพก GC ของตัวเองไปด้วย
WIT ดูเหมือนความพยายามแบบ COM/CORBA/gRPC อีกครั้งหนึ่ง
Emscripten ทั้งซับซ้อนและไม่เสถียร ส่วน wasi-sdk ก็ฟีเจอร์ยังไม่พอ
ทั้ง LLVM และ engine ต่าง ๆ ก็ยังปรับแต่งได้ไม่ดีพอ และ tooling ฝั่ง Wasm ของ Rust ก็แทบหยุดพัฒนาไปแล้ว
แม้แต่การimport โมดูล Wasm จาก JS แบบมาตรฐานก็ยังไม่มี
การรองรับมัลติเธรดก็ยังต้องตั้งค่า header แบบ COOP/COEP ทำให้ใช้บน GitHub Pages ไม่ได้
ถ้า tooling พ้นระดับ “เทคเดโม” ไปได้จริง มันคงถูกใช้อย่างแพร่หลายกว่านี้มาก
บริษัทของเรา Leaning Technologies ใช้ Wasm อย่างจริงจัง
ใช้ WebVM เพื่อรันไบนารี x86 ในเบราว์เซอร์,
ใช้ BrowserCraft เพื่อรันแอป Java (รวมถึง Minecraft),
และใช้ BrowserPod เพื่อรัน Node.js container ในเบราว์เซอร์
มันทรงพลังมาก แต่เป็นเครื่องมือสำหรับ power user การคอมไพล์ลอจิกฟรอนต์เอนด์ทั่วไปเป็น Wasm นั้นไม่มีประสิทธิภาพ
หลายคนมองว่าความเร็วในการพัฒนาของ CheerpJ น่าประทับใจ และถ้ามาเร็วกว่านี้ 10 ปี เว็บแพลตฟอร์มอาจเปลี่ยนไปเลย
สำหรับคนที่ไม่ชอบ JS เสน่ห์ที่แท้จริงของ Wasm คือการสร้างเว็บไซต์ที่ไม่มี JS
ผมทำงานอยู่ที่ Dioxus ซึ่งเป็นเฟรมเวิร์ก Wasm บน Rust
ปัญหาของ Wasm ฝั่งฟรอนต์เอนด์คือขาดเครื่องมือพื้นฐานอย่าง bundle splitting, hot reload, debugging symbol และการรวม asset
ในปี 2025 เราปรับปรุงส่วนนี้ไปมากแล้ว และการเชื่อมกับเครื่องมืออย่าง Vite ก็ดีขึ้น
ด้วยเครื่องมือ AI ความเร็วในการพัฒนา Rust ก็เพิ่มขึ้นด้วย และผมคาดว่าในอนาคตWasm frameworkจะได้รับความสนใจมากขึ้น
มีคนชี้ว่าขนาดไบนารีของ Wasm ใหญ่เกินไป
ในสภาพแวดล้อม DSL อาจต้องใช้เวลาดาวน์โหลดตั้งแต่หลายวินาทีถึงหลายนาที
ขณะที่ JS มีขนาดเล็กกว่าและรันได้ระหว่างดาวน์โหลดตามที่เขาอ้าง
ถ้าบิลด์ด้วย Rust ก็ลดลงมาได้ในระดับ 10~100KB
JS ไม่ได้รันระหว่างดาวน์โหลด และ Wasm ก็เริ่มทำงานได้เร็วกว่าเพราะมี streaming compile
มันเท่ากับไปทำซ้ำฟังก์ชันที่เบราว์เซอร์มีให้อยู่แล้ว
ตัวอย่างเช่น FSHistory ใช้แค่ 24KB ก็ทำ x86 emulation ได้แล้ว
เพียงแต่ระบบนิเวศ native ไม่คุ้นกับการ optimize ขนาดโค้ดมากนัก
คำพูดในบทความที่ว่า “ไม่มีเว็บไซต์ขนาดใหญ่ที่สร้างด้วย Wasm” ไม่ตรงกับประสบการณ์ของผม
เป้าหมายของโปรเจกต์ Wasm ไม่เคยเป็นการแทนที่เว็บแอปทั้งก้อน
ดูเหมือนผู้คนจะคาดหวังผิด แล้วจึงถามว่า “ทำไมมันถึงไม่เกิดขึ้น”
ผมเคยใช้ Wasm กับงานจริงหลายแบบ
โดยให้แบ็กเอนด์ตัดส่งเฉพาะส่วนที่จำเป็นก็พอ