From 704720721c9142bebda5618c9e05679d74c62e62 Mon Sep 17 00:00:00 2001 From: Josh Goldberg Date: Sun, 25 Aug 2019 16:42:40 -0400 Subject: [PATCH 1/6] Added allow-generics option to invalid-void rule --- src/rules/invalidVoidRule.ts | 62 +++++++++++++++++-- .../allow-generics/true/test.ts.lint | 7 +++ .../allow-generics/true/tslint.json | 7 +++ .../allow-generics/whitelist/test.ts.lint | 11 ++++ .../allow-generics/whitelist/tslint.json | 7 +++ .../invalid-void/{ => default}/test.ts.lint | 6 ++ .../invalid-void/{ => default}/tslint.json | 0 7 files changed, 94 insertions(+), 6 deletions(-) create mode 100644 test/rules/invalid-void/allow-generics/true/test.ts.lint create mode 100644 test/rules/invalid-void/allow-generics/true/tslint.json create mode 100644 test/rules/invalid-void/allow-generics/whitelist/test.ts.lint create mode 100644 test/rules/invalid-void/allow-generics/whitelist/tslint.json rename test/rules/invalid-void/{ => default}/test.ts.lint (95%) rename test/rules/invalid-void/{ => default}/tslint.json (100%) diff --git a/src/rules/invalidVoidRule.ts b/src/rules/invalidVoidRule.ts index 2baec30a50f..66748ac6c39 100644 --- a/src/rules/invalidVoidRule.ts +++ b/src/rules/invalidVoidRule.ts @@ -19,6 +19,12 @@ import * as ts from "typescript"; import * as Lint from "../index"; +const OPTION_ALLOW_GENERICS = "allow-generics"; + +interface Options { + allowGenerics: boolean | Set; +} + export class Rule extends Lint.Rules.AbstractRule { /* tslint:disable:object-literal-sort-keys */ public static metadata: Lint.IRuleMetadata = { @@ -32,9 +38,26 @@ export class Rule extends Lint.Rules.AbstractRule { So "nothing" cannot be mixed with any other types. If you need this - use \`undefined\` type instead.`, hasFix: false, - optionsDescription: "Not configurable.", - options: null, - optionExamples: [true], + optionsDescription: Lint.Utils.dedent` + If \`${OPTION_ALLOW_GENERICS}\` is specified as \`true\`, then generic types will always be allowed to to be \`void\`. + Alternately, provide an array of strings for \`${OPTION_ALLOW_GENERICS}\` to exclusively allow those.`, + options: { + type: "object", + properties: { + [OPTION_ALLOW_GENERICS]: { + oneOf: [ + { type: "boolean" }, + { type: "array", items: { type: "string" }, minLength: 1 }, + ], + }, + }, + additionalProperties: false, + }, + optionExamples: [ + true, + [true, { [OPTION_ALLOW_GENERICS]: true }], + [true, { [OPTION_ALLOW_GENERICS]: ["Promise", "PromiseLike"] }], + ], type: "maintainability", typescriptOnly: true, }; @@ -43,7 +66,16 @@ export class Rule extends Lint.Rules.AbstractRule { public static FAILURE_STRING = "void is not a valid type other than return types"; public apply(sourceFile: ts.SourceFile): Lint.RuleFailure[] { - return this.applyWithFunction(sourceFile, walk); + return this.applyWithFunction(sourceFile, walk, { + // tslint:disable-next-line:no-object-literal-type-assertion + allowGenerics: this.getAllowGenerics(this.ruleArguments[0] as boolean | string[] | undefined) + }); + } + + private getAllowGenerics(rawArgument: boolean | string[] | undefined) { + return rawArgument instanceof Array + ? new Set(rawArgument) + : !!rawArgument; } } @@ -75,10 +107,28 @@ const failedKinds = new Set([ ts.SyntaxKind.CallExpression, ]); -function walk(ctx: Lint.WalkContext): void { +function walk(ctx: Lint.WalkContext): void { + const isWhitelistedTypeReferenceNode = (node: ts.Node) => { + if (!ts.isTypeReferenceNode(node)) { + return false; + } + + if (!(ctx.options.allowGenerics instanceof Set)) { + return ctx.options.allowGenerics; + } + + if (!ts.isIdentifier(node.typeName)) { + return false; + } + + return ctx.options.allowGenerics.has(node.typeName.text) + } + ts.forEachChild(ctx.sourceFile, function cb(node: ts.Node) { if (node.kind === ts.SyntaxKind.VoidKeyword && failedKinds.has(node.parent.kind)) { - ctx.addFailureAtNode(node, Rule.FAILURE_STRING); + if (!isWhitelistedTypeReferenceNode(node.parent)) { + ctx.addFailureAtNode(node, Rule.FAILURE_STRING); + } } ts.forEachChild(node, cb); diff --git a/test/rules/invalid-void/allow-generics/true/test.ts.lint b/test/rules/invalid-void/allow-generics/true/test.ts.lint new file mode 100644 index 00000000000..7cb70a4bc72 --- /dev/null +++ b/test/rules/invalid-void/allow-generics/true/test.ts.lint @@ -0,0 +1,7 @@ +type Generic = [T]; +type GenericVoid = Generic; + +function takeVoid(thing: void) { } + ~~~~ [0] + +[0]: void is not a valid type other than return types diff --git a/test/rules/invalid-void/allow-generics/true/tslint.json b/test/rules/invalid-void/allow-generics/true/tslint.json new file mode 100644 index 00000000000..d7dec9afca2 --- /dev/null +++ b/test/rules/invalid-void/allow-generics/true/tslint.json @@ -0,0 +1,7 @@ +{ + "rules": { + "invalid-void": [true, { + "allow-generics": true + }] + } +} diff --git a/test/rules/invalid-void/allow-generics/whitelist/test.ts.lint b/test/rules/invalid-void/allow-generics/whitelist/test.ts.lint new file mode 100644 index 00000000000..b6bbd63509a --- /dev/null +++ b/test/rules/invalid-void/allow-generics/whitelist/test.ts.lint @@ -0,0 +1,11 @@ +type Allowed = [T]; +type AllowedVoid = Allowed; + +type Banned = [T]; +type BannedVoid = Banned; + ~~~~ [0] + +function takeVoid(thing: void) { } + ~~~~ [0] + +[0]: void is not a valid type other than return types diff --git a/test/rules/invalid-void/allow-generics/whitelist/tslint.json b/test/rules/invalid-void/allow-generics/whitelist/tslint.json new file mode 100644 index 00000000000..44c4d38f9ef --- /dev/null +++ b/test/rules/invalid-void/allow-generics/whitelist/tslint.json @@ -0,0 +1,7 @@ +{ + "rules": { + "invalid-void": [true, { + "allow-generics": ["Allowed"] + }] + } +} diff --git a/test/rules/invalid-void/test.ts.lint b/test/rules/invalid-void/default/test.ts.lint similarity index 95% rename from test/rules/invalid-void/test.ts.lint rename to test/rules/invalid-void/default/test.ts.lint index 27c065770b1..6581888fb03 100644 --- a/test/rules/invalid-void/test.ts.lint +++ b/test/rules/invalid-void/default/test.ts.lint @@ -99,6 +99,12 @@ type UnionType3 = string | (number & any | (string | void)); type IntersectionType = string & number & void; ~~~~ [0] +function returnsVoidPromiseDirectly(): Promise { + return Promise.resolve(); +} + +async function returnsVoidPromiseAsync(): Promise {} + #if typescript >= 2.8.0 type MappedType = { [K in keyof T]: void; diff --git a/test/rules/invalid-void/tslint.json b/test/rules/invalid-void/default/tslint.json similarity index 100% rename from test/rules/invalid-void/tslint.json rename to test/rules/invalid-void/default/tslint.json From a7190a57224e41f7ad8d65c2378621844ae7cae9 Mon Sep 17 00:00:00 2001 From: Josh Goldberg Date: Sat, 31 Aug 2019 09:26:17 -0400 Subject: [PATCH 2/6] Allowed generics by default --- src/rules/invalidVoidRule.ts | 92 ++++++++++++++----- .../allow-generics/false/test.ts.lint | 16 ++++ .../allow-generics/false/tslint.json | 7 ++ .../allow-generics/true/test.ts.lint | 6 +- .../allow-generics/whitelist/test.ts.lint | 5 +- test/rules/invalid-void/default/test.ts.lint | 8 +- 6 files changed, 106 insertions(+), 28 deletions(-) create mode 100644 test/rules/invalid-void/allow-generics/false/test.ts.lint create mode 100644 test/rules/invalid-void/allow-generics/false/tslint.json diff --git a/src/rules/invalidVoidRule.ts b/src/rules/invalidVoidRule.ts index 66748ac6c39..092e61fe4df 100644 --- a/src/rules/invalidVoidRule.ts +++ b/src/rules/invalidVoidRule.ts @@ -25,12 +25,18 @@ interface Options { allowGenerics: boolean | Set; } +interface RawOptions { + [OPTION_ALLOW_GENERICS]?: boolean | Set; +} + +type GenericReference = ts.NewExpression | ts.TypeReferenceNode; + export class Rule extends Lint.Rules.AbstractRule { /* tslint:disable:object-literal-sort-keys */ public static metadata: Lint.IRuleMetadata = { ruleName: "invalid-void", description: Lint.Utils.dedent` - Disallows usage of \`void\` type outside of return type. + Disallows usage of \`void\` type outside of generic or return types. If \`void\` is used as return type, it shouldn't be a part of intersection/union type.`, rationale: Lint.Utils.dedent` The \`void\` type means "nothing" or that a function does not return any value, @@ -39,8 +45,8 @@ export class Rule extends Lint.Rules.AbstractRule { If you need this - use \`undefined\` type instead.`, hasFix: false, optionsDescription: Lint.Utils.dedent` - If \`${OPTION_ALLOW_GENERICS}\` is specified as \`true\`, then generic types will always be allowed to to be \`void\`. - Alternately, provide an array of strings for \`${OPTION_ALLOW_GENERICS}\` to exclusively allow those.`, + If \`${OPTION_ALLOW_GENERICS}\` is specified as \`false\`, then generic types will no longer be allowed to to be \`void\`. + Alternately, provide an array of strings for \`${OPTION_ALLOW_GENERICS}\` to exclusively allow generic types by those names.`, options: { type: "object", properties: { @@ -55,7 +61,7 @@ export class Rule extends Lint.Rules.AbstractRule { }, optionExamples: [ true, - [true, { [OPTION_ALLOW_GENERICS]: true }], + [true, { [OPTION_ALLOW_GENERICS]: false }], [true, { [OPTION_ALLOW_GENERICS]: ["Promise", "PromiseLike"] }], ], type: "maintainability", @@ -63,19 +69,27 @@ export class Rule extends Lint.Rules.AbstractRule { }; /* tslint:enable:object-literal-sort-keys */ - public static FAILURE_STRING = "void is not a valid type other than return types"; + public static FAILURE_STRING_ALLOW_GENERICS = + "void is not a valid type other than generic or return types"; + public static FAILURE_STRING_NO_GENERICS = "void is not a valid type other than return types"; + public static FAILURE_WRONG_GENERIC = (genericName: string) => + `${genericName} may not have void as a generic type`; public apply(sourceFile: ts.SourceFile): Lint.RuleFailure[] { return this.applyWithFunction(sourceFile, walk, { // tslint:disable-next-line:no-object-literal-type-assertion - allowGenerics: this.getAllowGenerics(this.ruleArguments[0] as boolean | string[] | undefined) + allowGenerics: this.getAllowGenerics(this.ruleArguments[0] as RawOptions), }); } - private getAllowGenerics(rawArgument: boolean | string[] | undefined) { - return rawArgument instanceof Array - ? new Set(rawArgument) - : !!rawArgument; + private getAllowGenerics(rawArgument: RawOptions) { + if (!rawArgument) { + return true; + } + + const allowGenerics = rawArgument[OPTION_ALLOW_GENERICS]; + + return allowGenerics instanceof Array ? new Set(allowGenerics) : !!allowGenerics; } } @@ -108,26 +122,62 @@ const failedKinds = new Set([ ]); function walk(ctx: Lint.WalkContext): void { - const isWhitelistedTypeReferenceNode = (node: ts.Node) => { - if (!ts.isTypeReferenceNode(node)) { - return false; - } + const defaultFailureString = ctx.options.allowGenerics + ? Rule.FAILURE_STRING_ALLOW_GENERICS + : Rule.FAILURE_STRING_NO_GENERICS; + + const getGenericReferenceName = (node: GenericReference) => { + const rawName = ts.isNewExpression(node) + ? node.expression + : node.typeName; + + return ts.isIdentifier(rawName) + ? rawName.text + : rawName.getText(ctx.sourceFile); + } + const getTypeReferenceFailure = (node: GenericReference) => { if (!(ctx.options.allowGenerics instanceof Set)) { - return ctx.options.allowGenerics; + return ctx.options.allowGenerics ? undefined : defaultFailureString; } - if (!ts.isIdentifier(node.typeName)) { - return false; + const genericName = getGenericReferenceName(node); + + return ctx.options.allowGenerics.has(genericName) + ? undefined + : Rule.FAILURE_WRONG_GENERIC(genericName); + }; + + const checkTypeReference = (parent: GenericReference, node: ts.Node) => { + const failure = getTypeReferenceFailure(parent); + + if (failure !== undefined) { + ctx.addFailureAtNode(node, failure); + } + }; + + const isParentGenericReference = ( + parent: ts.Node, + node: ts.Node, + ): parent is GenericReference => { + if (ts.isTypeReferenceNode(parent)) { + return true; } - return ctx.options.allowGenerics.has(node.typeName.text) - } + return ( + ts.isNewExpression(parent) && + parent.typeArguments !== undefined && + ts.isTypeNode(node) && + parent.typeArguments.indexOf(node) !== -1 + ); + }; ts.forEachChild(ctx.sourceFile, function cb(node: ts.Node) { if (node.kind === ts.SyntaxKind.VoidKeyword && failedKinds.has(node.parent.kind)) { - if (!isWhitelistedTypeReferenceNode(node.parent)) { - ctx.addFailureAtNode(node, Rule.FAILURE_STRING); + if (isParentGenericReference(node.parent, node)) { + checkTypeReference(node.parent, node); + } else { + ctx.addFailureAtNode(node, defaultFailureString); } } diff --git a/test/rules/invalid-void/allow-generics/false/test.ts.lint b/test/rules/invalid-void/allow-generics/false/test.ts.lint new file mode 100644 index 00000000000..e0b0cd6088e --- /dev/null +++ b/test/rules/invalid-void/allow-generics/false/test.ts.lint @@ -0,0 +1,16 @@ +type Generic = [T]; +type GenericVoid = Generic; + ~~~~ [0] + +function takeVoid(thing: void) { } + ~~~~ [0] + +let voidPromise: Promise = new Promise(() => {}); + ~~~~ [0] + ~~~~ [0] + +let voidMap: Map = new Map(); + ~~~~ [0] + ~~~~ [0] + +[0]: void is not a valid type other than return types diff --git a/test/rules/invalid-void/allow-generics/false/tslint.json b/test/rules/invalid-void/allow-generics/false/tslint.json new file mode 100644 index 00000000000..baddd96c2b4 --- /dev/null +++ b/test/rules/invalid-void/allow-generics/false/tslint.json @@ -0,0 +1,7 @@ +{ + "rules": { + "invalid-void": [true, { + "allow-generics": false + }] + } +} diff --git a/test/rules/invalid-void/allow-generics/true/test.ts.lint b/test/rules/invalid-void/allow-generics/true/test.ts.lint index 7cb70a4bc72..13b3272cdf7 100644 --- a/test/rules/invalid-void/allow-generics/true/test.ts.lint +++ b/test/rules/invalid-void/allow-generics/true/test.ts.lint @@ -4,4 +4,8 @@ type GenericVoid = Generic; function takeVoid(thing: void) { } ~~~~ [0] -[0]: void is not a valid type other than return types +let voidPromise: Promise = new Promise(() => {}); + +let voidMap: Map = new Map(); + +[0]: void is not a valid type other than generic or return types diff --git a/test/rules/invalid-void/allow-generics/whitelist/test.ts.lint b/test/rules/invalid-void/allow-generics/whitelist/test.ts.lint index b6bbd63509a..d7ed9a98516 100644 --- a/test/rules/invalid-void/allow-generics/whitelist/test.ts.lint +++ b/test/rules/invalid-void/allow-generics/whitelist/test.ts.lint @@ -3,9 +3,10 @@ type AllowedVoid = Allowed; type Banned = [T]; type BannedVoid = Banned; - ~~~~ [0] + ~~~~ [Generic % ('Banned')] function takeVoid(thing: void) { } ~~~~ [0] -[0]: void is not a valid type other than return types +[0]: void is not a valid type other than generic or return types +[Generic]: %s may not have void as a generic type diff --git a/test/rules/invalid-void/default/test.ts.lint b/test/rules/invalid-void/default/test.ts.lint index 6581888fb03..c0c4345fe12 100644 --- a/test/rules/invalid-void/default/test.ts.lint +++ b/test/rules/invalid-void/default/test.ts.lint @@ -75,9 +75,9 @@ class ClassName { ~~~~ [0] } -let invalidMap: Map = new Map(); - ~~~~ [0] - ~~~~ [0] +let voidPromise: Promise = new Promise(() => {}); + +let voidMap: Map = new Map(); let letVoid: void; ~~~~ [0] @@ -124,4 +124,4 @@ function foo(arr: readonly void[]) { } ~~~~ [0] #endif -[0]: void is not a valid type other than return types +[0]: void is not a valid type other than generic or return types From 66975a8dc4b1af72dbc111dde703d9c0d17c1ce5 Mon Sep 17 00:00:00 2001 From: Josh Goldberg Date: Sat, 31 Aug 2019 09:33:45 -0400 Subject: [PATCH 3/6] Lint and format fixes --- src/rules/invalidVoidRule.ts | 17 +++++++---------- 1 file changed, 7 insertions(+), 10 deletions(-) diff --git a/src/rules/invalidVoidRule.ts b/src/rules/invalidVoidRule.ts index 092e61fe4df..dc5e44fbd11 100644 --- a/src/rules/invalidVoidRule.ts +++ b/src/rules/invalidVoidRule.ts @@ -15,6 +15,7 @@ * limitations under the License. */ +import * as tsutils from "tsutils"; import * as ts from "typescript"; import * as Lint from "../index"; @@ -25,7 +26,7 @@ interface Options { allowGenerics: boolean | Set; } -interface RawOptions { +type RawOptions = undefined | { [OPTION_ALLOW_GENERICS]?: boolean | Set; } @@ -89,7 +90,7 @@ export class Rule extends Lint.Rules.AbstractRule { const allowGenerics = rawArgument[OPTION_ALLOW_GENERICS]; - return allowGenerics instanceof Array ? new Set(allowGenerics) : !!allowGenerics; + return allowGenerics instanceof Array ? new Set(allowGenerics) : Boolean(allowGenerics); } } @@ -127,14 +128,10 @@ function walk(ctx: Lint.WalkContext): void { : Rule.FAILURE_STRING_NO_GENERICS; const getGenericReferenceName = (node: GenericReference) => { - const rawName = ts.isNewExpression(node) - ? node.expression - : node.typeName; + const rawName = ts.isNewExpression(node) ? node.expression : node.typeName; - return ts.isIdentifier(rawName) - ? rawName.text - : rawName.getText(ctx.sourceFile); - } + return ts.isIdentifier(rawName) ? rawName.text : rawName.getText(ctx.sourceFile); + }; const getTypeReferenceFailure = (node: GenericReference) => { if (!(ctx.options.allowGenerics instanceof Set)) { @@ -160,7 +157,7 @@ function walk(ctx: Lint.WalkContext): void { parent: ts.Node, node: ts.Node, ): parent is GenericReference => { - if (ts.isTypeReferenceNode(parent)) { + if (tsutils.isTypeReferenceNode(parent)) { return true; } From 8c2e11ad52060c439826f04083c6bb6f06a0489d Mon Sep 17 00:00:00 2001 From: Josh Goldberg Date: Sat, 31 Aug 2019 09:38:31 -0400 Subject: [PATCH 4/6] Annoying not having these things running locally --- src/rules/invalidVoidRule.ts | 16 +++++++++------- 1 file changed, 9 insertions(+), 7 deletions(-) diff --git a/src/rules/invalidVoidRule.ts b/src/rules/invalidVoidRule.ts index dc5e44fbd11..2690c98db13 100644 --- a/src/rules/invalidVoidRule.ts +++ b/src/rules/invalidVoidRule.ts @@ -26,9 +26,11 @@ interface Options { allowGenerics: boolean | Set; } -type RawOptions = undefined | { - [OPTION_ALLOW_GENERICS]?: boolean | Set; -} +type RawOptions = + | undefined + | { + [OPTION_ALLOW_GENERICS]?: boolean | Set; + }; type GenericReference = ts.NewExpression | ts.TypeReferenceNode; @@ -84,7 +86,7 @@ export class Rule extends Lint.Rules.AbstractRule { } private getAllowGenerics(rawArgument: RawOptions) { - if (!rawArgument) { + if (rawArgument == undefined) { return true; } @@ -128,9 +130,9 @@ function walk(ctx: Lint.WalkContext): void { : Rule.FAILURE_STRING_NO_GENERICS; const getGenericReferenceName = (node: GenericReference) => { - const rawName = ts.isNewExpression(node) ? node.expression : node.typeName; + const rawName = tsutils.isNewExpression(node) ? node.expression : node.typeName; - return ts.isIdentifier(rawName) ? rawName.text : rawName.getText(ctx.sourceFile); + return tsutils.isIdentifier(rawName) ? rawName.text : rawName.getText(ctx.sourceFile); }; const getTypeReferenceFailure = (node: GenericReference) => { @@ -162,7 +164,7 @@ function walk(ctx: Lint.WalkContext): void { } return ( - ts.isNewExpression(parent) && + tsutils.isNewExpression(parent) && parent.typeArguments !== undefined && ts.isTypeNode(node) && parent.typeArguments.indexOf(node) !== -1 From 3c4f3681c6ee80f2ed77666e0a707af1fe6951d4 Mon Sep 17 00:00:00 2001 From: Josh Goldberg Date: Sun, 8 Sep 2019 19:12:56 -0400 Subject: [PATCH 5/6] Apply suggestions from code review Thanks! Co-Authored-By: Adi Dahiya --- src/rules/invalidVoidRule.ts | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/src/rules/invalidVoidRule.ts b/src/rules/invalidVoidRule.ts index 2690c98db13..83c0380c807 100644 --- a/src/rules/invalidVoidRule.ts +++ b/src/rules/invalidVoidRule.ts @@ -73,10 +73,10 @@ export class Rule extends Lint.Rules.AbstractRule { /* tslint:enable:object-literal-sort-keys */ public static FAILURE_STRING_ALLOW_GENERICS = - "void is not a valid type other than generic or return types"; - public static FAILURE_STRING_NO_GENERICS = "void is not a valid type other than return types"; + "void is only valid as a return type or generic type variable"; + public static FAILURE_STRING_NO_GENERICS = "void is only valid as a return type"; public static FAILURE_WRONG_GENERIC = (genericName: string) => - `${genericName} may not have void as a generic type`; + `${genericName} may not have void as a type variable`; public apply(sourceFile: ts.SourceFile): Lint.RuleFailure[] { return this.applyWithFunction(sourceFile, walk, { From 03e54f427c16fc431a4a398f1e462eb449e146e2 Mon Sep 17 00:00:00 2001 From: Josh Goldberg Date: Sun, 8 Sep 2019 19:22:41 -0400 Subject: [PATCH 6/6] Added tests --- test/rules/invalid-void/allow-generics/false/test.ts.lint | 2 +- test/rules/invalid-void/allow-generics/true/test.ts.lint | 2 +- test/rules/invalid-void/allow-generics/whitelist/test.ts.lint | 4 ++-- test/rules/invalid-void/default/test.ts.lint | 2 +- 4 files changed, 5 insertions(+), 5 deletions(-) diff --git a/test/rules/invalid-void/allow-generics/false/test.ts.lint b/test/rules/invalid-void/allow-generics/false/test.ts.lint index e0b0cd6088e..2ad5f1ef10f 100644 --- a/test/rules/invalid-void/allow-generics/false/test.ts.lint +++ b/test/rules/invalid-void/allow-generics/false/test.ts.lint @@ -13,4 +13,4 @@ let voidMap: Map = new Map(); ~~~~ [0] ~~~~ [0] -[0]: void is not a valid type other than return types +[0]: void is only valid as a return type diff --git a/test/rules/invalid-void/allow-generics/true/test.ts.lint b/test/rules/invalid-void/allow-generics/true/test.ts.lint index 13b3272cdf7..900c5f54946 100644 --- a/test/rules/invalid-void/allow-generics/true/test.ts.lint +++ b/test/rules/invalid-void/allow-generics/true/test.ts.lint @@ -8,4 +8,4 @@ let voidPromise: Promise = new Promise(() => {}); let voidMap: Map = new Map(); -[0]: void is not a valid type other than generic or return types +[0]: void is only valid as a return type or generic type variable diff --git a/test/rules/invalid-void/allow-generics/whitelist/test.ts.lint b/test/rules/invalid-void/allow-generics/whitelist/test.ts.lint index d7ed9a98516..3734b406e2b 100644 --- a/test/rules/invalid-void/allow-generics/whitelist/test.ts.lint +++ b/test/rules/invalid-void/allow-generics/whitelist/test.ts.lint @@ -8,5 +8,5 @@ type BannedVoid = Banned; function takeVoid(thing: void) { } ~~~~ [0] -[0]: void is not a valid type other than generic or return types -[Generic]: %s may not have void as a generic type +[0]: void is only valid as a return type or generic type variable +[Generic]: %s may not have void as a type variable diff --git a/test/rules/invalid-void/default/test.ts.lint b/test/rules/invalid-void/default/test.ts.lint index c0c4345fe12..1f1fef5fc85 100644 --- a/test/rules/invalid-void/default/test.ts.lint +++ b/test/rules/invalid-void/default/test.ts.lint @@ -124,4 +124,4 @@ function foo(arr: readonly void[]) { } ~~~~ [0] #endif -[0]: void is not a valid type other than generic or return types +[0]: void is only valid as a return type or generic type variable