TypeScript 声明文件
TypeScript 的一个核心优势是它能够与现有的 JavaScript 库和代码无缝协作。然而,标准的 JavaScript 文件(.js)本身不包含类型信息。为了让 TypeScript 编译器理解这些 JavaScript 库的类型、函数签名和对象形状,我们使用声明文件(Declaration Files)。
声明文件以 .d.ts 为扩展名,它们不包含任何实现代码(函数体、变量的初始值等),只包含类型定义。
为什么需要声明文件?
当你使用一个流行的 JavaScript 库(如 jQuery, Lodash, React)时,你希望在 TypeScript 代码中调用它提供的函数时,能获得类型检查和智能自动补全。声明文件就是提供这些类型信息的桥梁。
没有声明文件的情况:
有声明文件的情况:
如何获取声明文件?
对于绝大多数流行的 JavaScript 库,你不需要手动编写声明文件。社区已经为我们做好了这项工作。
1. 库自带声明文件
许多现代的库在发布时就已经包含了它们自己的 .d.ts 声明文件。当你通过 npm 安装这些库时,声明文件会自动被 TypeScript 识别。
2. DefinitelyTyped 项目
对于那些本身不包含类型声明的 JavaScript 库,有一个名为 DefinitelyTyped 的庞大社区项目,它为成千上万的库提供了高质量的声明文件。
这些声明文件都发布在 npm 的 @types scope 下。你只需要安装对应的 @types 包即可。
例如,要为 lodash 库安装声明文件,你只需运行:
安装完成后,你就可以在 TypeScript 项目中像使用原生 TypeScript 库一样使用 lodash 了。
编写你自己的声明文件
在某些情况下,你可能需要为你自己的 JavaScript 代码或一个没有类型定义的第三方库编写声明文件。
declare 关键字
declare 关键字用于告诉 TypeScript 某个变量、函数或模块是存在的,并且有特定的类型,但它的具体实现是在其他地方(通常是一个 .js 文件)。
声明一个全局变量:
声明一个模块:
声明文件结构
- 全局声明: 如果你的 JavaScript 代码是在全局作用域中运行(例如通过
<script>标签引入),你可以直接在.d.ts文件中使用declare var,declare function等。 - 模块化声明: 如果你的 JavaScript 代码是一个模块,你应该使用
declare module 'module-name' { ... }的语法。
编写高质量的声明文件可能很复杂,需要对 TypeScript 的类型系统有深入的理解。但对于大多数开发者来说,主要是消费(而不是创建)声明文件。
tsconfig.json 中的相关配置
"noImplicitAny": true: 这是一个推荐开启的选项。当它为true时,如果 TypeScript 无法推断一个变量的类型并且没有对应的声明文件,它会报错,而不是隐式地将其视为any类型。这可以帮助你发现项目中缺少类型定义的地方。"typeRoots"和"types": 这些选项可以让你控制编译器去哪里查找声明文件,通常情况下你不需要手动配置它们。