为什么 JavaScript 可能仍然是你最好的选择。
TypeScript 语言于 2012 年发布。刚发布时只是一个 JavaScript 超集。但几年后,它开始以过度炒作的速度爆炸式地增长。
它确实给 JavaScript 生态系统带来了一些有用的功能。然而,仅凭这些优点就足以让我们 all in Ts 吗?Ts 是否存在一些没人讨论的缺点?你是否应该关心这些缺点?
如果你想在项目中使用 Ts,我建议你阅读我的建议后再重新考虑是否要使用 Ts。本文将列出最值得考虑的 5 个 Ts 的缺点。
1.使你的代码混乱
在 JS 中,通过使用更清晰的参数和方法名称,我们的代码库应该已经是非常明确的了。我们不需要任何虚拟类型检查。
但使用 TypeScript 时,Ts 会导致很多冗余的内容。
下面是一个例子:
const sum = (a, b) => a + b;
如果我们将其移植到 TypeScript,它将变为:
const sum = (a: number, b: number): number => (a + b) as number;
Ts 比 JS 阅读和理解都要困难得多。没有足够的 TypeScript 知识,Ts 将会变得难以理解。Ts 是异类,并且不赏心悦目。(其实我觉得很好看)
这导致了一个结果:开发人员现在突然需要理解一种新的语言。并且在你编写代码时,编辑器将占用更多的 CPU 资源来对代码提供帮助。
2.浏览器支持性差
浏览器并不支持原生的 Ts 代码。虽然微软提出过一个针对的提案,但这个提案仍然在早期阶段,你可以点击这里 查阅
这意味着什么?无论如何我们最后都要运行 JS 代码,那我们花精力去使用 Ts 的目的是什么?我们需要在项目中添加很多额外的步骤,而结果仍然 JS 代码,这个决定看起来十分不理智。
如果微软能将那个提案变成现实,那么这种说法值得参考。尽管如此,我们仍然需要等待浏览器能良好地支持 Ts 代码。
3.非常多的配置选项
在使用 Ts 前,我们需要配置相当多的选项。我们需要掌握tsconfig.json
的使用方法。
运行下面的代码来初始化一个 ts 项目
# install TypeScript globally
# 安装Ts依赖
npm install -g typescript
# init project
# 初始化Ts项目
tsc --init
package.json
中的部分设定:
-
compilerOptions
:最主要的配置选项,包含了代码如何工作的选项。其中包含:格式检查,模块,发行,编辑器支持……这是我们花费最多时间来配置的地方 -
include files
:包含的文件名或者模式数组 -
exclude files
:不包含的文件名或者模式数组
当我们配置完tsconfig
文件,还不能马上运行 Ts 代码。我们需要配置一个 Webpack 加载器来打包我们的 Ts 代码。你会纠结于选择 Babel 还是 ts-loader 来打包你的代码。于是这件事便愈发复杂了。
除此之外,我们还需要不断更新我们的 Ts 代码库。每一个版本都会有大量不同的更新。这意味着我们要花费相当多的时间在这些大约 4 个月就会产生一次的更新上
4.陡峭的学习路线(Steep Learning Curve)
Ts 比 JS 更加复杂,需要花费一些时间来适应和掌握。下面是一些 Ts 的新特新:
-
映射类型
-
元组(Tuples)
-
类型推断(Inference)
-
模板字符串(Template Literals)~(这不是 js 的吗?)~
-
函数重载
-
联合类型(Unions)eg:
number | string
-
泛型(Generics)
Ts 的一些特性比较难以理解。不同于其他特性,它们产生了一些比较奇怪的 JS 代码。比如 enum,JS 里并没有这样的特性。
下面是展示的代码。
enum Status {
Succes,
Error,
Warning,
Info
}
对于 JS 使用者而言,这个特性会花费他们不少时间去掌握。~(我寻思 enum 用得也不多啊)~
此外,Ts 会产生下面的 JS 代码:
var Status;
(function (Status) {
Status[(Status["Succes"] = 0)] = "Succes";
Status[(Status["Error"] = 1)] = "Error";
Status[(Status["Warning"] = 2)] = "Warning";
Status[(Status["Info"] = 3)] = "Info";
})(Status || (Status = {}));
上面的代码看上去有点冗余,我们在写 Ts 时需要注意这些类似的问题。但这增加了我们工作的复杂性。
5.与第三方的兼容性
一些第三方库不完全支持 Ts,有时候是完全不支持,编写者没有理由这么做。但这导致 Ts 的我们会使用未经检查的代码,这破坏了 Ts 的原则。
这还不是最糟的,有时候我们会遇见一些支持但不完全支持 Ts 的库,或者一些前后矛盾的接口。这让我们的工作更加艰难和麻烦。我们该如何相信第三方的 Ts 功能?
幸运的是,我们可以使用 DefinitelyTyped 包社区,这是一个高质量的 Ts 类似的仓库,它可以一定程度上解决这个问题。如果你尝试使用它,你会发现你经常打开 PRs 去解决一些可能发生的问题。
6. 影响开发速度
高效是开发的一个重要方面。Ts 各种问题导致我们背负了一个**“TypeScript 负担”**。这严重影响了我们的开发效率,让我们的开发工作变得更不敏捷和更拘谨。这也是 JS 不使用类型检查的原因。
很多支持者说 Ts 能帮助避免很多恶性 BUG。然而,Ts 给予了any
和Function
这 2 个宽泛的类型,并且你可以使用@ts-ignore
来逃过类型检查。这导致了 Ts 代码不一定那么可信。
那么,如何才能确保我们代码的健壮性,减少 bug 的产生?
只有通过大量的测试,才能让我们的代码在更极端的情况下仍然健壮。
同时,Ts 的编译器也会拖累我们,ESBuild 或者 SWC 能更快地完成这个流程。但是,大多数人都是用 Webpack。我们可以使用 Bable 代替 Webpack 来提升打包速度。但是这个速度是牺牲类型换来的,这会导致在编译时无法报出类型的错误,但这个错误可能在运行出现。
最后
我希望这篇文章能减少你的偏见,Ts 是一个优秀的语言,但是现在被过度炒作了
你可以继续在复杂的项目中使用 Ts,当你的团队也掌握 Ts 时,Ts 可能会展现它的优势。
但是,对于小型的应用(Minimum Viable Product)或项目,我建议你拒绝 Ts。因为随着 DDL 的靠近,一个未被完全证实有用的工具可能会给你的团队造成不小的麻烦。