Skip to content

Latest commit

 

History

History
1244 lines (843 loc) · 18.1 KB

typescript.md

File metadata and controls

1244 lines (843 loc) · 18.1 KB

Typescript

Require that member overloads be consecutive (adjacent-overload-signatures from TSLint)

✅ Enabled (error)

// Bad
/*
interface IFoo {
	foo(s: string): void;
	foo(n: number): void;
	bar(): void;
	foo(sn: string | number): void;
}
*/
// Good
interface IFoo {
	foo(sn: string | number): void;
	foo(s: string): void;
	foo(n: number): void;
	bar(): void;
}

Requires using either T[] or Array for arrays (array-type)

✅ Enabled (error)

// Bad
/*
(async () => {
	type A = Array<string>;
})();
*/
// Good
(async () => {
	type A = string[];
})();

Bans “// @ts-ignore” comments from being used (ban-ts-ignore)

✅ Enabled (error)

// Bad
/*
(() => {
	if (false) {
		// @ts-ignore
		console.log('hello');
	}
})();
*/

✅ Enabled (error)

// Bad
/*
(() => {
	const a: String = 'a';
	const b: Number = 1;
})();
*/
// Good
(() => {
	const a: string = 'a';
	const b: number = 1;
})();

✅ Enabled (error)

// Bad
/*
import { no_camelcased } from 'eslint';

(() => {
	no_camelcased();
	const my_favorite_color = '#112C85';
	console.log(my_favorite_color);
})();
*/
// Good
import { no_camelcased as noCamelcased } from 'eslint';

(() => {
	noCamelcased();
	const myFavoriteColor = '#112C85';
	console.log(myFavoriteColor);
})();

✅ Enabled (error)

// Bad
/*
class invalidClassName {}
class Another_Invalid_Class_Name {}
const bar = class invalidName {};
interface someInterface {}
*/
// Good
class ValidClassName {}
class AnotherValidClassName {}
const bar = class ValidName {};
interface ISomeInterface {
	name: string;
}

❌ Disabled

// Good
// Should indicate that no value is returned (void)
function test() {
	return;
}

// Should indicate that a number is returned
const fn = function () {
	return 1;
};

// Should indicate that a string is returned
const arrowFn = () => 'test';

class Test {
	// Should indicate that no value is returned (void)
	public method() {
		return;
	}
}

✅ Enabled (error)

// Bad
/*
class Animal {
	constructor(name) {
		this.animalName = name;
	}
	animalName: string;
	get name(): string {
		return this.animalName;
	}
	set name(value: string) {
		this.animalName = value;
	}
	walk() {
		// method
	}
}
*/
// Good
class Animal {
	private _animalName: string;
	public constructor(name: string) {
		this._animalName = name;
	}
	public get name(): string {
		return this._animalName;
	}
	public set name(value: string) {
		this._animalName = value;
	}
	public walk() {
		// method
	}
}

✅ Enabled (error)

// Bad
/*
(() => {
	type ReadOnly<SomeType extends object> = {
		readonly [TKey in keyof SomeType]: SomeType[TKey]
	};
})();
*/
// Good
(() => {
	type IReadOnly<TSomeType extends object> = {
		readonly [TKey in keyof TSomeType]: TSomeType[TKey]
	};
})();

✅ Enabled (error)

// Bad
/*
type ReadOnly<SomeType extends object> = {
	readonly [TKey in keyof SomeType]: SomeType[TKey]
};
*/
// Good
type ReadOnly<TSomeType extends object> = {
	readonly [TKey in keyof TSomeType]: TSomeType[TKey]
};

✅ Enabled (error)

// Bad
/*
interface Animal {
	name: string;
}
*/
// Good
interface IAnimal {
	name: string;
}

✅ Enabled (error)

// Bad
/*
interface IFoo {
	name: string,
	greet(): void,
}
*/
// Good
interface IFoo {
	name: string;
	greet(): void;
}

✅ Enabled (error)

// Bad
/*
class HappyClass {
	private foo: string;
	private bar = 123;
	public _fizz() {}
}
*/
// Good
class HappyClass {
	private _foo: string;
	private _bar = 123;
	public fizz() {}
}

