智能客服
你问我答,随时在线为你解决问题
您当前浏览的3.1/4.0版本文档归档不再维护,推荐您使用最新的HarmonyOS NEXT版本文档。详细请参考文档维护策略变更。
序号 | 规则ID | 描述 | 正例 | 反例 | RuleSet |
|---|---|---|---|---|---|
1 | @typescript-eslint/await-thenable | 如果await一个非Thenable的值,await 会把该值转换为已正常处理的 Promise,然后等待其处理结果。此时await反而会影响代码性能 | await Promise.resolve('value'); const createValue = async () => 'value'; await createValue(); | await 'value'; const createValue = () => 'value'; await createValue(); | recommended |
2 | @typescript-eslint/consistent-type-imports | 如果导入类型(type),将导入类型和导出其他对象分开写 | import type { Foo } from 'Foo'; import type Bar from 'Bar'; type T = Foo; const x: Bar = 1; | import { Foo } from 'Foo'; import Bar from 'Bar'; type T = Foo; const x: Bar = 1; | recommended |
3 | @typescript-eslint/explicit-function-return-type | 声明函数和类方法的返回类型可以使得编译器能够帮助检查返回类型的一致性 | // No return value should be expected (void) function test(): void { return; } // A return value of type number var fn = function (): number { return 1; }; // A return value of type string var arrowFn = (): string => 'test'; class Test { // No return value should be expected (void) method(): void { return; } } | // Should indicate that no value is returned (void) function test() { return; } // Should indicate that a number is returned var fn = function () { return 1; }; // Should indicate that a string is returned var arrowFn = () => 'test'; class Test { // Should indicate that no value is returned (void) method() { return; } } | recommended |
4 | @typescript-eslint/no-dynamic-delete | delete会改变对象的布局,而delete对象的可计算属性会非常危险,而且会大幅约束语言运行时的优化从而影响执行性能 | const container: { [i: string]: number } = { /* ... */ }; // 一定程度也会影响优化性能,但比删除可计算属性好一些。 delete container.aaa; delete container[7]; delete container['-Infinity']; | // Can be replaced with the constant equivalents, such as container.aaa delete container['aaa']; delete container['Infinity']; // Dynamic, difficult-to-reason-about lookups const name = 'name'; delete container[name]; delete container[name.toUpperCase()]; | recommended |
5 | @typescript-eslint/no-for-in-array | for in在语义上原本是用来遍历对象属性,虽然使用它来遍历数组也合法,但是会影响执行性能。禁止使用for in来进行数组访问,一般使用forEach/for of/for(int i;...)来遍历数组 | for (const x in { a: 3, b: 4, c: 5 }) { console.log(x); } | for (const x in [3, 4, 5]) { console.log(x); } | recommended |
6 | @typescript-eslint/no-this-alias | 禁止将This赋值给一个变量,约束This在一个Scope内使用 | setTimeout(() => { this.doWork(); }); | const self = this; setTimeout(function () { self.doWork(); }); | recommended |
7 | @typescript-eslint/no-explicit-any | 不允许定义any类型。它的目的是为了让类型在TS中尽量明确,帮助语言运行时优化 | const age: number = 17; function greet(): string {} function greet(param: Array<string>): string {} | const age: any = 'seventeen'; function greet(): any {} function greet(param: Array<any>): string {} | recommended |
8 | @typescript-eslint/no-unsafe-argument | 不允许使用any作为参数传递 | declare function foo(arg1: string, arg2: number, arg3: string): void; foo('a', 1, 'b'); const tuple1 = ['a', 1, 'b'] as const; foo(...tuple1); | declare function foo(arg1: string, arg2: number, arg3: string): void; const anyTyped = 1 as any; foo(...anyTyped); foo(anyTyped, 1, 'a'); const tuple1 = ['a', anyTyped, 'b'] as const; foo(...tuple1); | recommended |
9 | @typescript-eslint/no-unsafe-assignment | 不允许在赋值中使用any | const x = 1; const x: Set<string> = new Set<string>(); | const x = 1 as any, const x: Set<string> = new Set<any>(); | recommended |
10 | @typescript-eslint/no-unsafe-call | 不允许call类型为any的变量 | declare const typedVar: () => void; declare const typedNested: { prop: { a: () => void } }; typedVar(); typedNested.prop.a(); | declare const anyVar: any; declare const nestedAny: { prop: any }; anyVar(); anyVar.a.b(); nestedAny.prop(); nestedAny.prop['a'](); | recommended |
11 | @typescript-eslint/no-unsafe-member-access | 不允许访问类型为any的对象的成员 | declare const properlyTyped: { prop: { a: string } }; properlyTyped.prop.a; properlyTyped.prop['a']; | declare const anyVar: any; declare const nestedAny: { prop: any }; anyVar.a; anyVar.a.b; nestedAny.prop.a; nestedAny.prop['a']; | recommended |
12 | @typescript-eslint/no-unsafe-return | 不允许声明函数返回值类型为any或者any[] | function foo1() : number { return 1; } | function foo1() { return 1 as any; } | recommended |
13 | @typescript-eslint/adjacent-overload-signatures | 要求重载方法声明必须连续 | export function bar(): void; export function foo(s: string): void; export function foo(n: number): void; export function foo(sn: string | number): void; | export function foo(s: string): void; export function foo(n: number): void; export function bar(): void; export function foo(sn: string | number): void; | all |
14 | @typescript-eslint/array-type | 检查 `T[]` 或 `Array<T>`的使用一致性 | const x: string[] = ['a', 'b']; const y: readonly string[] = ['a', 'b']; | const x: Array<string> = ['a', 'b']; const y: ReadonlyArray<string> = ['a', 'b']; | all |
15 | @typescript-eslint/ban-ts-comment | 禁止在`@ts-<directive>` 注解后添加注释 | if (false) { // Compiler warns about unreachable code error console.log('hello'); } | if (false) { // @ts-ignore: Unreachable code error console.log('hello'); } if (false) { /* @ts-ignore: Unreachable code error */ console.log('hello'); } | all |
16 | @typescript-eslint/ban-tslint-comment | 禁止`// tslint:<rule-flag>`注释 | // This is a comment that just happens to mention tslint /* This is a multiline comment that just happens to mention tslint */ someCode(); // This is a comment that just happens to mention tslint | /* tslint:disable */ /* tslint:enable */ /* tslint:disable:rule1 rule2 rule3... */ /* tslint:enable:rule1 rule2 rule3... */ // tslint:disable-next-line someCode(); // tslint:disable-line // tslint:disable-next-line:rule1 rule2 rule3… | all |
17 | @typescript-eslint/ban-types | 禁用特定类型 | // use lower-case primitives for consistency const str: string = 'foo'; const bool: boolean = true; const num: number = 1; const symb: symbol = Symbol('foo'); const bigInt: bigint = 1n; | // use lower-case primitives for consistency const str: String = 'foo'; const bool: Boolean = true; const num: Number = 1; const symb: Symbol = Symbol('foo'); const bigInt: BigInt = 1n; | all |
18 | @typescript-eslint/class-literal-property-style | 强制类字面量公开类型一致 | class Mx { public readonly myField1 = 1; // not a literal public readonly myField2 = [1, 2, 3]; private readonly ['myField3'] = 'hello world'; public get myField4() { return `hello from ${window.location.href}`; } } | class Mx { public static get myField1() { return 1; } private get ['myField2']() { return 'hello world'; } } | all |
19 | @typescript-eslint/consistent-indexed-object-style | 要求或禁止`Record`类型 | interface Foo { [key: string]: unknown; } type Foo = { [key: string]: unknown; }; | type Foo = Record<string, unknown>; | all |
20 | @typescript-eslint/consistent-type-assertions | 要求使用一致的类型断言 | const x: T = { ... }; const y = { ... } as any; const z = { ... } as unknown; function foo(): T { return { ... }; } | const x = { ... } as T; function foo() { return { ... } as T; } | all |
21 | @typescript-eslint/consistent-type-definitions | 强制类型定义使用一致的`interface` 或 `type` | type T = string; type Foo = string | {}; interface T { x: number; } | type T = { x: number }; | all |
22 | @typescript-eslint/explicit-member-accessibility | 要求类属性或方法使用明确的访问标签 | class Animal { constructor(public animalName: string) {} } | class Animal { constructor(public readonly animalName: string) {} } | all |
23 | @typescript-eslint/explicit-module-boundary-types | 要求导出函数中提供明确的return及参数类型 | // Function is not exported function test() { return; } // A return value of type number export var fn = function (): number { return 1; }; | // Should indicate that no value is returned (void) export function test() { return; } // Should indicate that a number is returned export default function () { return 1; } | recommended |
24 | @typescript-eslint/member-delimiter-style | 要求对interfaces和type字面量提供精确的数字定界符 | interface Foo { name: string; greet(): string; } interface Foo { name: string } | interface Foo { name: string greet(): string } // using incorrect delimiter interface Bar { name: string, greet(): string, } | all |
25 | @typescript-eslint/member-ordering | 要求一致的成员声明顺序 | interface Foo { [Z: string]: any; // -> signature A(): void; // -> method new (); // -> constructor B: string; // -> field } | interface Foo { B: string; // -> field new (); // -> constructor A(): void; // -> method [Z: string]: any; // -> signature } | all |
26 | @typescript-eslint/method-signature-style | 强制使用特定的方法签名语法 | interface T1 { func(arg: string): number; } type T2 = { func(arg: boolean): void; }; | interface T1 { func: (arg: string) => number; } type T2 = { func: (arg: boolean) => void; }; | all |
27 | @typescript-eslint/naming-convention | 强制代码仓使用同样的命名规范 | - | - | all |
28 | @typescript-eslint/no-base-to-string | 要求仅在转换为字符串时在对象上调用 .toString() | // These types all have useful .toString()s 'Text' + true; `Value: ${123}`; `Arrays too: ${[1, 2, 3]}`; (() => {}).toString(); | // Passing an object or class instance to string concatenation: '' + {}; class MyClass {} const value = new MyClass(); value + ''; // Interpolation and manual .toString() calls too: `Value: ${value}`; ({}.toString()); | all |
29 | @typescript-eslint/no-confusing-non-null-assertion | 不允许在可能引发歧义的位置使用非空断言 | interface Foo { bar?: string; num?: number; } const foo: Foo = getFoo(); const isEqualsBar = foo.bar == 'hello'; const isEqualsNum = (1 + foo.num!) == 2; | interface Foo { bar?: string; num?: number; } const foo: Foo = getFoo(); const isEqualsBar = foo.bar! == 'hello'; const isEqualsNum = 1 + foo.num! == 2; | all |
30 | @typescript-eslint/no-confusing-void-expression | void 类型的表达式需出现在语句位置(不可用于赋值、返回等) | // just a regular void function in a statement position alert('Hello, world!'); // this function returns a boolean value so it's ok const response = confirm('Are you sure?'); console.log(confirm('Are you sure?')); | // somebody forgot that `alert` doesn't return anything const response = alert('Are you sure?'); console.log(alert('Are you sure?')); | all |
31 | @typescript-eslint/no-empty-interface | 禁止声明空interface | // an interface with any number of members interface Foo { name: string; } // same as above interface Bar { age: number; } // an interface with more than one supertype // in this case the interface can be used as a replacement of a union type. interface Baz extends Foo, Bar {} | // an empty interface interface Foo {} // an interface with only one supertype (Bar === Foo) interface Bar extends Foo {} // an interface with an empty list of supertypes interface Baz {} | all |
32 | @typescript-eslint/no-extra-non-null-assertion | 不允许多余的非空断言 | const foo: { bar: number } | null = null; const bar = foo!.bar; function foo(bar: number | undefined) { const bar: number = bar!; } | const foo: { bar: number } | null = null; const bar = foo!!!.bar; function foo(bar: number | undefined) { const bar: number = bar!!!; } | all |
33 | @typescript-eslint/no-extraneous-class | 不允许将类用作namespace | export const version = 42; export function isProduction() { return process.env.NODE_ENV === 'production'; } function logHelloWorld() { console.log('Hello, world!'); } | class StaticConstants { static readonly version = 42; static isProduction() { return process.env.NODE_ENV === 'production'; } } class HelloWorldLogger { constructor() { console.log('Hello, world!'); } } | all |
34 | @typescript-eslint/no-floating-promises | 恰当地处理类Promise的语句 | const promise = new Promise((resolve, reject) => resolve('value')); await promise; async function returnsPromise() { return 'value'; } returnsPromise().then( () => {}, () => {}, ); Promise.reject('value').catch(() => {}); Promise.reject('value').finally(() => {}); | const promise = new Promise((resolve, reject) => resolve('value')); promise; async function returnsPromise() { return 'value'; } returnsPromise().then(() => {}); Promise.reject('value').catch(); Promise.reject('value').finally(); | all |
35 | @typescript-eslint/no-implicit-any-catch | 避免catch表达式中变量为隐含的any类型 | try { // ... } catch (e: unknown) { // ... } | try { // ... } catch (e) { // ... } | all |
36 | @typescript-eslint/no-inferrable-types | 不允许对初始化为数字、字符串或布尔值的变量或参数进行显式类型声明 | const a = 10n; const a = BigInt(10); const a = !0; const a = Boolean(null); const a = true; | const a: bigint = 10n; const a: bigint = BigInt(10); const a: boolean = !0; const a: boolean = Boolean(null); const a: boolean = true; | all |
37 | @typescript-eslint/no-invalid-void-type | 禁止在泛型或返回类型之外使用 `void` 类型 | type NoOp = () => void; function noop(): void {} let trulyUndefined = void 0; async function promiseMeSomething(): Promise<void> {} type stillVoid = void | never; | type PossibleValues = string | number | void; type MorePossibleValues = string | ((number & any) | (string | void)); function logSomething(thing: void) {} function printArg<T = void>(arg: T) {} | all |
38 | @typescript-eslint/no-misused-new | 强制new和constructor定义有效 | declare class C { constructor(); } interface I { new (): C; } | declare class C { new(): C; } interface I { new (): I; constructor(): void; } | all |
39 | @typescript-eslint/no-misused-promises | 禁止Promise使用在未设计处理它们的位置 | const promise = Promise.resolve('value'); // Always `await` the Promise in a conditional if (await promise) { // Do something } const val = (await promise) ? 123 : 456; while (await promise) { // Do something } | const promise = Promise.resolve('value'); if (promise) { // Do something } const val = promise ? 123 : 456; while (promise) { // Do something } | all |
40 | @typescript-eslint/no-namespace | 禁用TypeScript namespace关键字 | declare module 'foo' {} | module foo {} namespace foo {} declare module foo {} declare namespace foo {} | all |
41 | @typescript-eslint/no-non-null-asserted-optional-chain | 禁止在可选链式调用中使用非空断言 | foo?.bar; foo?.bar(); | foo?.bar!; foo?.bar()!; | all |
42 | @typescript-eslint/no-non-null-assertion | 禁止使用`!`后缀运算符做非空断言 | interface Example { property?: string; } declare const example: Example; const includesBaz = example.property?.includes('baz') ?? false; | interface Example { property?: string; } declare const example: Example; const includesBaz = example.property!.includes('baz'); | all |
43 | @typescript-eslint/no-require-imports | 禁止调用require方法 | import * as lib1 from 'lib1'; import { lib2 } from 'lib2'; import * as lib3 from 'lib3'; | const lib1 = require('lib1'); const { lib2 } = require('lib2'); import lib3 = require('lib3'); | all |
44 | @typescript-eslint/no-type-alias | 允许或禁止使用type别名 | type Foo = 'a'; type Foo = 'a' | 'b'; type Foo = string; | - | all |
45 | @typescript-eslint/no-unnecessary-boolean-literal-compare | 禁止对布尔型字面量进行非必要的比较 | declare const someCondition: boolean; if (someCondition) { } | declare const someCondition: boolean; if (someCondition === true) { } | all |
46 | @typescript-eslint/no-unnecessary-condition | 禁止条件语句恒为true或false | function head<T>(items: T[]) { // Necessary, since items.length might be 0 if (items.length) { return items[0].toUpperCase(); } } | function head<T>(items: T[]) { // items can never be nullable, so this is unnecessary if (items) { return items[0].toUpperCase(); } } | all |
47 | @typescript-eslint/no-unnecessary-qualifier | 禁止非必要的命名空间引用 | enum A { B, C = B, } namespace A { export type B = number; const x: B = 3; } | enum A { B, C = A.B, } namespace A { export type B = number; const x: A.B = 3; } | all |
48 | @typescript-eslint/no-unnecessary-type-arguments | 禁止使用和默认值相等的泛型 | function f<T = number>() {} f(); f<string>(); | function f<T = number>() {} f<number>(); | all |
49 | @typescript-eslint/no-unnecessary-type-assertion | 禁止使用不改变表达式类型的类型断言 | const foo = <number>3; const foo = 3 as number; | const foo = 3; const bar = foo!; const foo = <3>3; | all |
50 | @typescript-eslint/no-unnecessary-type-constraint | 禁止对泛型做不必要约束 | interface Foo<T> {} type Bar<T> = {}; class Baz<T> { qux<U> { } } | interface FooAny<T extends any> {} type BarAny<T extends any> = {}; class BazAny<T extends any> { quxAny<U extends any>() {} } | recommended |
51 | @typescript-eslint/parameter-properties | 变量的修饰符控制 | class Foo { constructor(name: string) {} } | class Foo { constructor(readonly name: string) {} } class Foo { constructor(private name: string) {} } | all |
52 | @typescript-eslint/prefer-as-const | 强制对字面量类型使用`as const` | let foo = 'bar'; let foo = 'bar' as const; let foo: 'bar' = 'bar' as const; | let bar: 2 = 2; let foo = <'bar'>'bar'; let foo = { bar: 'baz' as 'baz' }; | all |
53 | @typescript-eslint/prefer-enum-initializers | 要求显示初始化每个枚举成员的值 | enum Status { Open = 'Open', Close = 'Close', } enum Direction { Up = 1, Down = 2, } | enum Status { Open = 1, Close, } enum Direction { Up, Down, } | all |
54 | @typescript-eslint/prefer-for-of | 尽可能地使用for…of代替传统的for循环 | declare const array: string[]; for (const x of array) { console.log(x); } for (let i = 0; i < array.length; i++) { // i is used, so for-of could not be used. console.log(i, array[i]); } | declare const array: string[]; for (let i = 0; i < array.length; i++) { console.log(array[i]); } | all |
55 | @typescript-eslint/prefer-function-type | 强制使用函数类型而非带有调用签名的interface | type Example = () => string; function foo(example: () => number): number { return bar(); } | interface Example { (): string; } function foo(example: { (): number }): number { return example(); } | all |
56 | @typescript-eslint/prefer-includes | 强制使用includes方法替代indexOf方法 | str.includes(value); array.includes(value); readonlyArray.includes(value); | str.indexOf(value) !== -1; array.indexOf(value) !== -1; readonlyArray.indexOf(value) === -1; | all |
57 | @typescript-eslint/prefer-literal-enum-member | 要求所有的枚举成员都是字面量 | enum Valid { A, B = 'TestStr', // A regular string C = 4, // A number D = null, E = /some_regex/, } | const str = 'Test'; enum Invalid { A = str, // Variable assignment B = {}, // Object assignment C = `A template literal string`, // Template literal D = new Set(1, 2, 3), // Constructor in assignment E = 2 + 2, // Expression assignment } | recommended |
58 | @typescript-eslint/prefer-namespace-keyword | 要求使用namespace替代module来声明自定义TypeScript模块 | namespace Example {} declare module 'foo' {} | module Example {} | all |
59 | @typescript-eslint/prefer-nullish-coalescing | 强制使用null合并运算符而不是逻辑链接 | const foo: any = 'bar'; foo ?? 'a string'; foo ?? 'a string'; foo ?? 'a string'; foo ?? 'a string'; | const foo: any = 'bar'; foo !== undefined && foo !== null ? foo : 'a string'; foo === undefined || foo === null ? 'a string' : foo; foo == undefined ? 'a string' : foo; foo == null ? 'a string' : foo; | all |
60 | @typescript-eslint/prefer-optional-chain | 强制使用简洁的可选链式调用,而不是拼接逻辑与、否定逻辑或或空对象 | foo?.a?.b?.c; foo?.['a']?.b?.c; foo?.a?.b?.method?.(); | foo && foo.a && foo.a.b && foo.a.b.c; foo && foo['a'] && foo['a'].b && foo['a'].b.c; foo && foo.a && foo.a.b && foo.a.b.method && foo.a.b.method(); | all |
61 | @typescript-eslint/prefer-readonly | 如果私有成员在构造方法外不会被修改,则应被标记为readonly | class Container { // Public members might be modified externally public publicMember: boolean; // Protected members might be modified by child classes protected protectedMember: number; // This is modified later on by the class private modifiedLater = 'unchanged'; public mutate() { this.modifiedLater = 'mutated'; } } | class Container { // These member variables could be marked as readonly private neverModifiedMember = true; private onlyModifiedInConstructor: number; public constructor( onlyModifiedInConstructor: number, // Private parameter properties can also be marked as readonly private neverModifiedParameter: string, ) { this.onlyModifiedInConstructor = onlyModifiedInConstructor; } } | all |
62 | @typescript-eslint/prefer-readonly-parameter-types | 函数参数应该被标记为readonly以防止被输入值意外修改 | function array1(arg: readonly string[]) {} function array2(arg: readonly (readonly string[])[]) {} function array3(arg: readonly [string, number]) {} function array4(arg: readonly [readonly string[], number]) {} | function array1(arg: string[]) {} // array is not readonly function array2(arg: readonly string[][]) {} // array element is not readonly function array3(arg: [string, number]) {} // tuple is not readonly function array4(arg: readonly [string[], number]) {} // tuple element is not readonly | all |
63 | @typescript-eslint/prefer-reduce-type-parameter | 在调用 Array#reduce 而不是强制转换时强制使用类型参数 | [1, 2, 3].reduce<number[]>((arr, num) => arr.concat(num * 2), []); ['a', 'b'].reduce<Record<string, boolean>>( (accum, name) => ({ ...accum, [name]: true, }), {}, ); | [1, 2, 3].reduce((arr, num) => arr.concat(num * 2), [] as number[]); ['a', 'b'].reduce( (accum, name) => ({ ...accum, [name]: true, }), {} as Record<string, boolean>, ); | all |
64 | @typescript-eslint/prefer-regexp-exec | 如果未提供全局标记,强制使用RegExp#exec替代String#match | /thing/.exec('something'); 'some things are just things'.match(/thing/g); const text = 'something'; const search = /thing/; search.exec(text); | something'.match(/thing/); 'some things are just things'.match(/thing/); const text = 'something'; const search = /thing/; text.match(search); | all |
65 | @typescript-eslint/prefer-string-starts-ends-with | 强制使用String#startsWith和String#endsWith替代其它的用于检测子字符串的判同方法 | declare const foo: string; // starts with foo.startsWith('bar'); // ends with foo.endsWith('bar'); | declare const foo: string; // starts with foo[0] === 'b'; foo.charAt(0) === 'b'; foo.indexOf('bar') === 0; foo.slice(0, 3) === 'bar'; foo.substring(0, 3) === 'bar'; foo.match(/^bar/) != null; /^bar/.test(foo); // ends with foo[foo.length - 1] === 'b'; foo.charAt(foo.length - 1) === 'b'; foo.lastIndexOf('bar') === foo.length - 3; foo.slice(-3) === 'bar'; foo.substring(foo.length - 3) === 'bar'; foo.match(/bar$/) != null; /bar$/.test(foo); | all |
66 | @typescript-eslint/prefer-ts-expect-error | 强制使用@ts-expect-error替代@ts-ignore | // @ts-expect-error const str: string = 1; /** * Explaining comment * * @ts-expect-error */ const multiLine: number = 'value'; /** @ts-expect-error */ const block: string = 1; const isOptionEnabled = (key: string): boolean => { // @ts-expect-error: if key isn't in globalOptions it'll be undefined which is false return !!globalOptions[key]; }; | // @ts-ignore const str: string = 1; /** * Explaining comment * * @ts-ignore */ const multiLine: number = 'value'; /** @ts-ignore */ const block: string = 1; const isOptionEnabled = (key: string): boolean => { // @ts-ignore: if key isn't in globalOptions it'll be undefined which is false return !!globalOptions[key]; }; | all |
67 | @typescript-eslint/promise-function-async | 任何返回Promise的函数或方法都要添加async标记 | const arrowFunctionReturnsPromise = async () => Promise.resolve('value'); async function functionReturnsPromise() { return Promise.resolve('value'); } | const arrowFunctionReturnsPromise = () => Promise.resolve('value'); function functionReturnsPromise() { return Promise.resolve('value'); } | all |
68 | @typescript-eslint/require-array-sort-compare | 要求Array#sort调用必须提供一个compareFunction | const array: any[]; const userDefinedType: { sort(): void }; array.sort((a, b) => a - b); array.sort((a, b) => a.localeCompare(b)); userDefinedType.sort(); | const array: any[]; const stringArray: string[]; array.sort(); // String arrays should be sorted using `String#localeCompare`. stringArray.sort(); | all |
69 | @typescript-eslint/restrict-plus-operands | 要求两个加法操作数的类型相同,且必须是“bigint”、“number”或“string” | var foo = parseInt('5.5', 10) + 10; var foo = 1n + 1n; | var foo = '5.5' + 5; var foo = 1n + 1; | all |
70 | @typescript-eslint/restrict-template-expressions | 强制模板字面量表达式为string类型 | const arg = 'foo'; const msg1 = `arg = ${arg}`; const msg2 = `arg = ${arg || 'default'}`; const stringWithKindProp: string & { _kind?: 'MyString' } = 'foo'; const msg3 = `stringWithKindProp = ${stringWithKindProp}`; | const arg1 = [1, 2]; const msg1 = `arg1 = ${arg1}`; const arg2 = { name: 'Foo' }; const msg2 = `arg2 = ${arg2 || null}`; | all |
71 | @typescript-eslint/strict-boolean-expressions | 布尔表达式中禁用特殊类型 | // Using logical operator short-circuiting is allowed const Component = () => { const entry = map.get('foo') || {}; return entry && <p>Name: {entry.name}</p>; }; // nullable values should be checked explicitly against null or undefined let num: number | undefined = 0; if (num != null) { console.log('num is defined'); } | // nullable numbers are considered unsafe by default let num: number | undefined = 0; if (num) { console.log('num is defined'); } // nullable strings are considered unsafe by default let str: string | null = null; if (!str) { console.log('str is empty'); } | all |
72 | @typescript-eslint/switch-exhaustiveness-check | 要求switch-case语句以union类型结束 | type Day = | 'Monday' | 'Tuesday' | 'Wednesday' | 'Thursday' | 'Friday' | 'Saturday' | 'Sunday'; const day = 'Monday' as Day; let result = 0; switch (day) { case 'Monday': result = 1; break; default: result = 42; } | type Day = | 'Monday' | 'Tuesday' | 'Wednesday' | 'Thursday' | 'Friday' | 'Saturday' | 'Sunday'; const day = 'Monday' as Day; let result = 0; switch (day) { case 'Monday': result = 1; break; } | all |
73 | @typescript-eslint/triple-slash-reference | 禁止某些支持 ES6 样式导入声明的三重斜杠指令 | - | /// <reference path="foo" /> /// <reference types="bar" /> /// <reference lib="baz" /> | all |
74 | @typescript-eslint/type-annotation-spacing | 类型注解需保持前后间距一致 | let foo: string = "bar"; function foo(): string {} class Foo { name: string; } type Foo = () => {}; | let foo:string = "bar"; let foo :string = "bar"; let foo : string = "bar"; function foo():string {} function foo() :string {} function foo() : string {} | all |
75 | @typescript-eslint/typedef | 要求在特定位置使用类型注解 | const [a]: number[] = [1]; const [b]: [number] = [2]; const [c, d]: [boolean, string] = [true, 'text']; | const [a] = [1]; const [b, c] = [1, 2]; | all |
76 | @typescript-eslint/unbound-method | 强制未绑定方法在其预期范围内被调用 | class MyClass { public logUnbound(): void { console.log(this); } public logBound = () => console.log(this); } const instance = new MyClass(); // logBound will always be bound with the correct scope const { logBound } = instance; logBound(); // .bind and lambdas will also add a correct scope const dotBindLog = instance.logBound.bind(instance); const innerLog = () => instance.logBound(); | class MyClass { public log(): void { console.log(this); } } const instance = new MyClass(); // This logs the global scope (`window`/`global`), not the class instance const myLog = instance.log; myLog(); // This log might later be called with an incorrect scope const { log } = instance; | all |
77 | @typescript-eslint/unified-signatures | 禁止两个可以通过union或可选参数合二为一的重载 | function x(x: number | string): void; function y(...x: number[]): void; | function x(x: number): void; function x(x: string): void; function y(): void; function y(...x: number[]): void; | all |
78 | @typescript-eslint/brace-style | 大括号风格 | if (foo) { bar(); } else { baz(); } | if (foo) { bar(); } else { baz(); } | all |
79 | @typescript-eslint/comma-dangle | 逗号风格 | var foo = { bar: "baz", qux: "quux" }; | foo({ bar: "baz", qux: "quux", }); | all |
80 | @typescript-eslint/comma-spacing | 逗号前后空格 | var foo = 1, bar = 2 , baz = 3; var arr = [1, 2]; var arr = [1,, 3] var obj = {"foo": "bar", "baz": "qur"}; | var foo = 1 ,bar = 2; var arr = [1 , 2]; var obj = {"foo": "bar" ,"baz": "qur"}; | all |
81 | @typescript-eslint/default-param-last | 缺省参数放在最后 | function f(a = 0) {} function f(a: number, b = 0) {} function f(a: number, b?: number) {} function f(a: number, b?: number, c = 0) {} | function f(a = 0, b: number) {} function f(a: number, b = 0, c: number) {} function f(a: number, b?: number, c: number) {} | all |
82 | @typescript-eslint/dot-notation | 强制使用点符号访问对象属性 | var x = foo.bar; | var x = foo["bar"]; | all |
83 | @typescript-eslint/func-call-spacing | 方法调用时方法名和括号之间的空格 | fn(); | fn (); fn (); | all |
84 | @typescript-eslint/init-declarations | 变量声明时初始化 | function foo() { var bar = 1; let baz = 2; const qux = 3; } | function foo() { var bar; let baz; } | all |
85 | @typescript-eslint/keyword-spacing | 关键字前后的空格 | if (foo) { //... } else if (bar) { //... } else { //... } | if (foo) { //... }else if (bar) { //... }else { //... } | all |
86 | @typescript-eslint/lines-between-class-members | 类成员之间使用空行分隔 | class MyClass { x; foo() { //... } bar() { //... } } | class MyClass { x; foo() { //... } bar() { //... } } | all |
87 | @typescript-eslint/no-array-constructor | 不要使用原始的Array构造方法(要带泛型) | Array<number>(0, 1, 2); new Array<Foo>(x, y, z); Array(500); new Array(someOtherArray.length); | Array(0, 1, 2); new Array(0, 1, 2); | all |
88 | @typescript-eslint/no-dupe-class-members | 重复的类成员声明(后面的声明会覆盖前面的) | class Foo { bar() { } qux() { } } | class Foo { bar() { } bar() { } } | all |
89 | @typescript-eslint/no-duplicate-imports | 同一个模块多次import | import { AValue, type AType, type BType } from './mama-mia' | import { AValue, type AType } from './mama-mia' import type { BType } from './mama-mia' | all |
90 | @typescript-eslint/no-empty-function | 空方法体 | function foo() { // do nothing. } var foo = function() { // any clear comments. }; var foo = () => { bar(); }; | function foo() {} var foo = function() {}; var foo = () => {}; | all |
91 | @typescript-eslint/no-extra-parens | 无额外的运算符优先级括号 | (0).toString(); ({}.toString.call()); (function(){}) ? a() : b(); | a = (b * c); (a * b) + c; | all |
92 | @typescript-eslint/no-extra-semi | 无多余的分号 | var x = 5; function foo() { // code } | var x = 5;; function foo() { // code }; | all |
93 | @typescript-eslint/no-implied-eval | 避免隐含的eval表达式 | setTimeout(function () { alert('Hi!'); }, 100); setInterval(function () { alert('Hi!'); }, 100); | setTimeout('alert(`Hi!`);', 100); setInterval('alert(`Hi!`);', 100); | all |
94 | @typescript-eslint/no-invalid-this | 不要编写无效的this表达式 | this.a = 0; baz(() => this); function Foo() { // OK, this is in a legacy style constructor. this.a = 0; baz(() => this); } | function foo() { this.a = 0; baz(() => this); } var foo = function() { this.a = 0; baz(() => this); }; | all |
95 | @typescript-eslint/no-loop-func | 不要在循环体中重复创建函数 | var a = function() {}; for (var i=10; i; i--) { a(); } | for (var i=10; i; i--) { (function() { return i; })(); } while(i) { var a = function() { return i; }; a(); } | all |
96 | @typescript-eslint/no-loss-of-precision | 避免数值精度丢失 | const x = 12345 const x = 123.456 const x = 123e34 | const x = 9007199254740993 const x = 5123000000000000000000000000001 const x = 1230000000000000000000000.0 | all |
97 | @typescript-eslint/no-magic-numbers | 避免使用魔鬼数字 | var TAX = 0.25; var dutyFreePrice = 100, finalPrice = dutyFreePrice + (dutyFreePrice * TAX); | var dutyFreePrice = 100, finalPrice = dutyFreePrice + (dutyFreePrice * 0.25); | all |
98 | @typescript-eslint/no-redeclare | 避免重复声明 | var a = 3; a = 10; | var a = 3; var a = 10; | all |
99 | @typescript-eslint/no-shadow | 避免变量名隐藏 | var a = 3; function b() { var b = 10; } | var a = 3; function b() { var a = 10; } | all |
100 | @typescript-eslint/no-throw-literal | 不要throw字面常量 | throw new Error(); throw new Error("error"); const e = new Error("error"); throw e; | throw 'error'; throw 0; throw undefined; | all |
101 | @typescript-eslint/no-unused-expressions | 避免不可达的表达式 | {} {myLabel: someVar} function namedFunctionDeclaration () {} | 0 if(0) 0 {0} f(0), {} | all |
102 | @typescript-eslint/no-unused-vars | 避免声明后又不使用的变量 | var x = 10; alert(x); | some_unused_var = 42; var x; | all |
103 | @typescript-eslint/no-use-before-define | 不要在变量定义前使用它们 | var a; a = 10; alert(a); function f() {} f(1); | alert(a); var a = 10; f(); function f() {} | all |
104 | @typescript-eslint/no-useless-constructor | 不要定义无用的构造方法 | class A { } class A { constructor () { doSomething(); } } class B extends A { constructor() { super('foo'); } } | class A { constructor () { } } class B extends A { constructor (...args) { super(...args); } } | all |
105 | @typescript-eslint/quotes | 引号控制:字符串需使用双引号 | var double = "double"; var unescaped = "a string containing 'single' quotes"; | var single = 'single'; var backtick = `back${x}tick`; | all |
106 | @typescript-eslint/require-await | 避免async修饰的方法中缺失await表达式 | async function foo() { await doSomething(); } bar(async () => { await doSomething(); }); | async function foo() { doSomething(); } bar(async () => { doSomething(); }); | all |
107 | @typescript-eslint/return-await | 避免使用非必须的return await | async function foo() { return bar(); } async function foo() { await bar(); return; } | async function foo() { return await bar(); } | all |
108 | @typescript-eslint/semi | 分号控制 | var name = "ESLint"; class Foo { bar = 1; } | var name = "ESLint" class Foo { bar = 1 } | all |
109 | @typescript-eslint/space-before-function-paren | 方法/函数声明时名称和括号间空格控制 | function foo() { // ... } | function foo () { // ... } | all |
110 | @typescript-eslint/space-infix-ops | 运算符前后空格控制 | a + b a + b a ? b : c | a+b a+ b a +b a?b:c | all |