node/tools/eslint/lib/rules/space-before-blocks.js
Michaël Zasso 2d441493a4 tools: update eslint to v1.10.3
PR-URL: https://github.com/nodejs/io.js/pull/2286
Reviewed-By: Roman Reiss <me@silverwind.io>
2016-01-13 23:15:39 +01:00

132 lines
4.0 KiB
JavaScript
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

/**
* @fileoverview A rule to ensure whitespace before blocks.
* @author Mathias Schreck <https://github.com/lo1tuma>
* @copyright 2014 Mathias Schreck. All rights reserved.
*/
"use strict";
var astUtils = require("../ast-utils");
//------------------------------------------------------------------------------
// Rule Definition
//------------------------------------------------------------------------------
module.exports = function(context) {
var config = context.options[0],
sourceCode = context.getSourceCode(),
checkFunctions = true,
checkKeywords = true;
if (typeof config === "object") {
checkFunctions = config.functions !== "never";
checkKeywords = config.keywords !== "never";
} else if (config === "never") {
checkFunctions = false;
checkKeywords = false;
}
/**
* Checks whether or not a given token is an arrow operator (=>).
*
* @param {Token} token - A token to check.
* @returns {boolean} `true` if the token is an arrow operator.
*/
function isArrow(token) {
return token.type === "Punctuator" && token.value === "=>";
}
/**
* Checks the given BlockStatement node has a preceding space if it doesnt start on a new line.
* @param {ASTNode|Token} node The AST node of a BlockStatement.
* @returns {void} undefined.
*/
function checkPrecedingSpace(node) {
var precedingToken = context.getTokenBefore(node),
hasSpace,
parent,
requireSpace;
if (precedingToken && !isArrow(precedingToken) && astUtils.isTokenOnSameLine(precedingToken, node)) {
hasSpace = sourceCode.isSpaceBetweenTokens(precedingToken, node);
parent = context.getAncestors().pop();
if (parent.type === "FunctionExpression" || parent.type === "FunctionDeclaration") {
requireSpace = checkFunctions;
} else {
requireSpace = checkKeywords;
}
if (requireSpace) {
if (!hasSpace) {
context.report({
node: node,
message: "Missing space before opening brace.",
fix: function(fixer) {
return fixer.insertTextBefore(node, " ");
}
});
}
} else {
if (hasSpace) {
context.report({
node: node,
message: "Unexpected space before opening brace.",
fix: function(fixer) {
return fixer.removeRange([precedingToken.range[1], node.range[0]]);
}
});
}
}
}
}
/**
* Checks if the CaseBlock of an given SwitchStatement node has a preceding space.
* @param {ASTNode} node The node of a SwitchStatement.
* @returns {void} undefined.
*/
function checkSpaceBeforeCaseBlock(node) {
var cases = node.cases,
firstCase,
openingBrace;
if (cases.length > 0) {
firstCase = cases[0];
openingBrace = context.getTokenBefore(firstCase);
} else {
openingBrace = context.getLastToken(node, 1);
}
checkPrecedingSpace(openingBrace);
}
return {
"BlockStatement": checkPrecedingSpace,
"ClassBody": checkPrecedingSpace,
"SwitchStatement": checkSpaceBeforeCaseBlock
};
};
module.exports.schema = [
{
"oneOf": [
{
"enum": ["always", "never"]
},
{
"type": "object",
"properties": {
"keywords": {
"enum": ["always", "never"]
},
"functions": {
"enum": ["always", "never"]
}
},
"additionalProperties": false
}
]
}
];