flightcontrolhq / superjson

Safely serialize JavaScript expressions to a superset of JSON, which includes Dates, BigInts, and more.
https://www.flightcontrol.dev?ref=superjson
MIT License
4.17k stars 90 forks source link

fix: support cjs #301

Open acheronfail opened 1 month ago

acheronfail commented 1 month ago

It doesn't take much to support CJS, and it really helps the community with large applications and projects that continue to use this package.

Explanation

I'm not going to put my opinions on ESM vs CJS here since I don't want to start a flame war, but this change should make both parties happy, by supporting both: superjson can still be written in ESM and ship ESM, but tsc will transpile it to CJS for the CJS consumers.

If the package is require()'d, then it will use the dist-cjs/* files, and if it's import'd, then it will use dist/index.js.

Testing

  1. clone and setup superjson locally
  2. run yarn link inside superjson's directory
  3. create a node package with "type": "module", in this directory run yarn add superjson && yarn link superjson
  4. in this new directory, create index.js with import S from 'superjson'; console.log(S); and run it
  5. create a node package with "type": "commonjs", in this directory run yarn add superjson && yarn link superjson
  6. in this new directory, create index.js with console.log(require('superjson'));, and run it

Maintenance burden

In terms of burden for superjson maintainers, really it's having an extra 2 files: tsconfig.cjs.json and commonjs.js. Both of these files together add up to 33 lines of code - it's not a lot. Since the superjson package uses ESM, we can confidently just patch the require calls in the tsc output, since ESM imports are more strict than CJS ones, etc.

Final notes

Ultimately this is up to the superjson maintainers to accept or not, but I've at least proposed it as a starting point. Up to the maintainers to decide if they want to do it this way to support all their consumers or just a subset...

Fixes #268 Fixes #299