FormaLang in, WebAssembly components out.
formawasm takes a typed
IrModule from FormaLang and emits a
Component-Model .wasm binary —
ready for wasmtime, wasmi, the browser, or any other compliant
runtime. WIT comes for free from the public surface.
The pipeline
.fv source ──► FormaLang ──► IrModule ──► formawasm ──► .wasm component ──► your runtime
From source to component to run, no Rust needed
# Install the CLI… cargo install formawasm # …write a FormaLang source file… echo 'pub fn id(x: I32) -> I32 { x }' > id.fv # …compile it… formawasm id.fv # wrote id.wasm (… bytes) from id.fv # …and run it under wasmtime. wasmtime run --invoke 'id(42)' id.wasm # 42
// id.wasm — auto-generated WIT view package formawasm:generated; world component { export id: func(x: s32) -> s32; }
Or wire the backend into your build
// Cargo.toml [dependencies] formawasm = "0.0.1-beta" // main.rs use formalang::{Pipeline, compile_to_ir}; use formawasm::WasmBackend; let module = compile_to_ir(source)?; let bytes = Pipeline::new() .emit(module, &WasmBackend::new())?; // bytes is a Vec<u8> ready for wasmtime, wasmi, jco, …
Why formawasm
Component Model native
Output is a Component-Model artifact from day one — never a bare core wasm module. Standards-compliant, runs in every compliant runtime, future-proof against the evolution of the platform.
WIT for free
The typed boundary is auto-generated from the public
surface of each module. No hand-written
.wit files, no manual
interface bookkeeping. Mark a function
pub; it becomes an export.
Runtime-agnostic
The backend stops at bytes. Pick wasmtime for the server, jco for the browser, wasmi for embedded — the same artifact runs unchanged. formawasm has no opinion on where you ship.
What's in the box
The full FormaLang surface
Structs, enums, traits, methods, generics (after monomorphisation), closures (after closure-conversion), virtual dispatch, host-provided externs. Strings, optionals, dictionaries, arrays, ranges — every container has a memory layout and a WIT mapping.
Optional optimization passes
Cargo features for binaryen
(wasm-opt at
-Os), DWARF debug
sections, and a wasmparser
defensive validation pass. All off by default; pay
only for what you turn on.
Strict quality bar
Strict-clippy, typed errors via
thiserror, no
unwrap /
panic in production
paths. Tests return Result;
every milestone runs end-to-end under wasmtime in CI.
Drop-in CLI
formawasm ships
as a tiny single-file source-to-component driver —
useful for smoke tests, quick experimentation, or as
a build-pipeline step where wiring the Rust API isn't
worth it.