我正在构建一个需要使用Web汇编(WASM(的Electron应用程序,但是我在导入WASM文件时遇到了Fetch抛出TypeError: Only absolute URLs are supported
的问题。
此外,也许这提出了一个更广泛的问题,即应该使用电子主进程还是渲染器进程来运行 WASM?它似乎确实在渲染过程中起作用。
这是完整的错误:
TypeError: Only absolute URLs are supported
at parseURL (/Users/devuser/development/electron-api-demos/node_modules/node-fetch/dist/index.cjs:897:8)
at new Request (/Users/devuser/development/electron-api-demos/node_modules/node-fetch/dist/index.cjs:922:17)
at /Users/devuser/development/electron-api-demos/node_modules/node-fetch/dist/index.cjs:1175:19
at new Promise (<anonymous>)
at fetch (/Users/devuser/development/electron-api-demos/node_modules/node-fetch/dist/index.cjs:1173:9)
at IpcMainImpl.<anonymous> (/Users/cbourne/development/electron-api-demos/main-process/communication/async-msg.js:20:36)
at IpcMainImpl.emit (events.js:223:5)
at WebContents.<anonymous> (electron/js2c/browser_init.js:4093:15)
at WebContents.emit (events.js:223:5)
这是我正在测试的主进程代码:
const {ipcMain} = require('electron')
require('/Users/devuser/development/electron-api-demos/script/wasm_exec.js')
const fetch = require("node-fetch");
ipcMain.on('asynchronous-message', (event, arg) => {
if (!WebAssembly.instantiateStreaming) { // polyfill
WebAssembly.instantiateStreaming = async (resp, importObject) => {
const source = await (await resp).arrayBuffer();
return await WebAssembly.instantiate(source, importObject);
};
}
const go = new Go();
let mod, inst;
WebAssembly.instantiateStreaming(fetch("test.wasm"), go.importObject).then((result) => {
mod = result.module;
inst = result.instance;
document.getElementById("runButton").disabled = false;
}).catch((err) => {
console.error(err);
});
async function run() {
console.clear();
await go.run(inst);
inst = await WebAssembly.instantiate(mod, go.importObject); // reset instance
}
event.sender.send('asynchronous-reply', 'pong')
})
问题根本不是 WASM,而是应该获取二进制文件的请求。您的fetch
来自node-fetch
; 主进程在 Node 中运行.js因此不像普通页面那样具有基址。要么提供一个完整的file:///
绝对的URL来fetch
,或者更容易地使用fs.readFileSync
:
const fs = require('fs');
WebAssembly.instantiate(fs.readFileSync("text.wasm"));
我只能回答你的部分问题。
WASM 可能不应该在主进程中运行。即使 WASM 将在独立线程中运行,您也应最大程度地减少主进程上的负载。当主进程被阻止时,即使像最小化应用程序这样的事情也不会发生,直到它被解锁。
有关更多信息,这是一篇好文章:https://medium.com/actualbudget/the-horror-of-blocking-electrons-main-process-351bf11a763c