node/tools/eslint/lib/rules/max-statements.js
silverwind d9b8758f47 tools: update ESLint to 2.7.0
PR-URL: https://github.com/nodejs/node/pull/6132
Reviewed-By: Brian White <mscdex@mscdex.net>
Reviewed-By: Jeremiah Senkpiel <fishrock123@rocketmail.com>
Reviewed-By: Rich Trott <rtrott@gmail.com>
Reviewed-By: thefourtheye <thechargingvolcano@gmail.com>
2016-04-20 16:24:21 -07:00

150 lines
4.3 KiB
JavaScript

/**
* @fileoverview A rule to set the maximum number of statements in a function.
* @author Ian Christian Myers
* @copyright 2013 Ian Christian Myers. All rights reserved.
*/
"use strict";
//------------------------------------------------------------------------------
// Rule Definition
//------------------------------------------------------------------------------
module.exports = function(context) {
//--------------------------------------------------------------------------
// Helpers
//--------------------------------------------------------------------------
var functionStack = [],
option = context.options[0],
maxStatements = 10,
ignoreTopLevelFunctions = context.options[1] && context.options[1].ignoreTopLevelFunctions || false,
topLevelFunctions = [];
if (typeof option === "object" && option.hasOwnProperty("maximum") && typeof option.maximum === "number") {
maxStatements = option.maximum;
}
if (typeof option === "object" && option.hasOwnProperty("max") && typeof option.max === "number") {
maxStatements = option.max;
}
if (typeof option === "number") {
maxStatements = option;
}
/**
* Reports a node if it has too many statements
* @param {ASTNode} node node to evaluate
* @param {int} count Number of statements in node
* @param {int} max Maximum number of statements allowed
* @returns {void}
* @private
*/
function reportIfTooManyStatements(node, count, max) {
if (count > max) {
context.report(
node,
"This function has too many statements ({{count}}). Maximum allowed is {{max}}.",
{ count: count, max: max });
}
}
/**
* When parsing a new function, store it in our function stack
* @returns {void}
* @private
*/
function startFunction() {
functionStack.push(0);
}
/**
* Evaluate the node at the end of function
* @param {ASTNode} node node to evaluate
* @returns {void}
* @private
*/
function endFunction(node) {
var count = functionStack.pop();
if (ignoreTopLevelFunctions && functionStack.length === 0) {
topLevelFunctions.push({ node: node, count: count});
} else {
reportIfTooManyStatements(node, count, maxStatements);
}
}
/**
* Increment the count of the functions
* @param {ASTNode} node node to evaluate
* @returns {void}
* @private
*/
function countStatements(node) {
functionStack[functionStack.length - 1] += node.body.length;
}
//--------------------------------------------------------------------------
// Public API
//--------------------------------------------------------------------------
return {
"FunctionDeclaration": startFunction,
"FunctionExpression": startFunction,
"ArrowFunctionExpression": startFunction,
"BlockStatement": countStatements,
"FunctionDeclaration:exit": endFunction,
"FunctionExpression:exit": endFunction,
"ArrowFunctionExpression:exit": endFunction,
"Program:exit": function() {
if (topLevelFunctions.length === 1) {
return;
}
topLevelFunctions.forEach(function(element) {
var count = element.count;
var node = element.node;
reportIfTooManyStatements(node, count, maxStatements);
});
}
};
};
module.exports.schema = [
{
"oneOf": [
{
"type": "integer",
"minimum": 0
},
{
"type": "object",
"properties": {
"maximum": {
"type": "integer",
"minimum": 0
},
"max": {
"type": "integer",
"minimum": 0
}
},
"additionalProperties": false
}
]
},
{
"type": "object",
"properties": {
"ignoreTopLevelFunctions": {
"type": "boolean"
}
},
"additionalProperties": false
}
];