External Post

posted: 2019/09/04

parcel + rustでwasm_bindingを使うとき (TypeError: WebAssembly.instantiate(): Imports argument must be present and must be an objectの解決

parcel + rustで基礎的な部分は公式ドキュメントでも十分だったがwasm-bindgenなどを噛ませようとすると、色々と工夫が必要だと下記よりわかった。

おそらくpacel2になったら解決する可能性などはある

手順

準備

cargo install wasm-pack

ひとまずrust-parcel-templateに習いやっておく

cargo install wasm-pack

cargoの作成

cargo new wasm

今回はwasmという名前で作成

Cargo.tomlにwasm-bindgen追加

[dependencies]
wasm-bindgen = "^0.2.50"

src/lib.rs

こんな感じで作成。

extern crate wasm_bindgen;
use wasm_bindgen::prelude::*;

#[wasm_bindgen]
pub fn main() -> String {
    return "Hello, world!!".to_string();
}

JSの呼び出し側はこんな具合

const start = async () => {
  const { main } = await import("../wasm/src/lib.rs")
  
  console.log(main())
  // console.log(add(1, 2))
}

で、このあたりで下記のようなエラーにぶつかる

Uncaught (in promise) TypeError: WebAssembly.instantiate(): Imports argument must be present and must be an object 

解決策

parcel-plugin-wasm.rsのインストール

現状parcel本体側ではどうもwasm-bindgenとうまく噛み合わないようなので、pluginを入れる

parcelの場合はpluginをインストールすれば読み込まれるので、あとは不要。

npm install parcel-plugin-wasm.rs

そしてこれは深く読んでないので原因は不明だが、呼び出し元をCargo.tomlにする必要があった。

const start = async () => {
  const { main } = await import("../wasm/Cargo.toml")
  // もと -> const { main } = await import("../wasm/src/lib.rs")
  
  console.log(main())
  // console.log(add(1, 2))
}

これで解決した

参考2

この記事の修正をする