Acesse o painel da sua conta

Não tem uma conta? Registrar

Entrar em contato

Visite também nosso site craftxp.com.br

  • img
  • img
  • img
  • img
  • img
  • img

Entre em contato

WebAssembly (Wasm): Executando Código de Alta Performance no Navegador

WebAssembly (Wasm): Executando Código de Alta Performance no Navegador

O que é WebAssembly?

O WebAssembly (abreviado como Wasm) é um formato de instrução binária de baixo nível, projetado para ser executado em navegadores modernos com desempenho próximo ao nativo. Diferente do JavaScript, que é interpretado e otimizado em tempo real (JIT), o Wasm é compilado antecipadamente em um formato binário compacto que a máquina entende quase diretamente.

Lançado oficialmente em 2017 e tornado padrão W3C em 2019, o WebAssembly é suportado por todos os principais navegadores (Chrome, Firefox, Safari, Edge) e está expandindo seu alcance para além do navegador com iniciativas como WASI (WebAssembly System Interface).

Por que usar WebAssembly?

Existem cenários específicos onde o Wasm brilha:

  • Processamento intensivo: edição de imagens, vídeo e áudio diretamente no navegador.
  • Jogos: engines como Unity e Unreal compilam para Wasm, permitindo jogos AAA no browser.
  • Criptografia e compressão: algoritmos críticos rodam de 3x a 10x mais rápido que JavaScript puro.
  • Aplicações científicas: simulações numéricas, renderização 3D e machine learning no lado cliente.
  • Portabilidade: reutilize código legado em C/C++/Rust no navegador sem reescrever.

Compilando C/C++ com Emscripten

O Emscripten é o compilador mais maduro para gerar Wasm a partir de código C e C++. Ele converte bytecode LLVM em módulos Wasm:

# Instalar Emscripten
git clone https://github.com/emscripten-core/emsdk.git
cd emsdk
./emsdk install latest
./emsdk activate latest
source ./emsdk_env.sh

# Compilar código C para Wasm
emcc hello.c -o hello.html -s WASM=1

Exemplo de um programa simples em C que soma dois números:

#include <stdio.h>

int main() {
    int a = 10, b = 20;
    printf("Soma: %d\n", a + b);
    return 0;
}

Ao compilar com emcc soma.c -o soma.html, você obtém três arquivos: soma.html, soma.js (glue code) e soma.wasm (bytecode binário).

WebAssembly com Rust

Rust tem suporte de primeira linha para Wasm. A ferramenta wasm-pack simplifica todo o fluxo:

# Instalar wasm-pack
curl https://rustwasm.github.io/wasm-pack/installer/init.sh -sSf | sh

# Criar um projeto
cargo new --lib meu-app-wasm
cd meu-app-wasm

No Cargo.toml, adicione:

[lib]
crate-type = ["cdylib"]

[dependencies]
wasm-bindgen = "0.2"

E em src/lib.rs:

use wasm_bindgen::prelude::*;

#[wasm_bindgen]
pub fn fibonacci(n: u32) -> u32 {
    match n {
        0 => 0,
        1 => 1,
        _ => fibonacci(n - 1) + fibonacci(n - 2),
    }
}

Compile com wasm-pack build --target web e importe no JavaScript:

import init, { fibonacci } from "./pkg/meu_app_wasm.js";
await init();
console.log(fibonacci(40));

WebAssembly com Go

Go também compila nativamente para Wasm desde a versão 1.11:

// main.go
package main

import "syscall/js"

func soma(this js.Value, args []js.Value) interface{} {
    return args[0].Int() + args[1].Int()
}

func main() {
    js.Global().Set("soma", js.FuncOf(soma))
    select {} // mantém o programa rodando
}

Compile com:

GOOS=js GOARCH=wasm go build -o main.wasm main.go

E carregue no HTML copiando wasm_exec.js do diretório de instalação do Go:

cp "$(go env GOROOT)/misc/wasm/wasm_exec.js" .

# No HTML:
<script src="wasm_exec.js"></script>
<script>
  const go = new Go();
  WebAssembly.instantiateStreaming(fetch("main.wasm"), go.importObject)
    .then(result => go.run(result.instance));
</script>

Wasm no Node.js

WebAssembly não se limita ao navegador. No Node.js, você pode carregar módulos Wasm nativamente:

const fs = require('fs');
const wasmBuffer = fs.readFileSync('./module.wasm');

WebAssembly.instantiate(wasmBuffer, {
  env: {
    print: (result) => console.log("Resultado:", result),
  },
}).then(({ instance }) => {
  instance.exports.run();
});

WASI: WebAssembly Fora do Navegador

A WASI (WebAssembly System Interface) permite executar módulos Wasm em ambientes fora do navegador, como servidores, edge computing e dispositivos IoT. Ferramentas como wasmtime e wasmer implementam essa especificação:

# Executar um módulo Wasm com Wasmtime
wasmtime run meu-modulo.wasm

# Com Wasmer
wasmer run meu-modulo.wasm

Isso abre portas para usar Wasm em funções serverless, plugins de aplicações e microserviços leves.

Dicas e Boas Práticas

  • Use Wasm apenas para o gargalo: não substitua todo o JavaScript por Wasm. Identifique funções críticas de performance.
  • Mantenha os módulos pequenos: módulos Wasm muito grandes aumentam o tempo de download e compilação.
  • Streaming compilation: use WebAssembly.instantiateStreaming() em vez de instantiate() para compilar enquanto o download ocorre.
  • Comunicação eficiente: minimize a troca de dados entre JS e Wasm. Prefira buffers de memória linear compartilhados.
  • Teste em múltiplos navegadores: embora o suporte seja amplo, o desempenho pode variar entre engines.

O WebAssembly não veio para substituir o JavaScript, mas para complementá-lo, permitindo que aplicações web executem tarefas que antes eram inviáveis no navegador. Com suporte crescente em Rust, Go, C, C++ e outras linguagens, o Wasm está rapidamente se tornando uma ferramenta essencial no arsenal de qualquer desenvolvedor web moderno.

Craft XP
Craft XP