✅ Enabled (error)

// Bad
/*
class Foo {
	private _c: string; // -> field
	protected static e: string; // -> field
	public d: string; // -> field

	public static a(): void {} // -> method
	public b(): void {} // -> method

	public constructor() {
		console.log('constructor');
	} // -> constructor
}
*/
// Good
class Foo {
	protected static e: string; // -> field
	public d: string; // -> field
	private _c: string; // -> field

	public constructor() {
		console.log('constructor');
	} // -> constructor

	public static a(): void {} // -> method
	public b(): void {} // -> method
}

✅ Enabled (error)

// Bad
/*
(() => {
	type Foo = object;
	const foo = <Foo>{};
}
*/
// Good
(() => {
	type Foo = object;
	const foo: Foo = {};
})();

✅ Enabled (error)

// Bad
/*
(async () => {
	const arr1 = Array(0, 1, 2);
	const arr2 = new Array(0, 1, 2);
})();
*/
// Good
(async () => {
	const arr1 = Array<number>(0, 1, 2);
	const arr2 = new Array<number>(0, 1, 2);

	const arr3 = Array(500);
	const arr4 = new Array(arr1.length);
})();

✅ Enabled (error)

// Bad
/*
(async () => {
	// an empty interface
	interface IFoo {}

	// an interface with only one supertype (Bar === Foo)
	interface IBar extends IFoo {}

	// an interface with an empty list of supertypes
	interface IBaz {}
})();
*/
// Good
(async () => {
	interface IFoo {
		name: string;
	}
	interface IBar extends IFoo {
		email: string;
	}
	interface IBaz {
		name: string;
	}
})();

❌ Disabled

// Bad
/*
const age: any = 'seventeen';
*/
// Good
// not that good but okay in this configuration
const age: any = 'seventeen';

✅ Enabled (error)

// Bad
/*
class ConstructorOnly {
	public constructor() {
		console.log('constructor');
	}
}
*/
// Good
class ConstructorOnly {
	private _version: string = '1.1.0'
	public constructor() {
		console.log(`constructor ${this._version}`);
	}
}

✅ Enabled (error)

// Bad
/*
for (const x in [3, 4, 5]) {
	console.log(x);
}
*/
// Good
// still not okay because not allowed by this rules: no-restricted-syntax, guard-for-in
for (const x in { a: 3, b: 4, c: 5 }) {
	console.log(x);
}

✅ Enabled (error)

// Bad
/*
(async () => {
	const foo: number = 5;
	const bar: boolean = true;
	const baz: string = 'str';
})();
*/
// Good
(async () => {
	const foo = 5;
	const bar = true;
	const baz = 'str';
})();

✅ Enabled (error)

// Bad
/*
(async () => {
	class C {
		new(): C;
	}

	interface IFoo {
		new (): IFoo;
		constructor(): void;
	}
})();
*/
// Good
(async () => {
	class C {
		public constructor() {}
	}
	interface IFoo {
		new (): C;
	}
})();

✅ Enabled (error)

// Bad
/*
module foo {}
namespace foo {}
declare module foo {}
declare namespace foo {}
*/
// Good
declare module 'foo' {}

✅ Enabled (error)

// Bad
/*
(() => {
	interface IFoo {
		bar?: string;
	}

	const foo: IFoo = { bar: 'bar' };
	const includesBaz: boolean = foo.bar!.includes('baz');
})();
*/
// Good
(() => {
	interface IFoo {
		bar?: string;
	}

	const foo: IFoo = { bar: 'baz' };
	const includesBaz: boolean = (foo.bar || '').includes('baz');
})();

✅ Enabled (error)

// Bad
/*
(() => {
	interface ITest {
		name: string;
	}
	const x = { name: 'test' } as ITest;
})();
*/
// Good
(() => {
	interface ITest {
		name: string;
	}
	const x: ITest = { name: 'test' };
})();

✅ Enabled (error)

