2019-10-28
可选链 Optional Chaining
// 之前
if (foo && foo.bar && foo.bar.baz) {
// ...
}
// 之后
if (foo?.bar?.baz) {
// ...
}
空值合并 Nullish Coalescing
// 之前
let x = (foo !== null && foo !== undefined) ?
foo :
bar();
// 之后
let x = foo ?? bar();
断言函数 Assertion Functions
当有一些不期望的情况发生时,某些特定的函数会将错误抛出。
function yell(str) {
assert(typeof str === "string");
return str.toUppercase();
// ~~~~~~~~~~~
// error: Property 'toUppercase' does not exist on type 'string'.
// Did you mean 'toUpperCase'?
}
function assert(condition: any, msg?: string): asserts condition {
if (!condition) {
throw new AssertionError(msg)
}
}
更好地支持 never
-Returning Functions
现在,当调用这些返回 never 的函数时,TypeScript 会识别出它们会影响控制流图,并说明原因。
function dispatch(x: string | number): SomeType {
if (typeof x === "string") {
return doThingWithString(x);
}
else if (typeof x === "number") {
return doThingWithNumber(x);
}
process.exit(1);
}
递归类型别名 Recursive Type Aliases
无需辅助接口也可进行重写。
type Json =
| string
| number
| boolean
| null
| { [property: string]: Json }
| Json[];
--declaration 和 --allowJs
允许 --allowJs 和 --declaration 混用
/**
* @callback Job
* @returns {void}
*/
/** Queues work */
export class Worker {
constructor(maxDepth = 10) {
this.started = false;
this.depthLimit = maxDepth;
/**
* NOTE: queued jobs may add more items to queue
* @type {Job[]}
*/
this.queue = [];
}
/**
* Adds a work item to the queue
* @param {Job} work
*/
push(work) {
if (this.queue.length + 1 > this.depthLimit) throw new Error("Queue full!");
this.queue.push(work);
}
/**
* Starts the queue if it has not yet started
*/
start() {
if (this.started) return false;
this.started = true;
while (this.queue.length) {
/** @type {Job} */(this.queue.shift())();
}
return true;
}
}
以上文件可自动生成 d.ts
/**
* @callback Job
* @returns {void}
*/
/** Queues work */
export class Worker {
constructor(maxDepth?: number);
started: boolean;
depthLimit: number;
/**
* NOTE: queued jobs may add more items to queue
* @type {Job[]}
*/
queue: Job[];
/**
* Adds a work item to the queue
* @param {Job} work
*/
push(work: Job): void;
/**
* Starts the queue if it has not yet started
*/
start(): boolean;
}
export type Job = () => void;
依赖的自动更新构建
打开的项目包含依赖时,TypeScript 将自动使用源 .ts/.tsx 文件进行替代。
检查未调用函数
interface User {
isAdministrator(): boolean;
notify(): void;
doNotDisturb?(): boolean;
}
// later...
// Broken code, do not use!
function doAdminThing(user: User) {
// oops!
if (user.isAdministrator) {
// ~~~~~~~~~~~~~~~~~~~~
// error! This condition will always return true since the function is always defined.
// Did you mean to call it instead?
sudo();
editTheConfiguration();
}
else {
throw new AccessDeniedError("User is not an admin");
}
}
TypeScript 文件中的 @ts-nocheck
允许我们在 TypeScript 文件的顶部添加 // @ts-nocheck
注释以禁用语义检查
重大更改
更新 lib.dom.d.ts 中的类型
函数真实性检查
if
条件下对函数类型进行检查时,只有需满足以下任意条件才不会抛错:
- 检查值来自可选属性
- strictNullChecks 已禁用
- 该函数稍后在
if
的正文中调用
本地和导入的类型声明现在会冲突
正确识别重复标识符的错误。
API 更改
为了支持前文所述的递归类型别名模式,我们已从 TypeReference
接口中删除了 typeArguments
属性。用户应该在 TypeChecker
实例上使用 getTypeArguments
函数。