Skip to content
This repository was archived by the owner on Jul 15, 2023. It is now read-only.
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
9 changes: 9 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -722,6 +722,15 @@ We recommend you specify exact versions of lint libraries, including `tslint-mic
</td>
<td>4.0.2</td>
</tr>
<tr>
<td>
<code>void-zero</code>
</td>
<td>
<code>void 0</code>, which resolves to <code>undefined</code>, can be confusing to newcomers. Exclusively use <code>undefined</code> to reduce ambiguity.
</td>
<td>6.1.0</td>
</tr>
<tr>
<td>
<code>no-var-self</code>
Expand Down
1 change: 1 addition & 0 deletions recommended_ruleset.js
Original file line number Diff line number Diff line change
Expand Up @@ -181,6 +181,7 @@ module.exports = {
'unified-signatures': true,
'use-default-type-parameter': true,
'variable-name': true,
'void-zero': true,

/**
* Accessibility. The following rules should be turned on to guarantee the best user
Expand Down
47 changes: 47 additions & 0 deletions src/voidZeroRule.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,47 @@
import * as ts from 'typescript';
import * as Lint from 'tslint';
import * as tsutils from 'tsutils';

import { ExtendedMetadata } from './utils/ExtendedMetadata';

const FAILURE_STRING: string = 'Replace void 0 with undefined';

export class Rule extends Lint.Rules.AbstractRule {
public static metadata: ExtendedMetadata = {
ruleName: 'void-zero',
type: 'maintainability',
description: 'Avoid using void 0; use undefined instead.',
hasFix: true,
rationale: 'void 0, which resolves to undefined, can be confusing to newcomers. Exclusively use undefined to reduce ambiguity.',
options: null, // tslint:disable-line:no-null-keyword
optionsDescription: '',
typescriptOnly: true,
issueClass: 'Non-SDL',
issueType: 'Warning',
severity: 'Low',
level: 'Opportunity for Excellence',
group: 'Clarity',
commonWeaknessEnumeration: '480'
};

public apply(sourceFile: ts.SourceFile): Lint.RuleFailure[] {
return this.applyWithFunction(sourceFile, walk);
}
}

function walk(ctx: Lint.WalkContext<void>) {
function cb(node: ts.Node): void {
if (tsutils.isVoidExpression(node)) {
if (node.expression !== undefined && node.expression.getText() === '0') {
const nodeStart = node.getStart();
const nodeWidth = node.getWidth();
const fix = new Lint.Replacement(nodeStart, nodeWidth, 'undefined');

ctx.addFailureAt(nodeStart, nodeWidth, FAILURE_STRING, fix);
}
}
return ts.forEachChild(node, cb);
}

return ts.forEachChild(ctx.sourceFile, cb);
}
22 changes: 22 additions & 0 deletions tests/void-zero/test.ts.fix
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
new Array(undefined);
function mockFunction(arg1: undefined, arg2: string) {}
mockFunction(undefined, 'arg2String')
const bar = undefined;
const foo = {
bar: undefined,
};
class MockClass {
private foo = undefined
static bar = undefined
}

new Array(undefined);
mockFunction(undefined, 'arg2String')
const bar = undefined;
const foo = {
bar: undefined,
};
class MockClass {
private foo = undefined
static bar = undefined
}
28 changes: 28 additions & 0 deletions tests/void-zero/test.ts.lint
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
new Array(undefined);
function mockFunction(arg1: undefined, arg2: string) {}
mockFunction(undefined, 'arg2String')
const bar = undefined;
const foo = {
bar: undefined,
};
class MockClass {
private foo = undefined
static bar = undefined
}

new Array(void 0);
~~~~~~ [Replace void 0 with undefined]
mockFunction(void 0, 'arg2String')
~~~~~~ [Replace void 0 with undefined]
const bar = void 0;
~~~~~~ [Replace void 0 with undefined]
const foo = {
bar: void 0,
~~~~~~ [Replace void 0 with undefined]
};
class MockClass {
private foo = void 0
~~~~~~ [Replace void 0 with undefined]
static bar = void 0
~~~~~~ [Replace void 0 with undefined]
}
5 changes: 5 additions & 0 deletions tests/void-zero/tslint.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
{
"rules": {
"void-zero": true
}
}
1 change: 1 addition & 0 deletions tslint-warnings.csv
Original file line number Diff line number Diff line change
Expand Up @@ -319,5 +319,6 @@ use-simple-attributes,Enforce usage of only simple attribute types.,TSLINT1PG0L9
valid-typeof,Ensures that the results of typeof are compared against a valid string.,TSLINT1IB59P1,tslint,Non-SDL,Error,Critical,Opportunity for Excellence,See description on the tslint or tslint-microsoft-contrib website,TSLint Procedure,,
variable-name,Checks variable names for various errors.,TSLINT1CIV7K3,tslint,Non-SDL,Warning,Important,Opportunity for Excellence,See description on the tslint or tslint-microsoft-contrib website,TSLint Procedure,"398, 710","CWE 398 - Indicator of Poor Code Quality
CWE 710 - Coding Standards Violation"
void-zero,Avoid using void 0; use undefined instead.,TSLINT1BDGNG2,tslint,Non-SDL,Warning,Low,Opportunity for Excellence,See description on the tslint or tslint-microsoft-contrib website,TSLint Procedure,480,"CWE 480 - Use of Incorrect Operator"
whitespace,Enforces whitespace style conventions.,TSLINTC35UUS,tslint,Non-SDL,Warning,Low,Opportunity for Excellence,See description on the tslint or tslint-microsoft-contrib website,TSLint Procedure,"398, 710","CWE 398 - Indicator of Poor Code Quality
CWE 710 - Coding Standards Violation"
1 change: 1 addition & 0 deletions tslint.json
Original file line number Diff line number Diff line change
Expand Up @@ -148,6 +148,7 @@
"switch-final-break": true,
"type-literal-delimiter": false,
"underscore-consistent-invocation": true,
"void-zero": true,
"use-default-type-parameter": false,
"use-named-parameter": true,
"use-simple-attributes": true,
Expand Down