【问题标题】:Remove TypeScript type annotations and assertions from code base从代码库中删除 TypeScript 类型注释和断言
【发布时间】:2026-01-11 14:50:01
【问题描述】:

考虑到有一个项目需要从 TypeScript 转换为 Babel,文件包含不能被 Babel 忽略的类型信息。

如何以自动方式从整个代码库中剥离 TS 类型注释和断言?

有没有办法将它们转换为Flow(考虑到某些TS类型的功能可以转换而有些不能)?

显然,这不能通过正则表达式获得。

该项目的代码中有很多 TS/ES.next 功能,并且应该是可读和可编辑的,这里不能使用 es6 目标进行编译。

【问题讨论】:

  • 如果你把你的 typescript 目标放到 es6 上,你基本上会在编译时“剥离”类型注释。这能回答你的第一个问题吗?对于你的第二个问题,我不知道。
  • @PelleJacobs 抱歉,应该明确提及这一点:代码应该保持良好的状态。转译会杀死所有格式和 ES.next 功能,并将代码变成 ES6 的蒸汽堆。
  • 嗯。我很确定这是你唯一的选择。恕我直言,编译后的代码相当不错,他们花了相当长的时间使其格式正确,以至于它被用于教授 javascript 代码样式。如果实在不行,就直接在github项目上开一个issue吧。
  • @PelleJacobs 遗憾的是,这不是一个选择。装饰器、异步函数等都被破坏了,类属性上的 JSDoc cmets 被 ES6 目标删除。我想我会打开一个问题,但我很确定它不会在未来几年内获得优先考虑。
  • tsc --target esnext 只会转译装饰器。所有其他语法都将保持不变。

标签: javascript typescript flowtype ecmascript-next


【解决方案1】:

这实际上是一个有趣的问题。我是 Flow 团队的一员,所以我真的很想得到一个好的答案,但现在并不简单。

首先,您可能想问为什么您真的想从 TypeScript 切换到 Flow。对于现有项目,您应该考虑是否值得花时间进行切换。

话虽如此,如果您确实觉得值得,我会描述我认为最好的。

增量迁移

显然停止并重写所有内容是一个坏主意™,将所有内容都扔掉并重新开始将是可悲的。这涉及到我们在 Facebook 构建的几乎所有东西的设计决策,包括 Flow。 Flow 旨在将应用程序逐步迁移到具有静态类型。

但是,从一个静态类型系统迁移到另一个静态类型系统有点不同。实际上可能会更容易一些,因为在构建时考虑了类型。

一次移动一个文件,尽量在某些地方与自己隔绝,这样你就不会被大量工作压得喘不过气来。

拥有良好的 libdefs

Flow 旨在尽可能多地进行推断,但在应用程序中对其有很大帮助的一件事是为您在任何地方使用的库提供出色的定义。

所以我会专注于将 libdefs 迁移到 Flow,要么找到存在的那些,要么编写自己的。如果你想了解更多,我写了一个漂亮的in depth article about it

确保您贡​​献了您编写的任何 libdef back to the community

设置您的构建系统

TypeScript 的编译和类型检查都内置在同一个编译器中。但是,Flow 将它们分开,以便您有多种选择。对于大多数东西,推荐使用 Babel,如果你在 an interactive page for it here 之前从未设置过 Babel。完成后,我还写了this guide about next steps


您在此过程中极有可能会遇到麻烦,请务必告知我们,以便我们为您提供帮助,并确保其他关注者不会遇到同样的困难。

希望这对您有很大帮助。玩得开心:)

【讨论】:

  • 我有一个关于编写 Flow 库定义的问题。 declare 实际上是做什么的?似乎没有必要。不幸的是,没有人在我遇到的 Github 上回答这个问题并提出同样的问题:github.com/facebook/flow/issues/4053 如果我真的不明白我在做什么,我不愿意公开任何事情。我没有找到declare 的文档。
【解决方案2】:

Sucrase typescript transform 允许从代码中剥离 TypeScript 类型并输出 ES.next 代码,而不会丢失格式(cmets 和空格)。

这涵盖了问题的第一部分,不涉及 Flow。

【讨论】:

    【解决方案3】:

    @babel/preset-typescript 完全按照您指定的方式进行操作。

    【讨论】:

      【解决方案4】:

      剥离 TypeScript:

      如果你有一个有效的 TS 项目

      这意味着您拥有所有依赖项和项目类型检查。

      使用tsconfig.json:

      {
        "include": ["./<SOURCE_DIR>"],
        "compilerOptions": {
          "outDir": "./<OUT_DIR>",
          "target": "es2020",
          "module": "es2020",
          "strict": false,
          "esModuleInterop": true,
          "jsx": "preserve",
          "moduleResolution": "node"
        }
      }
      

      然后运行npx tsc -p tsconfig.json

      你得到没有 TypeScript 的 ES6。

      【讨论】: