DEV Community

Cover image for Webassembly: Near-Native Performance for Web Applications
Gautam Vaja for CodeParrot

Posted on • Originally published at 10xdev.codeparrot.ai

Webassembly: Near-Native Performance for Web Applications

I was working on a web development project, building a 3D visualizer. This project required a lot of calculations and data processing. I used JavaScript, my go-to language for web development. At first, everything went well. But as I added more features, the website started to slow down. The rendering times increased, and the animations became choppy. It was clear that JavaScript alone wasn't enough for this project. It was slow because JavaScript is an interpreted language and runs on a single thread, meaning it can only do one thing at a time. These performance issues were a big problem, and I needed a solution.

Then, I discovered WebAssembly (Wasm). WebAssembly allows code written in other languages like C, C++, and Rust to run on the web at near-native speed. This means it can run much faster than JavaScript, especially for heavy computations. I decided to give it a try.

Why WebAssembly?

Key Features of WebAssembly

  1. Performance: WebAssembly is designed to be fast. It executes at near-native speed by taking advantage of common hardware capabilities. This makes it perfect for tasks that need a lot of computing power, such as 3D graphics, video editing, and scientific simulations.

  2. Portability: Code written in WebAssembly can run on any web platform, providing consistent performance across different browsers and devices. This means you can write your code once and run it anywhere without worrying about compatibility issues.

  3. Interoperability: WebAssembly works alongside JavaScript. You can call JavaScript functions from WebAssembly and vice versa. This allows you to use WebAssembly for performance-critical parts of your application while still leveraging JavaScript for other tasks.

  4. Security: WebAssembly is designed with a strong focus on security. It runs in a sandboxed environment, ensuring that it doesn’t have unrestricted access to the host system. This makes it safer to run potentially untrusted code in the browser.

When to Use WebAssembly

WebAssembly is not just limited to 3D visualizers; its potential applications are vast and varied.

Game Development

Web-based games often require complex graphics and physics calculations, which can be performance-heavy. By using WebAssembly, you can offload these intensive tasks from JavaScript, resulting in smoother gameplay and more responsive interactions. WebAssembly's near-native execution speed is ideal for creating high-performance games that run efficiently in the browser.

Video and Audio Editing

Real-time video and audio editing tools need to process large amounts of data quickly. JavaScript might struggle with these tasks, leading to delays and a poor user experience. WebAssembly can handle these intensive computations more effectively, enabling the creation of powerful web-based editing tools that rival desktop applications in performance.

Scientific Simulations

Scientific applications often involve simulations and data analysis that require significant computational power. WebAssembly can execute these tasks with the efficiency of native code, making it possible to run complex scientific models directly in the browser. This is especially useful for educational tools and research applications that need to provide real-time results.

Large-scale Data Visualization

When visualizing large datasets, performance is crucial. JavaScript alone may not be sufficient for rendering complex visualizations smoothly. WebAssembly can manage the heavy lifting, allowing for fast and interactive data exploration. This is particularly beneficial for applications in finance, healthcare, and other fields where data-driven insights are essential.

Getting Started with WebAssembly

To give you a taste of WebAssembly, let's walk through a simple example. We'll write a function in C, compile it to WebAssembly, and call it from JavaScript.

Step 1: Write the C Code

I started with a simple example. I wrote a basic function in C that adds two numbers together. Here’s what my hello.c file looked like:

#include <stdio.h>

int add(int a, int b) {
    return a + b;
}
Enter fullscreen mode Exit fullscreen mode

Step 2: Compile to WebAssembly

Next, I needed to convert this C code to WebAssembly. I used a tool called Emscripten, which compiles C and C++ code to WebAssembly. I followed the instructions on their website to install Emscripten. Then, I compiled my C code with this command:

emcc hello.c -s WASM=1 -o hello.js
Enter fullscreen mode Exit fullscreen mode

