Skip to content
On this page

TypeScript

tsconfig.json

files、include、exclude

includeexclude通过blob规则指定tsc编译识别哪些文件,默认情况下,会包含tsconfig.json同级目录下的所有.ts.d.ts.tsx类型的文件;

files用于指定相对路径/绝对路径的文件,且一旦指定了,就不会像include那样被exclude排除掉;

默认情况下,exclude会排除node_modulesbower_componentsjspm_packages<outdir>

@types、typeRoots、types

默认所有可见的@types包会在编译过程中被包含进来; node_modules/@types 文件夹下以及它们子文件夹下的所有包都是可见的;

如果指定了 typeRoots,只有 typeRoots 下面的包才会被包含进来;

如果指定了types,只有被列出来的包才会被包含进来;

其中,types优先于typeRoots

注意点

要发布@type的包,需要到DefinitelyTyped仓库下 fork 再提 PR;当然,你也可以为自己使用的 ts 库定义好类型,并用typeRoots显式指定引入;

如果是自己开发的 ts 库,在编译成 js 之后,可以在tsconfig.json指定compilerOptions.declaration来生成.d.ts声明文件,并在package.json中的types指定声明文件的路径;

node_modules/typescript/lib下,包含了各版本 ESMA 常规 API 的 ts 内置声明,可以显式的在compilerOptions.lib中指定引入,但是 node 是没有对应的标准实现的,所以需要引入具体的声明,即@types/node

extends

使用extends来继承另外的tsconfig.json配置,这在Monorepo中比较常见,或者是项目中引用 npm 包定义好的配置;

ts 模块

ts 实现的模块跟 js 的模块实现进程类型,从基础的namespace=>module=>es module

namespace Guang {
  export interface Person {
    name: string;
    age?: number;
  }

  const name = "guang";
  const age = 20;

  export const guang: Person = {
    name,
    age,
  };
  export function add(a: number, b: number): number {
    return a + b;
  }
}

modulenamespace没有本质上的区别,其经过编译后,源代码基本一致,只不过module后面常接路径,而namespace接命名空间;

再后来的es module中,建议使用exportexport default来进行导入导出,还新增了import type ** from '**'的导入语法,现在声明模块不推荐使用 namespace、module,建议直接使用es module

有了 es module 之后,TS 有了一个单独的设计:

在 dts 文件中,如果没有 import、export 语法,那所有的类型声明都是全局的,否则是模块内的。

某些情况下,我们引入 npm 包中的类型定义(命名空间),进行全局的类型扩展,此时应该使用declare global

import type { VNode } from "vue";

declare global {
  namespace JSX {
    interface Element extends VNode {}
  }
}

使用<references path="" />来引入模块,而不影响全局声明定义;

参考文献

TypeScript 中文网

TypeScript 深水区:3 种类型来源和 3 种模块语法