节点中的 Grunt 和 ES6 模块 - 不使用 .mjs 不兼容?
Grunt and ES6 modules in node - incompatible without the use of .mjs?
所以,我现在正在尝试使用 Typescript 和 Grunt,看看它对我来说是否值得。问题是:Typescript 不会编译为 *.mjs
文件,而只会编译为常规 *.js
文件。 Node 确实支持 ES6 模块,但前提是您将它们标记为“*.jsm”文件或通过设置 "type": "module"
。但是,在 package.json
中设置此顶级字段对同一目录中的任何 *.js
文件和任何后续文件具有全局范围。
这会破坏 Gruntfile.js
文件,因为它使用 CommonJS 模块,请参阅我的非常基本的 Gruntfile 作为示例:
module.exports = function (grunt) {
grunt.initConfig({
ts: {
default: {tsconfig: "./tsconfig.json"}
}
})
grunt.loadNpmTasks("grunt-ts");
grunt.registerTask("default", ["ts"]);
}
没想到会成功,我天真地将导出语法从 module.exports =
更改为 export default
,这预计不会起作用,因为它没有多大意义。
问题
- 是否有任何选项可以在节点中启用 ES6 模块的情况下使用 Grunt?
- 是否有正确的方法告诉 TypeScript 编译成
*.mjs
个文件?
可以先使用babel-node编译。这将解决 ES6 导出和导入问题。
npm install --save-dev @babel/core @babel/node
npx babel-node server.js
在 G运行t 之前使用 Babel 运行ning 的建议方法使 G运行t 有点多余。由于 TypeScript 尚不支持将 ES6 模块导出到 *.mjs
文件(当节点仍应为 运行 CommonJS 系统时,您必须在导入中使用 *.mjs
后缀)并且可能永远不会完全(参见 Design Meeting Notes 11/22/2019)我必须得出结论,ES6 模块仍然具有严重的影响和问题。更改文件扩展名不够,因为无扩展名的导入因节点而失败。您需要遍历每个已编译的文件并更改导入以专门加载 *.mjs
个文件。
但是,TypeScript 编译器 可以 以它确实理解 ES6 模块语法并编译为 CommonJS 的方式设置(参见 TS handbook)。
{
"compilerOptions": {
"module": "CommonJS",
// [...]
},
}
这样 TypeScript 代码就可以用 ES6 模块语法编写,并且输出可以与 CommonJS 兼容,而不会破坏其他代码。作为奖励,您可以跳过 Babel 方法,g运行t 可以 运行 TS 编译器。
如果您在 package.json
中设置了 "type": "module"
,您需要将 Gruntfile.js
重命名为 Gruntfile.cjs
,并 运行 将其重命名为 grunt --gruntfile Gruntfile.cjs
.
所以,我现在正在尝试使用 Typescript 和 Grunt,看看它对我来说是否值得。问题是:Typescript 不会编译为 *.mjs
文件,而只会编译为常规 *.js
文件。 Node 确实支持 ES6 模块,但前提是您将它们标记为“*.jsm”文件或通过设置 "type": "module"
。但是,在 package.json
中设置此顶级字段对同一目录中的任何 *.js
文件和任何后续文件具有全局范围。
这会破坏 Gruntfile.js
文件,因为它使用 CommonJS 模块,请参阅我的非常基本的 Gruntfile 作为示例:
module.exports = function (grunt) {
grunt.initConfig({
ts: {
default: {tsconfig: "./tsconfig.json"}
}
})
grunt.loadNpmTasks("grunt-ts");
grunt.registerTask("default", ["ts"]);
}
没想到会成功,我天真地将导出语法从 module.exports =
更改为 export default
,这预计不会起作用,因为它没有多大意义。
问题
- 是否有任何选项可以在节点中启用 ES6 模块的情况下使用 Grunt?
- 是否有正确的方法告诉 TypeScript 编译成
*.mjs
个文件?
可以先使用babel-node编译。这将解决 ES6 导出和导入问题。
npm install --save-dev @babel/core @babel/node
npx babel-node server.js
在 G运行t 之前使用 Babel 运行ning 的建议方法使 G运行t 有点多余。由于 TypeScript 尚不支持将 ES6 模块导出到 *.mjs
文件(当节点仍应为 运行 CommonJS 系统时,您必须在导入中使用 *.mjs
后缀)并且可能永远不会完全(参见 Design Meeting Notes 11/22/2019)我必须得出结论,ES6 模块仍然具有严重的影响和问题。更改文件扩展名不够,因为无扩展名的导入因节点而失败。您需要遍历每个已编译的文件并更改导入以专门加载 *.mjs
个文件。
但是,TypeScript 编译器 可以 以它确实理解 ES6 模块语法并编译为 CommonJS 的方式设置(参见 TS handbook)。
{
"compilerOptions": {
"module": "CommonJS",
// [...]
},
}
这样 TypeScript 代码就可以用 ES6 模块语法编写,并且输出可以与 CommonJS 兼容,而不会破坏其他代码。作为奖励,您可以跳过 Babel 方法,g运行t 可以 运行 TS 编译器。
如果您在 package.json
中设置了 "type": "module"
,您需要将 Gruntfile.js
重命名为 Gruntfile.cjs
,并 运行 将其重命名为 grunt --gruntfile Gruntfile.cjs
.