From 4d0ff0dce4bdef031f19a2ec8891ae58f98616ee Mon Sep 17 00:00:00 2001 From: Brandon Millman Date: Tue, 30 Jan 2018 14:02:13 -0800 Subject: Add protected keyword to underscore lint rule --- packages/tslint-config/CHANGELOG.md | 5 ++ .../rules/underscorePrivateAndProtectedRule.ts | 61 ++++++++++++++++++++++ .../tslint-config/rules/underscorePrivatesRule.ts | 61 ---------------------- packages/tslint-config/tslint.json | 2 +- 4 files changed, 67 insertions(+), 62 deletions(-) create mode 100644 packages/tslint-config/rules/underscorePrivateAndProtectedRule.ts delete mode 100644 packages/tslint-config/rules/underscorePrivatesRule.ts (limited to 'packages/tslint-config') diff --git a/packages/tslint-config/CHANGELOG.md b/packages/tslint-config/CHANGELOG.md index 1d56bca5b..dac4051ea 100644 --- a/packages/tslint-config/CHANGELOG.md +++ b/packages/tslint-config/CHANGELOG.md @@ -1,5 +1,10 @@ # CHANGELOG +## v0.5.0 - _TBD, 2018_ + + * Modified custom 'underscore-privates' rule, changing it to 'underscore-private-protected' requiring underscores to be prepended to private variable names + * Because our tools can be used in both a TS and JS environment, we want to make the private methods of any public facing interface show up at the bottom of auto-complete lists. Additionally, we wanted to remain consistent with respect to our usage of underscores in order to enforce this rule with a linter rule, rather then manual code reviews. + ## v0.4.0 - _December 28, 2017_ * Added custom 'underscore-privates' rule, requiring underscores to be prepended to private variable names diff --git a/packages/tslint-config/rules/underscorePrivateAndProtectedRule.ts b/packages/tslint-config/rules/underscorePrivateAndProtectedRule.ts new file mode 100644 index 000000000..2f05b0c18 --- /dev/null +++ b/packages/tslint-config/rules/underscorePrivateAndProtectedRule.ts @@ -0,0 +1,61 @@ +import * as Lint from 'tslint'; +import * as ts from 'typescript'; + +const UNDERSCORE = '_'; + +type RelevantClassMember = + | ts.MethodDeclaration + | ts.PropertyDeclaration + | ts.GetAccessorDeclaration + | ts.SetAccessorDeclaration; + +// Copied from: https://github.com/DanielRosenwasser/underscore-privates-tslint-rule +// The version on github is not published on npm +export class Rule extends Lint.Rules.AbstractRule { + public static FAILURE_STRING = 'private and protected members must be prefixed with an underscore'; + + public apply(sourceFile: ts.SourceFile): Lint.RuleFailure[] { + return this.applyWithFunction(sourceFile, walk); + } +} +function walk(ctx: Lint.WalkContext): void { + traverse(ctx.sourceFile); + + function traverse(node: ts.Node): void { + checkNodeForViolations(ctx, node); + return ts.forEachChild(node, traverse); + } +} +function checkNodeForViolations(ctx: Lint.WalkContext, node: ts.Node): void { + if (!isRelevantClassMember(node)) { + return; + } + // The declaration might have a computed property name or a numeric name. + const name = node.name; + if (!nameIsIdentifier(name)) { + return; + } + if (!nameStartsWithUnderscore(name.text) && memberIsPrivate(node)) { + ctx.addFailureAtNode(name, Rule.FAILURE_STRING); + } +} +function isRelevantClassMember(node: ts.Node): node is RelevantClassMember { + switch (node.kind) { + case ts.SyntaxKind.MethodDeclaration: + case ts.SyntaxKind.PropertyDeclaration: + case ts.SyntaxKind.GetAccessor: + case ts.SyntaxKind.SetAccessor: + return true; + default: + return false; + } +} +function nameStartsWithUnderscore(text: string) { + return text.charCodeAt(0) === UNDERSCORE.charCodeAt(0); +} +function memberIsPrivate(node: ts.Declaration) { + return Lint.hasModifier(node.modifiers, ts.SyntaxKind.PrivateKeyword, ts.SyntaxKind.ProtectedKeyword); +} +function nameIsIdentifier(node: ts.Node): node is ts.Identifier { + return node.kind === ts.SyntaxKind.Identifier; +} diff --git a/packages/tslint-config/rules/underscorePrivatesRule.ts b/packages/tslint-config/rules/underscorePrivatesRule.ts deleted file mode 100644 index 472ea09ff..000000000 --- a/packages/tslint-config/rules/underscorePrivatesRule.ts +++ /dev/null @@ -1,61 +0,0 @@ -import * as Lint from 'tslint'; -import * as ts from 'typescript'; - -const UNDERSCORE = '_'; - -type RelevantClassMember = - | ts.MethodDeclaration - | ts.PropertyDeclaration - | ts.GetAccessorDeclaration - | ts.SetAccessorDeclaration; - -// Copied from: https://github.com/DanielRosenwasser/underscore-privates-tslint-rule -// The version on github is not published on npm -export class Rule extends Lint.Rules.AbstractRule { - public static FAILURE_STRING = 'private members must be prefixed with an underscore'; - - public apply(sourceFile: ts.SourceFile): Lint.RuleFailure[] { - return this.applyWithFunction(sourceFile, walk); - } -} -function walk(ctx: Lint.WalkContext): void { - traverse(ctx.sourceFile); - - function traverse(node: ts.Node): void { - checkNodeForViolations(ctx, node); - return ts.forEachChild(node, traverse); - } -} -function checkNodeForViolations(ctx: Lint.WalkContext, node: ts.Node): void { - if (!isRelevantClassMember(node)) { - return; - } - // The declaration might have a computed property name or a numeric name. - const name = node.name; - if (!nameIsIdentifier(name)) { - return; - } - if (!nameStartsWithUnderscore(name.text) && memberIsPrivate(node)) { - ctx.addFailureAtNode(name, Rule.FAILURE_STRING); - } -} -function isRelevantClassMember(node: ts.Node): node is RelevantClassMember { - switch (node.kind) { - case ts.SyntaxKind.MethodDeclaration: - case ts.SyntaxKind.PropertyDeclaration: - case ts.SyntaxKind.GetAccessor: - case ts.SyntaxKind.SetAccessor: - return true; - default: - return false; - } -} -function nameStartsWithUnderscore(text: string) { - return text.charCodeAt(0) === UNDERSCORE.charCodeAt(0); -} -function memberIsPrivate(node: ts.Declaration) { - return Lint.hasModifier(node.modifiers, ts.SyntaxKind.PrivateKeyword); -} -function nameIsIdentifier(node: ts.Node): node is ts.Identifier { - return node.kind === ts.SyntaxKind.Identifier; -} diff --git a/packages/tslint-config/tslint.json b/packages/tslint-config/tslint.json index 44a8517dc..3266b022f 100644 --- a/packages/tslint-config/tslint.json +++ b/packages/tslint-config/tslint.json @@ -73,7 +73,7 @@ ], "space-within-parens": false, "type-literal-delimiter": true, - "underscore-privates": true, + "underscore-private-and-protected": true, "variable-name": [true, "ban-keywords", "allow-pascal-case"], "whitespace": [ true, -- cgit v1.2.3 From 7cc4a8f5cebb41ee5b9a37a1732d7f2af5d16d4a Mon Sep 17 00:00:00 2001 From: Brandon Millman Date: Tue, 30 Jan 2018 16:26:42 -0800 Subject: Fix lint errors --- packages/tslint-config/CHANGELOG.md | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) (limited to 'packages/tslint-config') diff --git a/packages/tslint-config/CHANGELOG.md b/packages/tslint-config/CHANGELOG.md index dac4051ea..f7dc6e5a4 100644 --- a/packages/tslint-config/CHANGELOG.md +++ b/packages/tslint-config/CHANGELOG.md @@ -2,8 +2,7 @@ ## v0.5.0 - _TBD, 2018_ - * Modified custom 'underscore-privates' rule, changing it to 'underscore-private-protected' requiring underscores to be prepended to private variable names - * Because our tools can be used in both a TS and JS environment, we want to make the private methods of any public facing interface show up at the bottom of auto-complete lists. Additionally, we wanted to remain consistent with respect to our usage of underscores in order to enforce this rule with a linter rule, rather then manual code reviews. + * Modified custom 'underscore-privates' rule, changing it to 'underscore-private-and-protected' requiring underscores to be prepended to both private and protected variable names ## v0.4.0 - _December 28, 2017_ -- cgit v1.2.3 From ca55cc99edee3697646e2b4f28622f345c290fd7 Mon Sep 17 00:00:00 2001 From: Brandon Millman Date: Tue, 30 Jan 2018 16:48:40 -0800 Subject: Add PR number to changelog --- packages/tslint-config/CHANGELOG.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'packages/tslint-config') diff --git a/packages/tslint-config/CHANGELOG.md b/packages/tslint-config/CHANGELOG.md index f7dc6e5a4..04d705941 100644 --- a/packages/tslint-config/CHANGELOG.md +++ b/packages/tslint-config/CHANGELOG.md @@ -2,7 +2,7 @@ ## v0.5.0 - _TBD, 2018_ - * Modified custom 'underscore-privates' rule, changing it to 'underscore-private-and-protected' requiring underscores to be prepended to both private and protected variable names + * Modified custom 'underscore-privates' rule, changing it to 'underscore-private-and-protected' requiring underscores to be prepended to both private and protected variable names (#354) ## v0.4.0 - _December 28, 2017_ -- cgit v1.2.3