nx
nx copied to clipboard
feat(node): allow executing esm compiled scripts
Current Behavior
The @nrwl/node:node executor is not able to execute esm module scripts
Expected Behavior
The @nrwl/node:node executor is able to execute esm module scripts
☁️ Nx Cloud Report
We didn't find any information for the current pull request with the commit e6fdb7feb45622b9a07ef63e7da3ad05a6a2be17. You might need to set the 'NX_BRANCH' environment variable in your CI pipeline.
Check the Nx Cloud Github Integration documentation for more information.
Sent with 💌 from NxCloud.
The latest updates on your projects. Learn more about Vercel for Git ↗︎
1 Ignored Deployment
Name | Status | Preview | Comments | Updated (UTC) |
---|---|---|---|---|
nx-dev | ⬜️ Ignored (Inspect) | May 4, 2023 9:45pm |
Why did the build not run?
@bulldog98 , thank you for the PR. Can you add some e2e tests for this change?
@bulldog98 , thank you for the PR. Can you add some e2e tests for this change?
Sure I first did not see there where e2e tests, but found them now.
@nartc I was unable to run the e2e test locally, how are they executed?
@bulldog98 I've rebased the branch and kicked off the build which is failing. Can you take a look? To run test locally, you'd need to start local-registry
with:
yarn local-registry enable
yarn local-registry start
then run the e2e:
yarn nx e2e e2e-node
sure I'm working on fixing the test.
@nartc I fixed the e2e test it works now
I had the same problem. How can I use this pr to test if it's the same problem?
@nartc sorry I had messed up the check to beEqual, but it should be a toContains
@bulldog98 Thanks for the PR. Everything looks good so far. Just one quick question, why did you have the following?
...
const dynamicImport = new Function('specifier', 'return import(specifier)');
...
Would this work as well?
...
function dynamicImport(specifier) {
return import(specifier);
}
dynamicImport(fileToRun);
...
That said, I'm curious why not just import(fileToRun)
The problem is that typescript transpiles the import(fileToRun)
to require(fileToRun)
the same happens with the version of @nartc.
The "real" fix would be to change "module" to "es2020" in the tsconfig - that would be a much larger change, but also this implicitly breaks environments that don't support the dynamic import syntax natively instead of explicitly. I think all current supported node versions should though?
@luxaritas yep, that's my concern as well. I also think the real fix is to support ESM across the board. With TS 4.7, we have a more "official" ESM support but we're somewhat waiting for the dust to settle before making substantial changes to all plugins.
pick up config from test case
nrwl build app support esm will fix some problem. use custom webpack
project.json
{
"targets": {
"build": {
"executor": "@nrwl/node:webpack",
"outputs": ["{options.outputPath}"],
"options": {
"outputPath": "dist/apps/<project>",
"main": "apps/<project>/src/main.ts",
"tsConfig": "apps/<project>/tsconfig.app.json",
"assets": ["apps/<project>/src/assets"],
"webpackConfig": "apps/<project>/webpack.config.js" <== add this
},
}
}
apps/
module.exports = (config, context) => ({
...config,
experiments: {
...config.experiments,
outputModule: true,
topLevelAwait: true,
},
output: {
path: config.output.path,
chunkFormat: 'module',
library: {
type: 'module',
},
},
})
Closing because we'd like to implement a better fix across Nx to support ESM instead of dynamic import hack. Thank you bulldog98 for the PR but I'll be closing this.
@nartc - This problem has completely derailed one of our active projects and it seems like many others on this thread are struggling with this also. Because of that I truly hope that closing this PR means that there will be an official fix released in the very near future.
Created similar bug to this one https://github.com/nrwl/nx/issues/12259
@nartc that's great news! is there anywhere we can track/contribute to this?
I hope this issue is solved soon! I've just upgraded my project to v14 and now I'm not able to do anything with it unless this issue is solved! My project is practically frozen!
why is it so complicated, seriously, i just want to set my f*cking desk on fire. 3 hours trying to add an app to NX that only uses yargs and inquirer 😮💨 , i quit
try this https://github.com/esbuild-kit/tsx just run command
as a workaround, is it possible to tell webpack to handle a specific node module as esm?
psuedo code:
// webpack.config.js
module: {
rules: [
{
test: /node_modules/the-package,
target: "module",
loader: "babel-loader",
},
],
},
@nartc 15.3.0 came out today, yet this is still broken. What's up?
I just upgraded to 15.4.2, and my project is borked. I'm not even sure there's a possible path forward until nx has ESM support... but does anyone have a workaround in the meantime?
@quaelin you can patch the file in the error directly and replace the require with import
@quaelin
I am using the following solution to solve the esm problem, you can refer to use it.
// apps/SOME/webpack.config.cjs
const nodeExternals = require('webpack-node-externals')
module.exports = (config, context) => {
return {
...config,
externalsPresets: {
node: true,
},
output: {
...config.output,
module: true,
libraryTarget: 'module',
chunkFormat: 'module',
library: {
type: 'module',
},
environment: {
module: true,
},
},
experiments: {
outputModule: true,
},
externals: nodeExternals({
importType: 'module',
}),
}
}
// project.json or workspace.json
"build": {
"executor": "@nrwl/webpack:webpack",
"dependsOn": ["build-porto"],
"outputs": ["{options.outputPath}"],
"options": {
"target": "node",
"compiler": "tsc",
"outputPath": "dist/apps/api",
"main": "apps/api/src/main.ts",
"tsConfig": "apps/api/tsconfig.app.json",
"assets": ["apps/api/src/assets"],
// add next line
"webpackConfig": "apps/api/webpack.config.cjs",
"generatePackageJson": true
},
add package.json or create package.json
//apps/SOME/package.json
"type": "module"
update project tsconfig.json
// tsconfig.app.json
{
"extends": "./tsconfig.json",
"compilerOptions": {
"outDir": "../../dist/out-tsc",
// change this
"module": "es2020",
"types": ["node"]
},
"exclude": ["jest.config.ts", "src/**/*.spec.ts", "src/**/*.test.ts"],
"include": ["src/**/*.ts"]
}
pnpm patch
- pnpm patch @nrwl/js
- modify
src/executors/node/node-with-require-overrides.js
-require(fileToRun);
+const dynamicImport = new Function('specifier', 'return import(specifier)');
+dynamicImport(fileToRun);
- pnpm patch-commit [path], path from step 1
In addition to using pnpm patch you can also use https://github.com/ds300/patch-package
@nartc @luxaritas Any plan for the official fix to be rolled out?
@nartc @luxaritas Will it be much better for the community to have this workaround merged while you are doing internal fix the perfect way? I think a lot of projects have been being impacted by this...