I'm trying to instantiate a .wasm file locally in node.js. The goal is to run the binary locally and reproduce the functionalities of the web page. Here's my minimum reproducible example:
const fetch = require("node-fetch");
const importObject = {
imports: {
imported_func: function(arg) {
console.log(arg);
}
}
};
fetch('https://www.supremenewyork.com/ticket.wasm').then(response =>
response.arrayBuffer()
).then(bytes => {
let mod = new WebAssembly.Module(bytes);
let instance = new WebAssembly.Instance(mod, importObject);
instance.exports.exported_func();
})
The error I get is:
TypeError: WebAssembly.Instance(): Import #0 module="wasi_unstable" error: module is not an object or function
I saw some questions with similar problems but no real solutions were provided. This is my first time working with wasm so I'm pretty lost.
Warning: This method is not the most efficient way of fetching and instantiating wasm modules. If at all possible, you should use the newer WebAssembly.instantiateStreaming () method instead, which fetches, compiles, and instantiates a module all in one step, directly from the raw bytecode, so doesn't require conversion to an ArrayBuffer .
In the worker (see wasm_worker.js ) we define an import object for the module to use, then set up an event handler to receive the module from the main thread. When the module is received, we create an instance from it using the WebAssembly.instantiate () method and invoke an exported function from inside it.
Instead, if you want to instantiate it yourself, you can look in the .wast at what it expects. However, you'll need to match the ABI expectations as well, like creating the stack, libc syscall imports if you print etc. In other words, emcc emits wasm files that are not standalone, they are designed to work with the .js file emcc emits for you.
In theory a wasm file could be standalone, if you don't use any imports, manage your own stack, etc. and just provide exports that are called from outside. You can try to experiment with this using the ONLY_MY_CODE option to emcc, but it's not much tested yet-the main focus in emscripten has been to get C and C++ programs to "just work".
Your module seems to depend on the wasi_unstable
API. If you want to load it you will need an implementation of that API.
To see exactly what imports you module needs you can use wasm2wat
or wasmdis
tools from wabt and binaryen projects respectively.
If you built your wasm module with emscripten then the recommended practice is to have the emscripten generate JS to that implenents these APIs and takes case of loading the module for you.
If you build your wasm module with the wasi-sdk then you need some kind of web polyfill for the WASI APIs.
This will make the error go away:
const importObject = {
imports: {
imported_func: function(arg) {
console.log(arg);
},
wasi_unstable: () => {}
}
};
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With