Skip to content

Commit

Permalink
Change: Switch :after to :exit (fixes #605)
Browse files Browse the repository at this point in the history
  • Loading branch information
nzakas committed Feb 12, 2014
1 parent 085cdde commit f1f453d
Show file tree
Hide file tree
Showing 14 changed files with 54 additions and 37 deletions.
17 changes: 17 additions & 0 deletions docs/developer-guide/working-with-rules.md
Expand Up @@ -41,6 +41,23 @@ module.exports = function(context) {

Each method that matches a node in the AST will be passed the corresponding node. You can then evaluate the node and it's surrounding tree to determine whether or not an issue needs reporting.

By default, the method matching a node name is called during the traversal when the node is first encountered, on the way down the AST. You can also specify to visit the node on the other side of the traversal, as it comes back up the tree, but adding `:exit` to the end of the node type, such as:

```js
module.exports = function(context) {

return {

"Identifier:exit": function(node) {
// do something with node
}
};

};
```

In this code, `"Identifier:exit"` is called on the way up the AST. This capability allows you to keep track as the traversal enters and exits specific parts of the AST.

The main method you'll use is `context.report()`, which publishes a warning or error (depending on the configuration being used). This method accepts three arguments: the AST node that caused the report, a message to display, and an optional object literal which is used to interpolate. For example:

context.report(node, "This is unexpected!");
Expand Down
6 changes: 3 additions & 3 deletions lib/eslint.js
Expand Up @@ -370,15 +370,15 @@ module.exports = (function() {

if (trailingComments) {
trailingComments.forEach(function(node) {
api.emit(node.type + "Comment:after", node);
api.emit(node.type + "Comment:exit", node);
});
}

api.emit(node.type + ":after", node);
api.emit(node.type + ":exit", node);

if (leadingComments) {
leadingComments.forEach(function(node) {
api.emit(node.type + "Comment:after", node);
api.emit(node.type + "Comment:exit", node);
});
}
}
Expand Down
2 changes: 1 addition & 1 deletion lib/rules/block-scoped-var.js
Expand Up @@ -85,7 +85,7 @@ module.exports = function(context) {

return {
"BlockStatement": pushBlock,
"BlockStatement:after": popBlock,
"BlockStatement:exit": popBlock,
"CatchClause": addCommonDeclaration,
"VariableDeclaration": addCommonDeclaration,
"FunctionDeclaration": addCommonDeclaration,
Expand Down
4 changes: 2 additions & 2 deletions lib/rules/complexity.js
Expand Up @@ -64,8 +64,8 @@ module.exports = function(context) {
return {
"FunctionDeclaration": startFunction,
"FunctionExpression": startFunction,
"FunctionDeclaration:after": endFunction,
"FunctionExpression:after": endFunction,
"FunctionDeclaration:exit": endFunction,
"FunctionExpression:exit": endFunction,

"CatchClause": increaseComplexity,
"ConditionalExpression": increaseComplexity,
Expand Down
4 changes: 2 additions & 2 deletions lib/rules/consistent-return.js
Expand Up @@ -33,8 +33,8 @@ module.exports = function(context) {

"FunctionDeclaration": enterFunction,
"FunctionExpression": enterFunction,
"FunctionDeclaration:after": exitFunction,
"FunctionExpression:after": exitFunction,
"FunctionDeclaration:exit": exitFunction,
"FunctionExpression:exit": exitFunction,

"ReturnStatement": function(node) {

Expand Down
24 changes: 12 additions & 12 deletions lib/rules/max-depth.js
Expand Up @@ -57,18 +57,18 @@ module.exports = function(context) {
"ForStatement": pushBlock,
"ForInStatement": pushBlock,

"IfStatement:after": popBlock,
"SwitchStatement:after": popBlock,
"TryStatement:after": popBlock,
"DoWhileStatement:after": popBlock,
"WhileStatement:after": popBlock,
"WithStatement:after": popBlock,
"ForStatement:after": popBlock,
"ForInStatement:after": popBlock,

"FunctionDeclaration:after": endFunction,
"FunctionExpression:after": endFunction,
"Program:after": endFunction
"IfStatement:exit": popBlock,
"SwitchStatement:exit": popBlock,
"TryStatement:exit": popBlock,
"DoWhileStatement:exit": popBlock,
"WhileStatement:exit": popBlock,
"WithStatement:exit": popBlock,
"ForStatement:exit": popBlock,
"ForInStatement:exit": popBlock,

"FunctionDeclaration:exit": endFunction,
"FunctionExpression:exit": endFunction,
"Program:exit": endFunction
};

};
4 changes: 2 additions & 2 deletions lib/rules/max-nested-callbacks.js
Expand Up @@ -39,10 +39,10 @@ module.exports = function(context) {
},


"FunctionExpression:after": function() {
"FunctionExpression:exit": function() {
callbackStack.pop();
}

};

};
};
4 changes: 2 additions & 2 deletions lib/rules/max-statements.js
Expand Up @@ -45,8 +45,8 @@ module.exports = function(context) {

"BlockStatement": countStatements,

"FunctionDeclaration:after": endFunction,
"FunctionExpression:after": endFunction
"FunctionDeclaration:exit": endFunction,
"FunctionExpression:exit": endFunction
};

};
2 changes: 1 addition & 1 deletion lib/rules/no-ex-assign.js
Expand Up @@ -21,7 +21,7 @@ module.exports = function(context) {
exceptionName = node.param.name;
},

"CatchClause:after": function() {
"CatchClause:exit": function() {
inCatch = false;
exceptionName = null;
},
Expand Down
2 changes: 1 addition & 1 deletion lib/rules/no-fallthrough.js
Expand Up @@ -72,7 +72,7 @@ module.exports = function(context) {
});
},

"SwitchStatement:after": function() {
"SwitchStatement:exit": function() {
switches.pop();
}
};
Expand Down
2 changes: 1 addition & 1 deletion lib/rules/no-unused-vars.js
Expand Up @@ -162,7 +162,7 @@ module.exports = function(context) {
}
},

"Program:after": function() {
"Program:exit": function() {
Object.keys(variables)
.forEach(function (name) {
variables[name].forEach(function (variable) {
Expand Down
6 changes: 3 additions & 3 deletions lib/rules/one-var.js
Expand Up @@ -44,9 +44,9 @@ module.exports = function(context) {

"VariableDeclaration": checkDeclarations,

"Program:after": endFunction,
"FunctionDeclaration:after": endFunction,
"FunctionExpression:after": endFunction
"Program:exit": endFunction,
"FunctionDeclaration:exit": endFunction,
"FunctionExpression:exit": endFunction
};

};
6 changes: 3 additions & 3 deletions lib/rules/strict.js
Expand Up @@ -43,9 +43,9 @@ module.exports = function(context) {
"FunctionDeclaration": enterScope,
"FunctionExpression": enterScope,

"Program:after": exitScope,
"FunctionDeclaration:after": exitScope,
"FunctionExpression:after": exitScope,
"Program:exit": exitScope,
"FunctionDeclaration:exit": exitScope,
"FunctionExpression:exit": exitScope,

"ExpressionStatement": function(node) {

Expand Down
8 changes: 4 additions & 4 deletions tests/lib/eslint.js
Expand Up @@ -529,7 +529,7 @@ describe("eslint", function() {
assert(spy.calledOnce, "Handler should be called.");
});

it("should fire LineComment and LineComment:after events", function() {
it("should fire LineComment and LineComment:exit events", function() {

function handler(node) {
var code = eslint.getSource(node);
Expand All @@ -542,7 +542,7 @@ describe("eslint", function() {

eslint.reset();
eslint.on("LineComment", spy);
eslint.on("LineComment:after", spy);
eslint.on("LineComment:exit", spy);

eslint.verify(code, config, true);
assert(spy.calledTwice, "Handler should be called.");
Expand All @@ -566,7 +566,7 @@ describe("eslint", function() {
assert(spy.calledOnce, "Handler should be called.");
});

it("should fire BlockComment:after event", function() {
it("should fire BlockComment:exit event", function() {

function handler(node) {
var code = eslint.getSource(node);
Expand All @@ -579,7 +579,7 @@ describe("eslint", function() {

eslint.reset();
eslint.on("BlockComment", spy);
eslint.on("BlockComment:after", spy);
eslint.on("BlockComment:exit", spy);

eslint.verify(code, config, true);
assert(spy.calledTwice, "Handler should be called.");
Expand Down

0 comments on commit f1f453d

Please sign in to comment.