hardhat icon indicating copy to clipboard operation
hardhat copied to clipboard

Initial support for ES Modules

Open fvictorio opened this issue 3 years ago • 1 comments

Support ES Modules in scripts and tests. The config and anything required from it will still have to be a commonjs module.

Todo:

  • [ ] Include .cjs/.cts/.mjs/.mts files when running the test task
  • [ ] Create a .cjs/.cts hardhat config during initialization if the projects has type: module

fvictorio avatar Aug 15 '22 20:08 fvictorio

This issue is also being tracked on Linear.

We use Linear to manage our development process, but we keep the conversations on Github.

LINEAR-ID: 6e5e4298-5f0d-4e67-8e6f-1002ab3a321a

github-actions[bot] avatar Aug 15 '22 20:08 github-actions[bot]

For example, they rely on an experimental API of Node that is not stable and triggers some annoying warnings.

Personally, I think this reason is not enough to disable TypeScript support.

vladfaust avatar Jan 02 '23 15:01 vladfaust

It's not that we are disabling it, it's that we don't want to invest significant time adding support for it right now if the result might break anytime soon. But we might re-consider this in some months.

If this is something you want or need, please upvote this issue

fvictorio avatar Jan 02 '23 16:01 fvictorio

Why not use tools such as tsup (a detailed example available here) that allow to build Hardhat in cjs and esm, and thus solve the problem while bringing the support to Typescript at the same time?

Olyno avatar Jan 03 '23 06:01 Olyno

Hardhat projects that use ESM will need to have a hardhat.config.cjs file (a CommonJS config file) and all the files required by it will need to be CJS too. But the rest of the project, including scripts and tests, will be writable in ESM.

this is actually quite a significant limitation because any of the hardhat plugins which depend on ESM-only modules (ex. IPFS https://github.com/ipfs/js-ipfs/blob/master/packages/ipfs-http-client/package.json#L21 ) will have to be held back to older versions, which has been starting to lead to problems at least with the plugin that I am working on. Any plans to change this in the near future?

dbeal-eth avatar Jan 03 '23 06:01 dbeal-eth

@Olyno the problem here is this: you want to write your Hardhat project in TS, and you want to transpile to ES modules (because one of your dependencies is ESM only). To execute your scripts/tests without having to compile the project, you have to use something like ts-node (or an alternative like swc). But ts-node's support for this is still very experimental, and migrating to another tool is not super easy.

How does bundling Hardhat itself fixes that?

Any plans to change this in the near future?

@dbeal-eth Yeah, definitely. We are just starting with ESM support for js projects because it's easier and we can support it without any major trade-offs. That doesn't mean we don't want to add ESM support for ts projects. We might just end up doing the ts-node-with-warnings fix, so that there's at least some workaround.

fvictorio avatar Jan 03 '23 07:01 fvictorio

@fvictorio actually my earlier query was regarding the restriction where the hardhat.config.cjs module has to be a cjs file, but that means that there is no capability for supporting ESM hardhat plugins. If you are developing a hardhat plugin that depends on another nodejs module which only supports ESM, its a problem...

dbeal-eth avatar Jan 03 '23 11:01 dbeal-eth

Oh, I see. Yeah, that will be a major breaking change, so it will have to wait until a future v3 of Hardhat.

fvictorio avatar Jan 03 '23 11:01 fvictorio

I'm using hardhat in a sveltekit project with a package.json file with those devDependencies as well:

		"@nomicfoundation/hardhat-chai-matchers": "^1.0.4",
		"@nomicfoundation/hardhat-network-helpers": "^1.0.6",
		"@nomicfoundation/hardhat-toolbox": "^2.0.0",
		"@nomiclabs/hardhat-ethers": "^2.2.0",

And this installs automatically hardhat: "0.1.0" (which does not seem to be the esm version??) instead of the "2.12.0-esm.1" that should be installed from the `dependencies":

"hardhat": "^2.12.0-esm.1",

the only solution I found for now is to add an override: { } in my npm. Is there a better approach?

mime29 avatar Feb 13 '23 15:02 mime29

Hey @mime29, can you open a separate issue and describe your system in detail? Thanks

alcuadrado avatar Feb 13 '23 15:02 alcuadrado

I don't claim to understand many (any?) details surrounding ESM, hardhat and node; and I'm not sure that this issue is the best place to report this, but it's where I arrived after googling about error TS5095: Option 'preserveValueImports' can only be used when 'module' is set to 'es2015' or later.

I wanted to report that setting "module," to node16 or nodenext instead of commonjs, allows a hardhat.config.ts file that uses import statements to run...

    "compilerOptions": {
        "target": "es2020",
        "module": "nodenext",

aathan avatar Feb 14 '23 06:02 aathan

ESModules are mandatory in Next.js TS projects, so importing the Hardhat Runtime is impossible in Typescript Next.js projects.

mihaic195 avatar Feb 14 '23 11:02 mihaic195

Hardhat can't be used in the browser. Or do you mean a combined node+next.js project?

alcuadrado avatar Feb 14 '23 13:02 alcuadrado

@alcuadrado I don't expect it to run in the browser. I opened a new issue with more details here: https://github.com/NomicFoundation/hardhat/issues/3676

mihaic195 avatar Feb 15 '23 12:02 mihaic195

Released in Hardhat v2.13.0 :tada:

fvictorio avatar Mar 02 '23 18:03 fvictorio