diff options
author | Florian Dold <florian.dold@gmail.com> | 2017-08-14 05:01:11 +0200 |
---|---|---|
committer | Florian Dold <florian.dold@gmail.com> | 2017-08-14 05:02:09 +0200 |
commit | 363723fc84f7b8477592e0105aeb331ec9a017af (patch) | |
tree | 29f92724f34131bac64d6a318dd7e30612e631c7 /node_modules/tslint/lib/rules/noUnboundMethodRule.js | |
parent | 5634e77ad96bfe1818f6b6ee70b7379652e5487f (diff) |
node_modules
Diffstat (limited to 'node_modules/tslint/lib/rules/noUnboundMethodRule.js')
-rw-r--r-- | node_modules/tslint/lib/rules/noUnboundMethodRule.js | 75 |
1 files changed, 45 insertions, 30 deletions
diff --git a/node_modules/tslint/lib/rules/noUnboundMethodRule.js b/node_modules/tslint/lib/rules/noUnboundMethodRule.js index 388cfa404..80804b58d 100644 --- a/node_modules/tslint/lib/rules/noUnboundMethodRule.js +++ b/node_modules/tslint/lib/rules/noUnboundMethodRule.js @@ -17,54 +17,56 @@ */ Object.defineProperty(exports, "__esModule", { value: true }); var tslib_1 = require("tslib"); +var tsutils_1 = require("tsutils"); var ts = require("typescript"); var Lint = require("../index"); +var OPTION_IGNORE_STATIC = "ignore-static"; var Rule = (function (_super) { tslib_1.__extends(Rule, _super); function Rule() { return _super !== null && _super.apply(this, arguments) || this; } Rule.prototype.applyWithProgram = function (sourceFile, program) { - return this.applyWithWalker(new Walker(sourceFile, this.getOptions(), program)); + return this.applyWithFunction(sourceFile, function (ctx) { return walk(ctx, program.getTypeChecker()); }, { + ignoreStatic: this.ruleArguments.indexOf(OPTION_IGNORE_STATIC) !== -1, + }); }; + /* tslint:disable:object-literal-sort-keys */ + Rule.metadata = { + ruleName: "no-unbound-method", + description: "Warns when a method is used as outside of a method call.", + optionsDescription: "You may optionally pass \"" + OPTION_IGNORE_STATIC + "\" to ignore static methods.", + options: { + type: "string", + enum: [OPTION_IGNORE_STATIC], + }, + optionExamples: [true, [true, OPTION_IGNORE_STATIC]], + type: "functionality", + typescriptOnly: true, + requiresTypeInfo: true, + }; + /* tslint:enable:object-literal-sort-keys */ + Rule.FAILURE_STRING = "Avoid referencing unbound methods which may cause unintentional scoping of 'this'."; return Rule; }(Lint.Rules.TypedRule)); -/* tslint:disable:object-literal-sort-keys */ -Rule.metadata = { - ruleName: "no-unbound-method", - description: "Warns when a method is used as outside of a method call.", - optionsDescription: "Not configurable.", - options: null, - optionExamples: [true], - type: "functionality", - typescriptOnly: true, - requiresTypeInfo: true, -}; -/* tslint:enable:object-literal-sort-keys */ -Rule.FAILURE_STRING = "Avoid referencing unbound methods which may cause unintentional scoping of 'this'."; exports.Rule = Rule; -var Walker = (function (_super) { - tslib_1.__extends(Walker, _super); - function Walker() { - return _super !== null && _super.apply(this, arguments) || this; - } - Walker.prototype.visitPropertyAccessExpression = function (node) { - if (!isSafeUse(node)) { - var symbol = this.getTypeChecker().getSymbolAtLocation(node); +function walk(ctx, tc) { + return ts.forEachChild(ctx.sourceFile, function cb(node) { + if (tsutils_1.isPropertyAccessExpression(node) && !isSafeUse(node)) { + var symbol = tc.getSymbolAtLocation(node); var declaration = symbol === undefined ? undefined : symbol.valueDeclaration; - if (declaration !== undefined && isMethod(declaration)) { - this.addFailureAtNode(node, Rule.FAILURE_STRING); + if (declaration !== undefined && isMethod(declaration, ctx.options.ignoreStatic)) { + ctx.addFailureAtNode(node, Rule.FAILURE_STRING); } } - _super.prototype.visitPropertyAccessExpression.call(this, node); - }; - return Walker; -}(Lint.ProgramAwareRuleWalker)); -function isMethod(node) { + return ts.forEachChild(node, cb); + }); +} +function isMethod(node, ignoreStatic) { switch (node.kind) { case ts.SyntaxKind.MethodDeclaration: case ts.SyntaxKind.MethodSignature: - return true; + return !(ignoreStatic && tsutils_1.hasModifier(node.modifiers, ts.SyntaxKind.StaticKeyword)); default: return false; } @@ -82,6 +84,19 @@ function isSafeUse(node) { // Allow most binary operators, but don't allow e.g. `myArray.forEach(obj.method || otherObj.otherMethod)`. case ts.SyntaxKind.BinaryExpression: return parent.operatorToken.kind !== ts.SyntaxKind.BarBarToken; + case ts.SyntaxKind.NonNullExpression: + case ts.SyntaxKind.AsExpression: + case ts.SyntaxKind.TypeAssertionExpression: + case ts.SyntaxKind.ParenthesizedExpression: + return isSafeUse(parent); + // Allow use in conditions + case ts.SyntaxKind.ConditionalExpression: + return parent.condition === node; + case ts.SyntaxKind.IfStatement: + case ts.SyntaxKind.WhileStatement: + case ts.SyntaxKind.DoStatement: + case ts.SyntaxKind.ForStatement: + return true; default: return false; } |