如何在包含tsconfig.json中定义的路径别名的NodeJS脚本中动态导入模块

j7dteeu8  于 2023-08-04  发布在  Node.js
关注(0)|答案(1)|浏览(159)

我们的项目使用React / Typescript和Nx以及WebPack和Babel。我们的monorepo包含几十个应用程序。作为我们i18 n计划的一部分,我正在开发一个git钩子,它将扫描每个应用程序目录并创建一个默认的libs/pages/xyz/src/i18n/translations/messages-en-US.json文件,我们的翻译团队可以将其摄取到他们的定制系统中,以便为其他语言(如messages-fr-CA.json)生成额外的文件。
我们的第一种方法是让Node脚本查找每个根应用程序消息文件(例如:libs/pages/xyz/src/i18n/messages.ts),将其转换为ES 2022,将其写入临时文件,然后通过import(temp.js)动态导入该文件,因此我们可以在将其写入默认libs/pages/xyz/src/i18n/translations/messages-en-US.json之前对该JSON进行多次转换。
然而,我在尝试动态导入这些文件时遇到了“模块未找到”错误,因为每个messages.ts文件都包含别名导入路径...
(ex:messages.ts从common/foo/xyz导入,但在我们的tsconfig.json路径中,它将Map到project-root/libs/shared/common/foo/src/xyz.ts
当使用ts.transpileModule(filePath, compilerOptions).outputText时,传输代码工作正常,但当我尝试const module = await import(compiledJSFilePath)时,我得到了模块解析错误,因为当动态导入带有别名导入的单个文件时,不使用在我的tsConfig.json中定义的别名路径...

// my-app/src/i18n/messages.ts
import fooMessages from 'Common/foo/messages';
import barMessages from 'Common/bar/messages';
... other required imports ...

export default {
  ...fooMessages,
  ...barMessages,
  ... other message files ...
}

// extract-messages.mjs
...
import * as fsp from 'node:fs/promises';
import ts from 'typescript';
...
tsContent = await fsp.readFile(targetAppRootMessageFile, { encoding: 'utf8' });
jsContent = ts.transpileModule(tsContent, compilerOptions).outputText;
await fsp.writeFile(tempOutputFile, jsContent);

const { default: messages } = await import(tempOutputFile);
... do transformations here ...
await fsp.writeFile(defaulti18nEnUSFile, JSON.stringify(transformedMessages, null, 2));
... delete temp file ...
... iterate to next application ...

字符串
我不是一个NodeJS / Typescript编译器大师,所以任何建议或指导都将不胜感激。

umuewwlo

umuewwlo1#

tsconfig.json中的paths别名仅适用于tsc编译器的类型,而不适用于实际发出的JS代码:
请注意,此功能不会更改tsc发出的导入路径,因此paths只应用于通知TypeScript另一个工具具有此Map,并将在运行时或捆绑时使用它。
我猜你的项目有一个特定的webpack路径别名配置,而tsconfig只是复制了这些,如上面引用的那样。
现在,IIUC,您正在编写一个新的工具脚本,它也将导入您编译的TS文件。因此,您需要在JS端再次实现路径别名。你可以例如使用tsconfig-paths库:
使用此选项加载其位置在tsconfig.jsonpaths部分中指定的模块
然后在执行新脚本时,启用tsconfig-paths,以便它根据tsconfig调整节点模块分辨率:

node -r tsconfig-paths/register extract-messages.mjs

字符串

相关问题