// Bad
/*
(() => {
	class Foo {
		constructor(readonly name: string) {}
	}
	class Foo {
		constructor(private name: string) {}
	}
	class Foo {
		constructor(protected name: string) {}
	}
	class Foo {
		constructor(public name: string) {}
	}
})();
*/
// Good
(() => {
	class Foo {
		constructor(name: string) {}
	}
})();

✅ Enabled (error)

// Bad
/*
const eslint = require('eslint');
*/
// Good
import eslint from 'eslint';

❌ Disabled

// Bad
/*
(() => {
	const self = this;

	setTimeout(() => {
		self.doWork();
	});
})();
*/
// Good
(() => {
	// already covered by consistent-this
	const _this = this;

	setTimeout(() => {
		_this.doWork();
	});
})();

❌ Disabled

// Good
(() => {
	/// <reference path="../../../../node_modules/@types/react/index.d.ts" />
})();

❌ Disabled

// Good
(() => {
	// primitives
	type Foo = 'a' | 'b';

	type Foo2 = string;

	type Foo3 = string[];

	// reference types
	interface IBar {}
	class Baz implements IBar {}

	type Foo5 = IBar & Baz;
})();

✅ Enabled (error)

// Bad
/*
namespace A {
	export type B = number;
	const x: A.B = 3;
}
*/
// Good
namespace X {
	export type B = number;
}
namespace Y {
	export const x: X.B = 3;
}

✅ Enabled (error)

// Bad
/*
(() => {
	function foo(x: number): number {
		return x!; // unnecessary non-null
	}
})();
*/
// Good
(() => {
	function foo(x: number | undefined): number {
		return x!;
	}
})();

✅ Enabled (error)

// Bad
/*
// Write-only variables are not considered as used.
let y = 10;
y = 5;

// A read for a modification of itself is not considered as used.
let z = 0;
z = z + 1;
*/
// Good
// Write-only variables are not considered as used.
let y = 10;
y = 5;

// A read for a modification of itself is not considered as used.
let z = 0;
z = z + y;

console.log(z);

❌ Disabled

// Bad
/*
(() => {
	alert(a);
	const a = 10;
})();
*/
// Good
(() => {
	const a = 10;
	alert(a);
})();

✅ Enabled (error)

// Bad
/*
(() => {
	var foo1 = require('foo');
	const foo2 = require('foo');
	let foo3 = require('foo');
})();
*/
// Good
import eslint from 'eslint';

✅ Enabled (error)

// Bad
/*
(() => {
	interface IFoo {
		(): string;
	}

	function foo(bar: { (): number }): number {
		return bar();
	}

	interface IFoo2 extends Function {
		(): void;
	}
})();
*/
// Good
(() => {
	interface IFoo {
		bar: number;
		(): void;
	}

	function foo(bar: { baz: number;(): string }): string {
		return bar();
	}

	interface IFoo2 {
		bar: string;
	}
	interface IBar extends IFoo2 {
		(): void;
	}
})();

✅ Enabled (error)

// Bad
/*
(() => {
	type Test = { x: number };
})();
*/
// Good
(() => {
	interface ITest {
		x: number;
	}
})();

✅ Enabled (error)

// Bad
/*
(() => {
	const arrowFunctionReturnsPromise = () => Promise.resolve('value');

	function functionReturnsPromise() {
		return Math.random() > 0.5 ? Promise.resolve('value') : false;
	}
})();
*/
// Good
(() => {
	const arrowFunctionReturnsPromise = async () => 'value';

	async function functionReturnsPromise() {
		return Math.random() > 0.5 ? 'value' : false;
	}
})();

✅ Enabled (error)

// Bad
/*
(() => {
	const foo = '5.5' + 5;
})();
*/
// Good
(() => {
	const foo = parseInt('5.5', 10) + 10;
})();

✅ Enabled (error)

// Bad
/*
(() => {
	const foo:string = 'bar';
})();
*/
// Good
(() => {
	const foo: string = 'bar';
})();

✅ Enabled (error)

// Bad
/*
(() => {
	interface IFoo {
		foo(sn: string | number): void;
		foo(s: string): void;
		foo(n: number): void;
		bar(): void;
	}
})();
*/
// Good
(() => {
	interface IFoo {
		foo(sn: string | number): void;
		bar(): void;
	}
})();