Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add type = "module" in package.json to support nodejs in bundler mode #1039

Closed
josephg opened this issue Jul 26, 2021 · 15 comments · Fixed by #1061
Closed

Add type = "module" in package.json to support nodejs in bundler mode #1039

josephg opened this issue Jul 26, 2021 · 15 comments · Fixed by #1061

Comments

@josephg
Copy link

josephg commented Jul 26, 2021

💡 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!
@CraigMacomber
Copy link

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: microsoft/TypeScript#44501 which actually works! (use "typescript": "npm:@typescript-deploys/pr-build@4.4.0-pr-44501-7" 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!

@josephg josephg changed the title Bundler mode missing type = "module" in package.json Add type = "module" in package.json to support nodejs in bundler mode Jul 28, 2021
@josephg
Copy link
Author

josephg commented Jul 28, 2021

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.

@CraigMacomber
Copy link

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.

@gthb
Copy link
Contributor

gthb commented Sep 22, 2021

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).

@neuronetio
Copy link

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");

@kachkaev
Copy link

It’d be great to see #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 🎉

@woss
Copy link

woss commented Oct 17, 2022

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!

acdamiani added a commit to acdamiani/voxviewer that referenced this issue Mar 25, 2023
acdamiani added a commit to acdamiani/voxviewer that referenced this issue Mar 25, 2023
@vacekj
Copy link

vacekj commented Apr 29, 2023

@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.

@LeoDog896
Copy link

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)

@AlansCodeLog
Copy link

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.

@magicwenli
Copy link

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'

@ben-laird
Copy link

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.

@drager
Copy link
Member

drager commented Nov 14, 2023

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.

@gthb
Copy link
Contributor

gthb commented Nov 14, 2023

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?)

@drager
Copy link
Member

drager commented Nov 14, 2023

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!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging a pull request may close this issue.