wasm-pack
wasm-pack copied to clipboard
Add type = "module" in package.json to support nodejs in bundler mode
π‘ Feature description
When you build using the default "bundler" mode, it can almost run directly from nodejs, using nodejs's built in ESM support.
Unfortunately, the created package.json file is missing "type": "module"
. Adding this to the created package.json not only fixes some bundler issues, but also makes nodejs understand the created package too:
foo.js:
import {greet} from 'my_module'
greet()
$ node --experimental-wasm-modules foo.js
(node:414396) ExperimentalWarning: Importing Web Assembly modules is an experimental feature. This feature could change at any time
(Use `node --trace-warnings ...` to show where the warning was created)
Hello world!
Using node 14.17.3 (the current LTS release) I was able to get node to load the "bundler" version of the package.
To make it work, I had to add a main
entry to the package.json as well as the "type": "module"
(otherwise I just got Error [ERR_MODULE_NOT_FOUND]: Cannot find package
...).
I also had to work around a typescript issue: the current releases of typescript generates require
where import
is needed. I could fix the generated js manually, or switch to pre-releases builds of the compiler with: https://github.com/microsoft/TypeScript/pull/44501 which actually works! (use "typescript": "npm:@typescript-deploys/[email protected]"
which is mentioned in the PR discussion)
So with those two items added to the generated package.json, and that typescript compiler per-release, I'm able to use a single package in both nodejs and in the browser.
@josephg Thanks so much for posting this: I'd never have tried this approach without your suggestion!
It seems like you should only need that fancy version of typescript to support having mixed mode JS files. Typescript should be able to compile using esm mode in the currently released typescript versions. I haven't tried it though.
It seems like you should only need that fancy version of typescript to support having mixed mode JS files. Typescript should be able to compile using esm mode in the currently released typescript versions. I haven't tried it though.
I can't change the module type for the package doing the import (multiple unrelated import of third party packages break if I change it), so I needed an alternative. But in general, yes, compiling to an esm module should be a solution.
I've just written up the process of getting the hello-wasm-pack
example to work under Next.js. It was not altogether painless :-) and included manually editing the package under node_modules
to be the kind of ESM that Next.js will work with. Please check out https://github.com/gthb/try-to-use-wasm-in-next.js/blob/main/README.md and consider changing the package.json
in the wasm-pack bundler output accordingly (I've posted a PR for that).
I am using this simple script after build to automatically add "type":"module"'
to package.json after build:
const fs = require("fs"); // replace with import fs from 'fs'; if you need
const packageFileContent = fs.readFileSync("./pkg/package.json", "utf-8");
const packageJSON = JSON.parse(packageFileContent);
packageJSON.type = "module";
packageJSON.main = packageJSON.module;
fs.writeFileSync("./pkg/package.json", JSON.stringify(packageJSON, null, 2), "utf-8");
Itβd be great to see https://github.com/rustwasm/wasm-pack/pull/1061 merged! Iβve crafted a demo where I use --targer=bundler
and then manually patch package.json
. It confirms that the proposed solution works in Node.js, Jest and Next.js π
i really don't understand why this is still an issue.
this effectively breaks imports and forces all of us to do hacks and workarounds. this is a very popular package, and it definitely deserves more attention from the core team! To the core team, you don't need to implement this yourself, just MERGE THE PRs and publish it. we are happy then!
@drager sorry to ping, but would really love to see this PR merged. We're using an npm module built with wasm-pack, and we're unable to use it natively in Node + ES Modules because it wrongly declares itself as a CommonJS module. I am more than happy to help with any polish or other tasks to get this over the finish line.
Another temporary fix could be using the Linux jq
command, e.g.:
"wasm-patch": "jq '.type = \"module\"' ./your-pkg/package.json > ./your-pkg/package.json.tmp && mv ./your-pkg/package.json.tmp ./your-pkg/package.json",
Then run it after you run wasm-pack
.
(The temporary file is necessary unless you're willing to install extra packages)
It would be nice to be really nice to have more control over the package.json in general (including whether it's generated). For a recent project I ended up deleting it on build and just made my own wrapping package.json at the root of the project.
This issue is a must for everyone who is learning wasm-pack for the first time.
Hello, new wasmer.
You can try this:
npm pkg set type='module'
npm pkg set main='<your_crate>.js'
Bumping this; closing this issue by merging any of the above PRs or implementing any of the above solutions would be appreciated by many. I'm needing WASM more and more as I get into systems + web development, and having this issue closed would resolve a major hurdle in my adoption of this. Don't mean to be a pain, and apologies if this ping comes off poorly.
Bumping this; closing this issue by merging any of the above PRs or implementing any of the above solutions would be appreciated by many. I'm needing WASM more and more as I get into systems + web development, and having this issue closed would resolve a major hurdle in my adoption of this. Don't mean to be a pain, and apologies if this ping comes off poorly.
Yes, need to rebase master into the current PR in order to get that merged.
Yes, need to rebase master into the current PR in order to get that merged.
Done. (Well, merged, not rebased, from master β but I think the PR should just be squash-merged to master anyway, right?)
Yes, need to rebase master into the current PR in order to get that merged.
Done. (Well, merged, not rebased, from master β but I think the PR should just be squash-merged to master anyway, right?)
Thank you!