fix: NET-1428: Ensure proper ESM/CJS entry point in the "browser" export
Summary
The aim here is to improve DX for those who want to use the SDK in their apps (webpack, rollup, etc.). Moves the static SDK build (streamr-sdk.web.js) to the "script" export and populates the "browser" export with proper browser-specific mods.
- [x] Fix browser tests 😱
- [ ] Can we make the browser test runner smarter? Lots of remapping in there, still. 😬 If I remove them it breaks viciously.
Goes really well with #3018 and #3017.
Changes
- Define proper "browser" exports.
- Add a postbuild script to DHT – rewrites its package.json to fix pathnames in
dist/package.json. - Refactor SDK's postbuild script – comes with a new package.json rewrite script (now written in ts).
- Simplify the
release.shscript and make it a bit more consistent. It's a good script.
Limitations and future improvements
- Devs still need to polyfill for their browser-targetted bundles (os, fs, stream, etc.). node-polyfill-webpack-plugin is a good one for Webpack.
Checklist before requesting a review
- [ ] Is this a breaking change? If it is, be clear in summary.
- [x] Read through code myself one more time.
- [x] Make sure any and all
TODOcomments left behind are meant to be left in. - [x] Has reasonable passing test coverage?
- [ ] Updated changelog if applicable.
- [x] Updated documentation if applicable.
Here's one interesting fact https://github.com/streamr-dev/hub/pull/1981#issuecomment-2687986542
I'm starting to wonder that we may want an explicit browser export (@streamr/sdk/browser) so that others who use it don't have to do jest hacks like I did there.
@harbu, about tsx
- Works out of the box for ESM scripts (import/export), but untested on CJS.
- Ignores tsconfig.json, so project-specific settings (module resolver, target, etc.) don’t matter.
I'd use it for standalone scripts. Why stop?
- Switching to ts-node broke the script (no import.meta, no JSON import assertions, etc.). It might work with the right options, but...
- ESLint complained about missing ESM features, too.
To satisfy ESLint and stick to ts-node, the easiest fix was compiling to proper CJS. It works really well without extra deps which is cool.
@harbu, and on the rewriting of package.json:
With relative pathnames in "browser" (especially) we have to alter dist/package.json before publishing. It is crucial for bundler resolvers. I believe it was the reason for rewriting SDK's package.json originally.
Not sure why the SDK is published from dist, but I’m not against it. The code’s there, so maybe it makes sense. That said, a single package.json per package feels cleaner. Publishing outside dist means dealing with two: one at the root, one in dist. Efficiency matters.
@teogeb @harbu, guys, have another look.
- I've updated docs.
- I've mentioned the breaking nature of the change in the changelog, too.
Last minute hiccups.
- Had to drop rollup's usage tips and update Gatsby's (see docs). I pointed to a bad export previously. Getting them up and running wasn't so easy (esp. Gatsby). Next.js much smoother.
- Getting GitHub Actions has encountered an internal error when running your job. I'll ignore it.