Babel 递归转译

Sea*_*ean 6 javascript node.js babeljs

设想

考虑以下目录结构

/views
  /one.js
  /two.js
/components
  /Header.js
  /Footer.js
/other
  ...
Run Code Online (Sandbox Code Playgroud)

我需要/views用 Babel 转译目录。我以编程方式执行此操作,但等效的 cli 命令如下所示:

babel views --out-dir .views

但该/views目录下的文件依赖于其他目录下的文件,即

/*
  views/one.js
*/

const Header = require('../components/Header');
...
Run Code Online (Sandbox Code Playgroud)

鉴于这种依赖性,我也需要/components/Header.js进行转译。

问题

我如何使用 Babel(可能与另一个库一起使用)转译指定的目录任何递归依赖项,而不转译整个代码库(例如/other等)?

mor*_*ney 1

在 Node.js 中获取依赖关系图可能有多种选择。你可以使用node-dependency-tree来获取你想要用 babel 转译的依赖图。Madge将是另一种可能的选择(dependency-tree内部使用)。

它是如何工作的?

依赖关系树接受一个起始文件,通过 precinct 提取其声明的依赖关系,通过归档柜将每个依赖关系解析为文件系统上的文件,然后递归地执行这些步骤,直到没有更多的依赖关系需要处理。

使用dependency-tree方法toList

返回树的后序遍历(列表形式),并删除重复的子树。这对于捆绑源文件很有用,因为列表给出了串联顺序。注意:您可以传递与 dependencyTree() 相同的参数

使用的两个参数toList

  • filename包含初始依赖关系的文件的路径,即依赖关系图的入口点。这是由模块使用的filing-cabinet
  • directory所有文件的路径,即解决依赖关系的根目录。该模块也使用此功能filing-cabinet

此构建脚本使用 CommonJS 模块、Node v16.16.0 和 Babel 7.19.3。我确信您可以毫无问题地将其转换为 ES 模块,或者如果您愿意,也可以基于 Promise。

构建.js

const fs = require('node:fs')
const { dirname, resolve } = require('node:path')
const dependencyTree = require('dependency-tree')
const babel = require('@babel/core')

dependencyTree.toList({
  filename: './views/one.js',
  directory: './views'
}).forEach(path => {
  const basepath = path.split('views/')
  const filepath = resolve('./.views', basepath[1])
  const directory = dirname(filepath)

  fs.mkdirSync(directory, { recursive: true })
  fs.writeFileSync(
    filepath,
    babel.transformSync(fs.readFileSync(path).toString()).code
  )
})
Run Code Online (Sandbox Code Playgroud)
node build.js
Run Code Online (Sandbox Code Playgroud)