
【2026年7月版】
WASMランタイムとフレームワークの地図(2026年) ― 「生API」を実装するのは誰か
公開日: 2026/07/24
読了時間: 約 22分
前回の記事では、WASM・WebGL・WebGPUが「置き換え」ではなく役割分担へ収束していることを整理しました(第1回)。本稿はその続編として、一段下のレイヤー――WASMの「生API」を実際に実装・抽象化しているランタイム、ツール、フレームワーク群を地図として描きます。2026年7月時点の整理です。
WASM周辺は一枚岩ではない
Wasmerを始めとするWASM周辺実装は、単一の「WASMフレームワーク」ではありません。実際には、次の層に分かれています。
アプリケーション / プラグイン / サーバーレス
│
▼
上位フレームワーク Spin / wasmCloud / Extism / Wasmer Edge
│
▼
Component Model・WASI・言語バインディング WIT / wit-bindgen / cargo-component / jco / wasm-tools
│
▼
WASMランタイム / 埋め込みAPI Wasmtime / Wasmer / WasmEdge / wazero / WAMR
│
▼
実行エンジン Cranelift / LLVM / Singlepass / Interpreter / AOT
│
▼
WebAssembly Core Specificationブラウザ側は、これとは別系列です。
Rust / C++ / C / Go など
│
wasm-bindgen / Emscripten / TinyGo
│
WebAssembly JavaScript API
│
V8 / SpiderMonkey / JavaScriptCore
│
WASM Coreしたがって技術選定では、まず「自分が何をしたいのか」を切り分ける必要があります。WASMバイナリを実行したいのか、ホストアプリへ実行機能を埋め込みたいのか、WASIを実装したいのか、Component Modelを使いたいのか、ブラウザAPIをWASMから呼びたいのか、プラグイン基盤を作りたいのか、サーバーレス/エッジ基盤を作りたいのか――ここが出発点になります。
「生API」とは何を指すか
WASM周辺には、少なくとも4種類の「生API」があります。混同すると選定を誤ります。
- WASM Core API ― モジュールをロード・検証・コンパイル・インスタンス化し、関数やメモリを操作するAPI。
Engine・Store・Module・Instance・Memory・Table・Global・Function・Linkerといった概念で構成されます。 - WASI API ― ファイル、標準入出力、環境変数、時計、乱数、ソケットなど、WASMの外部機能をホストが提供するAPI。単一APIではなく、標準化中のインターフェース群です。
- Component Model API ― モジュール間で、整数やポインタではなく文字列・リスト・レコード・列挙・リソースを受け渡す仕組み。WITで定義し、Canonical ABIで各言語の型へ変換します。
- Web APIバインディング ― ブラウザではWASMから直接DOMやWebGPUを呼べません。JavaScript APIとの橋渡し層(
wasm-bindgen/web-sys、Emscripten、TinyGoのsyscall/jsなど)が必要です。
ブラウザでのCore APIは、JavaScript APIとして次の形で公開されます。
const module = await WebAssembly.compile(bytes);
const instance = await WebAssembly.instantiate(module, imports);
const result = instance.exports.add(1, 2);ブラウザ外ランタイムは、これに相当する埋め込みAPIをRust・C・C++・Go・Pythonなどへ公開します。
主要WASMランタイム
Wasmtime ― 標準追従の中心
WasmtimeはBytecode Allianceが開発する、標準追従を重視したランタイムです。Core WASMとComponent ModelのJIT・AOT実行に対応し、CLIだけでなくRustライブラリとしてホストへ埋め込めます。実行エンジンはCraneliftとWinch、そしてWASI Preview 1/2とComponent Modelを備えます。
let engine = wasmtime::Engine::default();
let module = wasmtime::Module::from_file(&engine, "plugin.wasm")?;
let mut store = wasmtime::Store::new(&engine, ());
let instance = wasmtime::Instance::new(&mut store, &module, &[])?;強みは、標準への追従の速さ、Component Model対応の先行、WASI Preview 2との統合、Rustホストとの親和性、そしてCPU時間・メモリ・インスタンス数を制限しやすいことです。RustアプリへのWASM埋め込み、標準準拠のプラグイン基盤、サーバーレス実行基盤に向きます。POSIXアプリをそのまま大量に動かすより、WASIとComponent Modelへ合わせてアプリを構造化する方向が強い点は押さえておきます。
Wasmer ― ランタイムからホスティングまでの統合エコシステム
Wasmerは、ランタイム単体にとどまらず、パッケージ管理・ブラウザSDK・クラウド/エッジ実行までを含む統合エコシステムです。実行バックエンドはCranelift・LLVM・Singlepass・インタプリタ系を選べます。
最大の特徴が、独自拡張の WASIX です。標準WASIの不足を補い、スレッド・ソケット・プロセス・シグナル・端末といった、よりPOSIXに近い機能を提供します。実用性は高い一方、標準WASIランタイム間の完全な互換からは外れます。
WASI ─ 最小・Capability指向の標準API
WASIX ─ threads / processes / sockets / signals / terminal(よりPOSIX的)ブラウザ上でWASI/WASIXアプリを動かすJS SDKもあり、公式例ではブラウザ内でBashやUnixユーティリティをxterm.jsへ接続します。パッケージ生成のWasmer PackやWAIも展開していますが、標準エコシステムの中心はWITとComponent Modelであり、WAIはWasmer独自系として互換性・移行経路を個別に確認すべきです。標準WASI互換を最優先ならWasmtimeが分かりやすく、実用的なUnix互換機能を優先するならWasmer/WASIXが有力、という違いになります。
WasmEdge ― クラウドネイティブとエッジAI
WasmEdgeはCNCF Sandboxプロジェクトで、クラウドネイティブ、エッジ、AI推論、サーバーサイドWASMを重点領域とします。C/C++/Rust/Python/Node.jsのSDKを持ち、ランタイム機能をプラグインとして追加する設計が強いのが特徴です。公式プラグインにはWASI-CryptoやWASI-NNがあります。
WASM guest
├─ wasi-nn / wasi-crypto / sockets / custom host API
▼
WasmEdge plug-in
▼
TensorFlow / PyTorch / OpenVINO / host libraryAI推論はWASI-NNを通じてホスト側の推論ランタイムへ接続する方式で、ネットワーク全体をWASMへコンパイルするのではなく、WASMからホストの推論エンジンを呼びます。DockerのWASM実行系でも使われ、OCIイメージとしてWASMバイナリを配布できます。エッジAI、WASI-NN、OCI/Docker統合、Nginx/Proxy-Wasm連携に向きます。Component Modelは方針を示していますが、Wasmtimeほど一貫して中心機能とは限らないため、必要なWIT機能・WASI Preview 2・async・resource型の対応は個別確認が要ります。
wazero ― CGO不要の純Goランタイム
wazeroはGoだけで実装された、ネイティブ依存のないランタイムです。CGO不要・Cライブラリ不要で、Goバイナリへ静的に組み込みやすく、クロスコンパイルも容易。Goのcontextで実行中断や制御を組み込めます。
runtime := wazero.NewRuntime(ctx)
defer runtime.Close(ctx)
module, err := runtime.Instantiate(ctx, wasmBytes)
if err != nil {
return err
}
result, err := module.ExportedFunction("add").Call(ctx, 1, 2)Go製サーバーのプラグイン機能、CLI、ゲートウェイ/プロキシ/制御プレーン、CGO禁止環境、単一バイナリ配布に強みがあります。Component Modelの最先端機能を最優先するならWasmtimeが先行しますが、Core WASMとWASIをGoへ安全・簡潔に埋め込む用途では第一候補です。
WAMR / wasm3 ― 組み込み・極小環境
WAMR(WebAssembly Micro Runtime) はBytecode Allianceの、組み込み・IoT・TEE・エッジ向け軽量ランタイムです。classic/fast interpreter、AOT、JITを選べ、公式資料では構成によりインタプリタ部が約85KB、AOT部が約50KB程度とされています。マイクロコントローラー、IoTゲートウェイ、組み込みLinux、TEE、ファームウェア拡張に向きます。
wasm3 はさらに小さいインタプリタ型ランタイムで、JITを持たず低メモリ環境で動きます。極小・単純ならwasm3、組み込みだが複数の実行方式が必要ならWAMR、という住み分けです。ただしwasm3は更新頻度や最新Proposal・WASI・Component Model対応の面で慎重に選ぶべきです。
Chicory / GraalWasm ― JVM上のWASM
Chicory は100% Javaで実装されたJVMネイティブランタイムで、JNIやネイティブライブラリなしにWASMを実行できます。Maven/Gradleへ統合しやすく、Java業務システムやJVMサーバーのプラグイン機構に向きます。高性能JITやComponent Model最先端よりも、純Java・配布容易性・安全な埋め込みが価値の中心です。
GraalWasm はGraalVM上のWASM実装で、Polyglot APIを通じてJava/Kotlin等からWASMを実行します。既にGraalVMを使っている、あるいはPolyglot構成を組む場合に向きます。
ブラウザ内WASM実装
ブラウザでは、WasmtimeやWasmerを実行エンジンとして使うわけではありません。WASM Coreを直接実装しているのは、ブラウザ内のJavaScriptエンジンです。
Chrome / Edge → V8
Firefox → SpiderMonkey
Safari → JavaScriptCoreアプリから見えるのは共通のWebAssembly JavaScript APIで、その下でJIT/baseline/optimizingコンパイラが動きます。ただし、これらはWASM Core Specは実装しますが、WASIはブラウザ標準APIではありません。ブラウザでWASIを使うには、Wasmer JS SDK、WASI shim、Node互換レイヤ、仮想ファイルシステム、Workerベースのランタイム、JSで実装したhost importsといったポリフィルや仮想環境が必要になります。
バイナリを生成・変換する基盤ツール
- WABT(WebAssembly Binary Toolkit) ―
wat2wasm・wasm2wat・wasm-validate・wasm-objdump・wasm-stripなど、Core WASMを直接扱う最低レベルの工具群。仕様検証、デバッグ、バイナリ解析に使います。 - Binaryen ―
wasm-optを中心とする最適化・変換基盤。dead code elimination、inlining、constant folding、サイズ最適化、feature loweringなどを担い、Emscriptenなど多くのツールチェーン内部で使われます。 - wasm-tools ― Bytecode AllianceのRust製ツール群で、Core WASMとComponent Modelの両方を扱います。
component new/component wit/validateなどComponent Model関連が重要で、WABTがCore WASMの基礎工具なら、wasm-toolsはComponent Model時代の基礎工具という位置づけです。
wasm-tools component new module.wasm -o component.wasm
wasm-tools component wit component.wasm
wasm-tools validate component.wasmComponent Model周辺の実装
WIT ― コンポーネントのインターフェース定義言語
WITは、線形メモリの位置やポインタを公開せず、型付きインターフェースを定義します。
package asopi:storage;
interface blob-store {
resource blob {
size: func() -> u64;
read: func(offset: u64, length: u64) -> list<u8>;
}
open: func(name: string) -> result<blob, string>;
}Core WASM ABI : pointer + length + integer
Component Model : string + list + record + resource + result生成・変換ツール
- wit-bindgen ― WIT定義からGuest/Host向けコードを生成します(Rust・C・C++・Go・Java・C#・JavaScript・Pythonなど)。これは実行エンジンではなく、呼び出しコードの生成器である点が重要です。Wasmtimeが「実行する」のに対し、wit-bindgenは「呼び出しコードを生成する」役割です。
- cargo-component ― RustプロジェクトをComponent Model向けに構築するCargoサブコマンド。WIT依存の管理、バインディング生成、Core WASMからComponentへの変換、metadata付与、WASI Preview 2向けビルドを担う、RustでComponent Modelを使う際の実質標準ツールです。
- jco ― JavaScript向けのComponent Modelツールチェーン。ブラウザ/Node.jsにはComponentをネイティブ実行する共通APIがまだないため、
jco transpileがComponentをCore WASMとESモジュール(JS glue)へ変換します。WIT型からTypeScript定義も生成できます。 - componentize-py ― PythonコードをWASM Componentへ変換します。Pythonインタプリタを含むためサイズは大きくなりますが、WITインターフェースをPython関数として実装できます。
言語別バインディング
Rust ― wasm-bindgen / web-sys / js-sys
wasm-bindgen はRustとJavaScript間の高水準バインディング生成ツールで、ビルドするとWASM本体・JS glue・TypeScript宣言を生成します。web-sys はWebIDLから生成されたWeb APIバインディングで、DOM・WebGL・WebGPU・Fetch・Workersなどへアクセスできます。js-sys はArrayやPromiseなどJS組み込み型への低レベルバインディング。wasm-pack はビルド・テスト・npm公開をまとめるワークフローツールです(旧Working Groupサイトはメンテナンス終了が明示されており、各ツールの最新状況はリポジトリで確認すべきです)。
#[wasm_bindgen]
pub fn greet(name: &str) -> String {
format!("Hello, {name}")
}C/C++ ― Emscripten
EmscriptenはLLVMベースのC/C++向けツールチェーンで、単なるコンパイラではなく「Web向けのOS互換・ランタイム層」です。emscripten.h/html5.h、WebGL/WebGPU API、Fetch、WebSocket、Wasm Workers、pthreads、Audio Worklets、File System API、Embindなどを提供します。html5.h の低レベル関数は、対応するWeb APIを直接呼ぶ薄いバインディングです。
補助実装として、仮想ファイルシステムをWASM側へ移した WasmFS(マルチスレッド性能改善が目的)や、Web WorkersとSharedArrayBufferをC/C++から使う Wasm Workers があります。
Go ― TinyGo
TinyGoはGoコードを小さなWASMへコンパイルする主要手段で、ターゲットはwasm(ブラウザ+JS API)とwasi/wasip1(WASIランタイム)の2系統。標準GoでもWASMは生成できますが、ランタイムサイズや起動負荷ではTinyGoが有利な場合があります(反面、Go互換性・reflection・GC挙動には違いがあります)。
上位フレームワーク
- Extism ― WASMをアプリのプラグイン形式として使うフレームワーク。複数ホスト言語SDKとGuest言語PDK、マニフェスト、メモリ受け渡し、Host Function、サンドボックス制御を提供します。Wasmtimeなどの上にプラグイン用の共通モデルを構築するもので、生のWasmtime APIを自分で管理する代わりに
Plugin.call("transform", input)のように呼べます。ホスト言語を将来変更しうる場合に有効です。 - Spin ― Fermyonの、WASM Componentを使うサーバーサイド/サーバーレスFW。HTTP/Redis/Queueイベントをトリガに、outbound HTTP・key-value・databaseなどのホストインターフェースを提供します。高速コールドスタートと言語非依存が特徴で、「任意のWASMを実行するランタイム」ではなくWebアプリ向けの上位FWです。
- wasmCloud ― WASM Componentを分散アプリの構成単位として扱うFW。ビジネスロジック(Component)とインフラ機能(Capability Provider: S3/NATS/PostgreSQL/HTTP等)を分離します。Kubernetesコンテナの代替というより、分散コンポーネントとCapabilityの実行・接続基盤です。
- Proxy-Wasm ― Envoy/NGINX/サービスメッシュ拡張用のABI。リクエスト変換、認証、レート制限、ロギング、テレメトリ、セキュリティポリシーに使われます。Component Modelとは別系列の、特定ドメイン向けホストABIです。
GPUの生API実装 ― Dawn と wgpu
WASMからGPUを扱う場合、WebGPU側にも「仕様実装」と「ラッパー」があります。
Dawn はChromiumで使われるWebGPU実装で、webgpu.h を実装しWebGPU IDLにほぼ1対1対応するC APIを提供します。Native WebGPU、Cヘッダー、C++ラッパー、client-server wire protocol(Dawn Wire)、WGSLコンパイラTint、validation layerを含みます。ChromiumはGPU処理をブラウザプロセスから分離するため、Dawn Wireでクライアント・サーバー構成を取ります。C/C++でWebGPU生APIを使う、Chromium互換実装が必要、独自ブラウザ/レンダラーを作る、といった用途に向きます。
wgpu はRust製のWebGPU実装・抽象化ライブラリで、Dawnが仕様に近いC API実装なのに対し、Rustの型システムと所有権に合わせた安全なAPIを提供します。構成はwgpu-core(検証・状態管理)、wgpu-hal(Vulkan/Metal/D3D12等への低水準アクセス)、naga(シェーダー変換・検証)、wgpu-types。同じRustコードが、wasm32ターゲットではブラウザのnavigator.gpuを呼び、ネイティブビルドではVulkan/Metal/D3D12を呼びます。
同じRustコード
├─ wasm32 → navigator.gpu
└─ native → Vulkan / Metal / D3D12シェーダーコンパイラの Tint(WGSL→HLSL/MSL/SPIR-V)と Naga(WGSL/SPIR-V/GLSL↔各種)は、アプリFWではなく、WebGPU実装内部やシェーダーツールチェーンで使う基礎部品です。
WebGLの生APIは、Emscriptenが OpenGL ES系をWebGLへ変換する経路(SDL/GLFW/OpenGL ESコードを比較的少ない変更で移植)と、Rustのweb-sysがWebGl2RenderingContextなどの薄い生バインディングを提供する経路があります。後者の上位にはglow・three-d・rend3・Bevy renderer・wgpuなどが載ります。なお、デスクトップOpenGLとWebGLは同一ではなく、Immediate Modeなし、Geometry/Compute Shaderなし、一部Texture Format非対応、同期API制約といった差があります。
ランタイム比較
| 実装 | 主言語 | 実行方式 | WASI | Component Model | 主用途 |
|---|---|---|---|---|---|
| Wasmtime | Rust | JIT / AOT | 強い | 最も先行 | 標準準拠、サーバー、組み込み |
| Wasmer | Rust | JIT / AOT / 複数Backend | WASI + WASIX | 独自系も含む | 汎用、ブラウザ、Edge |
| WasmEdge | C++ | Interpreter / AOT | 強い | 進行中 | Edge、AI、OCI |
| wazero | Go | Compiler / Interpreter | 対応 | 限定的 | Go埋め込み |
| WAMR | C | Interpreter / JIT / AOT | 対応 | 限定的 | 組み込み、IoT |
| wasm3 | C | Interpreter | 基本対応 | 弱い | 極小環境 |
| Chicory | Java | Interpreter / JVM内実行 | 対応拡大中 | 発展中 | 純Java埋め込み |
| GraalWasm | Java / Graal | Interpreter / JIT | 要確認 | 限定的 | GraalVM統合 |
| V8 | C++ | JIT | なし | Core中心 | Chrome、Node |
| SpiderMonkey | C++ / Rust | JIT | なし | Core中心 | Firefox |
| JavaScriptCore | C++ | JIT | なし | Core中心 | Safari |
層別に「何を隠蔽するか」で並べると、次のようになります。
| 層 | 実装 | 何を隠蔽するか |
|---|---|---|
| Coreランタイム | Wasmtime / Wasmer / WasmEdge | バイナリ検証、JIT、Memory、Instance |
| 埋め込みSDK | wazero / Chicory / Wasmtime API | ホスト言語との統合 |
| WASI実装 | wasmtime-wasi / WASIX / WasmEdge WASI | ファイル、時計、乱数、ネットワーク |
| Component Tooling | WIT / wit-bindgen / cargo-component / jco | Canonical ABI、型変換 |
| ブラウザバインディング | wasm-bindgen / web-sys / Emscripten | JS/Web API境界 |
| プラグイン基盤 | Extism | ABI、設定、Host Function |
| サーバーレス | Spin | HTTP、イベント、デプロイ |
| 分散実行 | wasmCloud | Capability、Provider、配置 |
| Proxy拡張 | Proxy-Wasm | HTTPプロキシABI |
| GPU実装 | Dawn / wgpu | D3D12、Metal、Vulkan差 |
| Shader変換 | Tint / Naga | WGSL、HLSL、MSL、SPIR-V差 |
実際の選び方
- 標準WASI/Component Modelを中心にする → Wasmtime + WASI Preview 2 + WIT + wit-bindgen + cargo-component + wasm-tools。最も仕様に近く、独自ABI依存を抑えられます。
- POSIX的な既存アプリを動かす → Wasmer + WASIX + Wasmer JS SDK/Runtime。ただしWASIX依存部分は他ランタイムへの移植コストになります。
- Goアプリへプラグインを追加する → wazero + 独自Host Functions。複数言語対応まで要るならExtism。
- Javaアプリへ組み込む → ネイティブ依存を避けるならChicory、GraalVM基盤ならGraalWasm。
- 組み込み/IoT → WAMR。より小さく単純なインタプリタでよければwasm3。
- ブラウザでRustとWeb APIを接続 → wasm-bindgen + web-sys + js-sys。
- C/C++アプリをWebへ移植 → Emscripten + WasmFS + Wasm Workers + WebGL/WebGPUバインディング。
- ブラウザとネイティブでGPUコードを共有 → Rust + wgpu + Naga。C/C++でWebGPU仕様へ直接近づけるならDawn + webgpu.h + Tint。
まとめ ― 生APIはアダプター層に閉じ込める
WASMエコシステムには、大きく3つの流れがあります。
- 標準コンポーネント路線 ― Wasmtime / WASI Preview 2 / Component Model / WIT / wit-bindgen / cargo-component。WASMを「単体バイナリ」から「型付きソフトウェアコンポーネント」へ進化させる流れ。
- 実用OS互換路線 ― Wasmer / WASIX / Wasmer JS SDK / Wasmer Edge。既存Unixアプリを早くWASM化し、ブラウザやEdgeで動かす流れ。
- ドメイン特化路線 ― WasmEdge(Edge/AI)、wazero(Go)、WAMR(組み込み)、Chicory(JVM)、Spin(サーバーレス)、wasmCloud(分散)、Extism(プラグイン)、Proxy-Wasm(ネットワーク)。
最も長期的な互換性を重視するなら、Core WASM・WASI Preview 2・Component Model・WITを中心に据え、ランタイム固有機能はアダプター層へ閉じ込めるのが妥当です。WasmerのWASIXやWasmEdgeの独自プラグインは有用ですが、アプリ本体が直接依存すると、ランタイムを交換できなくなります。
Application domain
│ WIT interface
▼
Runtime adapter
├─ Wasmtime adapter
├─ Wasmer adapter
├─ WasmEdge adapter
└─ Browser adapter
▼
Runtime-specific APIつまり、生APIを直接使うのはアダプター層までに留め、アプリ本体はWIT(または独自の型付きインターフェース)で分離する。これが、現在のWASM周辺実装を安全に使うための基本設計です。次回(第3回)は、こうしたランタイム/ツールの上で動く「WASM系言語」――MoonBitを中心に――を整理します。