This command created two files: hello.wasm (the WebAssembly binary) and hello.js (JavaScript glue code).

Step 3: Integrate WebAssembly with JavaScript

I then created an index.html file to see my WebAssembly code in action:

<!DOCTYPE html>
<html lang="en">
  <head>
    <meta charset="UTF-8" />
    <meta name="viewport" content="width=device-width, initial-scale=1.0" />
    <title>WebAssembly Example</title>
  </head>
  <body>
    <h1>WebAssembly Example</h1>
    <script src="hello.js"></script>
    <script>
      Module.onRuntimeInitialized = () => {
        const result = Module._add(5, 7);
        console.log(`The result is: ${result}`);
      };
    </script>
  </body>
</html>
Enter fullscreen mode Exit fullscreen mode

In this HTML file, I included the JavaScript glue code (hello.js). Once the WebAssembly runtime was ready, I called the add function from my C code using Module._add.

Step 4: Run the Example

To see it working, I used a simple HTTP server. Running this command in my project directory worked perfectly:

python3 -m http.server
Enter fullscreen mode Exit fullscreen mode

I opened my browser and went to http://localhost:8000. In the console (F12 or right-click > Inspect > Console), I saw the output: "The result is: 12". It worked! I had successfully used WebAssembly to enhance my web application.

Real-World Benefits

Using WebAssembly, I was able to offload the heavy calculations from JavaScript, making my 3D visualizer run much faster and smoother. This experience showed me the potential of WebAssembly. It's not just a tool to speed up web applications; it's a game-changer.

For example, think about a web-based video editor. Video processing requires a lot of computation, and JavaScript alone might struggle to keep up. By using WebAssembly, you can perform these heavy tasks more efficiently, providing a better user experience. Similarly, in scientific computing, where large datasets are processed in real-time, WebAssembly can handle the workload much more effectively than JavaScript.

If you’re facing performance issues in your web projects, I highly recommend trying WebAssembly. It’s a powerful tool that can unlock new potentials for your applications.

Further Reading

Give WebAssembly a try, and see how it can improve your web development projects.

Top comments (9)

Collapse
 
miketalbot profile image
Mike Talbot ⭐ • Edited

I have a huge amount of time for engines like V8 optimising JS, so I'm not convinced about the significant speed increases of using WASM. I'm totally sold on moving existing code in a different language to WASM, but are there really massive performance benefits for rewriting JS?

In practice it seems like small speed ups are possible, but I don't think this should be the primary reason for using it.

I found this interesting: zaplib.com/docs/blog_post_mortem.h...

Collapse
 
efpage profile image
Eckehard

Are there any experiences how other languages like Go or Pascal perform compiled to WebAssembly? Are there any compatibility issues running different browsers?

Collapse
 
mvaja13 profile image
Gautam Vaja

currently Chrome and Firefox supports WASM, and C++ and Rust are most preffered.

Collapse
 
efpage profile image
Eckehard

Luckily it sems you are not right.

Referring to CanIuse most browsers seem to support WASM since 2017, source is a bit unclear on Android versions.

Thread Thread
 
mvaja13 profile image
Gautam Vaja

Thanks for pointing out.

Thread Thread
 
efpage profile image
Eckehard

I found a far better overview here. Following to this source, WASM is supported (more or less) by all modern browsers

WASM

There are still some conceptual limitations that may prevent people from using WASM more widely.

Collapse
 
bwca profile image
Volodymyr Yepishev

It's all fine and dandy until you actually try communicating with the wasm module from js and pass complex data structures or even mere strings. No fun there 👀

Collapse
 
m4rcxs profile image
Marcos Silva

wow! Awesome!

Collapse
 
keyurparalkar profile image
Keyur Paralkar

Article is insightful but I would suggest to add more points or examples from performance standpoint.

Some comments may only be visible to logged-in visitors. Sign in to view all comments. Some comments have been hidden by the post's author - find out more