Implement dual-module build (ESM + CJS) #2122
Open
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
I hit against the fact that this package is CJS-only recently. I'm implementing a JavaScript action and the lack of ESM means a lot of code is ending up in my
index.js
bundle that should get treeshaken.I built zshy as a build tool for Zod, and it's been working perfectly for a couple months now. It's designed for projects who are migrating from vanilla
tsc
, as it uses the actual TypeScript compiler (plus some TS Compiler API magic) to do ESM & CJS builds that respect your existing tsconfigs. You can see that there's pretty minimal changes here, but runningnpm run build
now produces both ESM and CJS builds alongside each other inlib
.I'd understand any concern around adding the new
zshy
dependency, but there's not a big learning curve. It's a comparatively thin layer overtsc
, and still uses all the existingtsconfig
settings (with some strategic overrides to do the ESM build, of course).I admit I was inspired to do this because it solves my problem, and it's a demonstrative example of
zshy
. It also pains me to see a fully TypeScript project forgoing ESM whenzshy
makes it so easy. So no worries if you close this, but if you were already looking for an easy way to do ESM this is it!PS
zshy
adds"exports"
to package.json. This in turn makes it illegal for ESM-aware versions of Node to import from subpaths not listed in the"exports"
map (e.g.import "@actions/core/lib/command.js"
). That's the biggest potentially breaking change (though in general this is a good practice that promotes better encapsulation).Closes #1770