【问题标题】:ES modules and jsconfig.json: Error [ERR_MODULE_NOT_FOUND]ES 模块和 jsconfig.json:错误 [ERR_MODULE_NOT_FOUND]
【发布时间】:2021-09-29 12:04:33
【问题描述】:

我有一个使用常规 JS 的节点 Web 应用项目。

我正在尝试使用jsconfig.json 设置一些路径。我尝试使用节点默认的Subpath imports,即使它确实有效,vscode intellisense 也停止了工作。

我发现你可以使用jsconfig.json 所以我设置了这个文件

{
  "compilerOptions": {
    "target": "es6",
    "module": "commonjs",
    "baseUrl": "./",
    "paths": {
      "@controllers/*": ["node/controllers/*"],
    },
  },
  "exclude": ["node_modules"]
}

我在package.json 上添加了

"type": "module",

我的文件夹结构是

├── node
│    └──controllers
│         └── foo.js
├── server.js
├── jsconfig.json
└── package.json

但是当我尝试从server.js导入时

import { foo } from '@controllers/foo.js'
// or import { foo } from '@controllers/foo'

foo.js

export const foo = 'Hello server'

我明白了

node:internal/process/esm_loader:74
     internalBinding('errors').triggerUncaughtException(

Error [ERR_MODULE_NOT_FOUND]: Cannot find package '@controllers/foo.js' imported from /Users/Alvaro/Sites/test/server.js

 at new NodeError (node:internal/errors:363:5)
 at packageResolve (node:internal/modules/esm/resolve:698:9)
 at moduleResolve (node:internal/modules/esm/resolve:739:18)
 at Loader.defaultResolve [as _resolve] (node:internal/modules/esm/resolve:853:11)
 at Loader.resolve (node:internal/modules/esm/loader:89:40)
 at Loader.getModuleJob (node:internal/modules/esm/loader:242:28)
 at ModuleWrap.<anonymous> (node:internal/modules/esm/module_job:73:40)
at link (node:internal/modules/esm/module_job:72:36) {
code: 'ERR_MODULE_NOT_FOUND'

【问题讨论】:

  • baseUrl:"."更改为baseUrl:"./"
  • @SachinAnanthakumar,它没有修复它。
  • 你在 foo.js 中添加了export default 吗?
  • 是的,当然,导出默认......
  • 我不知道为什么它不起作用,这是完整的错误堆栈跟踪吗?

标签: javascript node.js visual-studio-code


【解决方案1】:

经过数小时的研究,我发现在使用esm 时很难拥有自定义别名路径,并且很容易为commonjs 配置,

但是当您使用esm 时,它可以以稍微不同的方式实现, 我将在 方法 1 中为 esm 实现编写解决方案,然后在 方法 2

中为 commonjs 编写解决方案

方法一

第 0 步:

删除jsconfig.json

第 1 步:

在您的 package.json 添加一个 exports 属性,

"name": "package-name"

"exports":{
   "./@controllers/" : "./node/controllers/"
}

注意:不要忘记@controllers/node/controllers/后面的'/'

第 2 步

你必须导入文件

  import {foo} from "package-name/controllers/index.js" 
/*
package-name is the same value as the 'name' property in
the package.json
*/

要了解有关package.jsonexports 属性的更多信息,请参阅here

------------------------------XXXXXXXX---------------- ------------------

方法二

你不能在这个方法中使用es modules

步骤 0

安装module-alias 包。

npm i module-alias

如果package.json中存在type:module,则删除它或将值更改为commonjs

第 1 步

package.json中指定为entry point的文件的起始行添加以下代码

require(module-alias/register)

检查package.json中的main属性,作者的情况应该是server.js

package.json添加这个

"_moduleAliases": {
  "@root" : ".", // Don't forget to mnetion this
  "@controllers" : "node/controllers/*"
}

现在您可以从以下目录中获取模块

const {foo} = require("@controllers/foo.js") // if foo is named export 

//or

const foo = require("@controllers/foo.js");

你可以参考更多关于module-aliashere

【讨论】:

  • 感谢您的努力,我确实提到了节点导出路径以及上面关于子路径导入问题的链接。正如我在这个问题上提到的那样,它的问题是你会在 Vscode 上失去从这些路径导入的函数的智能感知。很遗憾,我不会很快放弃 ES 模块。
  • 目前还没有适用于node的解决方案,希望他们修复它,我今天会尝试找到一些解决方法
【解决方案2】:

你所尝试的几乎是正确的。

您可以使用别名,但它必须以 # 开头。

例如:在package.json

"imports": {
    "#app": "./app.js"
}

jsconfig.json

{
  "compilerOptions": {
    "paths": {
      "#app": ["./app.js"]
    }
  }
}

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2021-12-05
    • 1970-01-01
    • 2022-08-23
    • 1970-01-01
    • 2022-11-18
    • 2021-06-26
    相关资源
    最近更新 更多