なんかwasmを直読み出来るんだけど
Webpackがwasmの読み込みをサポートしているので、Next.jsでもちょっと設定を追加するだけで動作が確認出来ました
TypeScriptの定義まで自動で行われるので、連携する上で迷うところがありません
今回作成したコード
https://github.com/SoraKumo001/next-wasm
RustでWebAssemblyの生成
Rustのインストール
https://www.rust-lang.org/tools/install
これが無いと話にならないので、とりあえずインストールする必要があります
wasm-packのインストール
以下を実行してwasm-pack入れるとRustでWebAssemblyが簡単に生成できるようになります
cargo install wasm-pack
必要なコード
[package]
name = "wasm"
version = "0.1.0"
edition = "2018"
[lib]
crate-type = ["cdylib"]
[dependencies]
wasm-bindgen = "0.2.74"
use wasm_bindgen::prelude::*;
#[wasm_bindgen]
pub fn sums(value: i32) -> i32 {
let mut a: i32 = 0;
for i in 1..value+1 {
a += i;
}
a
}
1から任意の値までの合計を計算するプログラムです
RustからWebAssemblyを使う場合、あんまりゴチャゴチャ設定を書く必要はありません
コンパイル
wasm-pack build
以上のコマンドでWebAssemblyが出力されます
出力ファイル
以下の6つのファイルが生成されます
.gitignore
wasm.d.ts
wasm.js
wasm_bg.js
wasm_bg.wasm
wasm_bg.wasm.d.ts
必要なファイル
Next.jsから利用するときに必要なのは、以下の2つのファイルだけです
TypeScriptの定義も含まれています
wasm_bg.wasm
wasm_bg.wasm.d.ts
Next.js側
環境を整える
必要最低限のパッケージをインストールします
yarn init -y
yarn add next react react-dom
yarn add -D typescript @types/node @types/react
WebPackの設定
本来はasyncWebAssemblyをtrueにするだけで良いはずなのですが、webassemblyModuleFilenameの設定をいじらないとnext dev
では動くもののnext build
でエラーになります
module.exports = {
webpack: (config, { isServer }) => {
config.experiments = {
asyncWebAssembly: true,
};
config.output.webassemblyModuleFilename = (isServer ? '../' : '') + 'static/wasm/webassembly.wasm';
return config;
},
};
Next.jsからwasmを呼び出すコード
なんとwasmを直接import出来ます
TypeScriptの定義も自動生成されているので、何事も無かったかのように普通に呼び出して使えます
import { sums } from "../lib/wasm_bg.wasm";
import { useState } from "react";
const App = () => {
const [value, setValue] = useState(0);
return (
<div>
<input
onChange={(e) => {
const v = Number(e.target.value);
!isNaN(v) && setValue(sums(v));
}}
/>
<div>{value}</div>
</div>
);
};
export default App;
動作確認
- コマンド
next dev
- 確認
http://localhost:3000/
WebAssembly化したRustの関数から値が返ってきています
まとめ
ヤバいほど超簡単にWebAssemblyが使えます
wasmの中身がよく分かっていなくてもTypeScriptの定義があるので、何の違和感も無く使えます
Rustのソースを監視してファイル更新時にwasm-packを実行すると、さらに開発効率が上がりそうです
今後、WebAssemblyでスレッドサポートが標準化したら、そのパワーを生かした様々なライブラリが作られることが予想されます
そんな時代が来たらWeb開発の手法が大きく変わっていくかもしれません