Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to import a node module VS use the browser api?

In a TS package designed to run in both nodeJS and a browser, I want to access secure random generation from either crypto.getRandomValues(browser) or crypto.randomFillSync(node).

In package.json, I have "type": "module", my whole library uses ES6 imports (so require is not defined).
I use tsc to compile the regular node package and rollup to pack it into a UMD for browser.

Unfortunately, the node crypto module must be imported to be usable. The import statement cannot "hide" inside if, so it will crash when run in the browser.

if(typeof crypto == "object"){
  fillRandom = crypto.getRandomValues
}
else{ //node
  import crypto from "crypto" //Err: Cannot use import outside a module (browser)
  fillRandom = crypto.randomFillSync
}

With commonJS I could simply use require("crypto"), but I have already fully commited to using ESM modules.

I imagine I could swap out this part of the code before compiling TS for browser/node, so both versions would have the code that makes sense in their enviroment, but I don't know how, it seems a bit overkill.

Is there a way?

like image 980
Franartur Čech Avatar asked Oct 30 '25 06:10

Franartur Čech


1 Answers

Hi @Franartur Čech,

An import declaration can only be used at the top level of a module.

So, You just need to add await for your module.

if (typeof crypto == "object") {
    fillRandom = crypto.getRandomValues
} else {
    const { randomFillSync } = await import("crypto");
}

There is another similar type of answer I find on the internet. With the window.crypto property, it is available in modern browsers that support the Web Cryptography API, I guess.

if (typeof window !== "undefined" && typeof window.crypto === "object") {
  fillRandom = (buffer) => {
    window.crypto.getRandomValues(buffer);
  };
} else {
  // node.js environment
  const crypto = require("crypto");
  fillRandom = crypto.randomFillSync;
}
like image 116
DSDmark Avatar answered Nov 01 '25 19:11

DSDmark



Donate For Us

If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!