Skip to content

Commit

Permalink
Chore: Add metadata to existing rules - Batch 5 (refs eslint#5417)
Browse files Browse the repository at this point in the history
Chore: Add metadata to existing rules - Batch 5 (refs eslint#5417)
  • Loading branch information
vitorbal committed Apr 23, 2016
1 parent fc78e78 commit f827f72
Show file tree
Hide file tree
Showing 40 changed files with 2,509 additions and 2,106 deletions.
46 changes: 28 additions & 18 deletions lib/rules/no-octal-escape.js
Expand Up @@ -9,31 +9,41 @@
// Rule Definition
//------------------------------------------------------------------------------

module.exports = function(context) {
module.exports = {
meta: {
docs: {
description: "disallow octal escape sequences in string literals",
category: "Best Practices",
recommended: false
},

return {
schema: []
},

Literal: function(node) {
if (typeof node.value !== "string") {
return;
}
create: function(context) {

return {

var match = node.raw.match(/^([^\\]|\\[^0-7])*\\([0-3][0-7]{1,2}|[4-7][0-7]|[0-7])/),
octalDigit;
Literal: function(node) {
if (typeof node.value !== "string") {
return;
}

if (match) {
octalDigit = match[2];
var match = node.raw.match(/^([^\\]|\\[^0-7])*\\([0-3][0-7]{1,2}|[4-7][0-7]|[0-7])/),
octalDigit;

// \0 is actually not considered an octal
if (match[2] !== "0" || typeof match[3] !== "undefined") {
context.report(node, "Don't use octal: '\\{{octalDigit}}'. Use '\\u....' instead.",
{ octalDigit: octalDigit });
if (match) {
octalDigit = match[2];

// \0 is actually not considered an octal
if (match[2] !== "0" || typeof match[3] !== "undefined") {
context.report(node, "Don't use octal: '\\{{octalDigit}}'. Use '\\u....' instead.",
{ octalDigit: octalDigit });
}
}
}
}

};
};

}
};

module.exports.schema = [];
28 changes: 19 additions & 9 deletions lib/rules/no-octal.js
Expand Up @@ -9,17 +9,27 @@
// Rule Definition
//------------------------------------------------------------------------------

module.exports = function(context) {
module.exports = {
meta: {
docs: {
description: "disallow octal literals",
category: "Best Practices",
recommended: true
},

return {
schema: []
},

Literal: function(node) {
if (typeof node.value === "number" && /^0[0-7]/.test(node.raw)) {
context.report(node, "Octal literals should not be used.");
create: function(context) {

return {

Literal: function(node) {
if (typeof node.value === "number" && /^0[0-7]/.test(node.raw)) {
context.report(node, "Octal literals should not be used.");
}
}
}
};
};

}
};

module.exports.schema = [];
232 changes: 121 additions & 111 deletions lib/rules/no-param-reassign.js
Expand Up @@ -10,128 +10,138 @@

var stopNodePattern = /(?:Statement|Declaration|Function(?:Expression)?|Program)$/;

module.exports = function(context) {
var props = context.options[0] && Boolean(context.options[0].props);

/**
* Checks whether or not the reference modifies properties of its variable.
* @param {Reference} reference - A reference to check.
* @returns {boolean} Whether or not the reference modifies properties of its variable.
*/
function isModifyingProp(reference) {
var node = reference.identifier;
var parent = node.parent;

while (parent && !stopNodePattern.test(parent.type)) {
switch (parent.type) {

// e.g. foo.a = 0;
case "AssignmentExpression":
return parent.left === node;

// e.g. ++foo.a;
case "UpdateExpression":
return true;

// e.g. delete foo.a;
case "UnaryExpression":
if (parent.operator === "delete") {
module.exports = {
meta: {
docs: {
description: "disallow reassigning `function` parameters",
category: "Best Practices",
recommended: false
},

schema: [
{
type: "object",
properties: {
props: {type: "boolean"}
},
additionalProperties: false
}
]
},

create: function(context) {
var props = context.options[0] && Boolean(context.options[0].props);

/**
* Checks whether or not the reference modifies properties of its variable.
* @param {Reference} reference - A reference to check.
* @returns {boolean} Whether or not the reference modifies properties of its variable.
*/
function isModifyingProp(reference) {
var node = reference.identifier;
var parent = node.parent;

while (parent && !stopNodePattern.test(parent.type)) {
switch (parent.type) {

// e.g. foo.a = 0;
case "AssignmentExpression":
return parent.left === node;

// e.g. ++foo.a;
case "UpdateExpression":
return true;
}
break;

// EXCLUDES: e.g. cache.get(foo.a).b = 0;
case "CallExpression":
if (parent.callee !== node) {
return false;
}
break;

// EXCLUDES: e.g. cache[foo.a] = 0;
case "MemberExpression":
if (parent.property === node) {
return false;
}
break;

default:
break;

// e.g. delete foo.a;
case "UnaryExpression":
if (parent.operator === "delete") {
return true;
}
break;

// EXCLUDES: e.g. cache.get(foo.a).b = 0;
case "CallExpression":
if (parent.callee !== node) {
return false;
}
break;

// EXCLUDES: e.g. cache[foo.a] = 0;
case "MemberExpression":
if (parent.property === node) {
return false;
}
break;

default:
break;
}

node = parent;
parent = node.parent;
}

node = parent;
parent = node.parent;
return false;
}

return false;
}

/**
* Reports a reference if is non initializer and writable.
* @param {Reference} reference - A reference to check.
* @param {int} index - The index of the reference in the references.
* @param {Reference[]} references - The array that the reference belongs to.
* @returns {void}
*/
function checkReference(reference, index, references) {
var identifier = reference.identifier;

if (identifier &&
!reference.init &&

// Destructuring assignments can have multiple default value,
// so possibly there are multiple writeable references for the same identifier.
(index === 0 || references[index - 1].identifier !== identifier)
) {
if (reference.isWrite()) {
context.report(
identifier,
"Assignment to function parameter '{{name}}'.",
{name: identifier.name});
} else if (props && isModifyingProp(reference)) {
context.report(
identifier,
"Assignment to property of function parameter '{{name}}'.",
{name: identifier.name});
/**
* Reports a reference if is non initializer and writable.
* @param {Reference} reference - A reference to check.
* @param {int} index - The index of the reference in the references.
* @param {Reference[]} references - The array that the reference belongs to.
* @returns {void}
*/
function checkReference(reference, index, references) {
var identifier = reference.identifier;

if (identifier &&
!reference.init &&

// Destructuring assignments can have multiple default value,
// so possibly there are multiple writeable references for the same identifier.
(index === 0 || references[index - 1].identifier !== identifier)
) {
if (reference.isWrite()) {
context.report(
identifier,
"Assignment to function parameter '{{name}}'.",
{name: identifier.name});
} else if (props && isModifyingProp(reference)) {
context.report(
identifier,
"Assignment to property of function parameter '{{name}}'.",
{name: identifier.name});
}
}
}
}

/**
* Finds and reports references that are non initializer and writable.
* @param {Variable} variable - A variable to check.
* @returns {void}
*/
function checkVariable(variable) {
if (variable.defs[0].type === "Parameter") {
variable.references.forEach(checkReference);
/**
* Finds and reports references that are non initializer and writable.
* @param {Variable} variable - A variable to check.
* @returns {void}
*/
function checkVariable(variable) {
if (variable.defs[0].type === "Parameter") {
variable.references.forEach(checkReference);
}
}
}

/**
* Checks parameters of a given function node.
* @param {ASTNode} node - A function node to check.
* @returns {void}
*/
function checkForFunction(node) {
context.getDeclaredVariables(node).forEach(checkVariable);
}
/**
* Checks parameters of a given function node.
* @param {ASTNode} node - A function node to check.
* @returns {void}
*/
function checkForFunction(node) {
context.getDeclaredVariables(node).forEach(checkVariable);
}

return {
return {

// `:exit` is needed for the `node.parent` property of identifier nodes.
"FunctionDeclaration:exit": checkForFunction,
"FunctionExpression:exit": checkForFunction,
"ArrowFunctionExpression:exit": checkForFunction
};
// `:exit` is needed for the `node.parent` property of identifier nodes.
"FunctionDeclaration:exit": checkForFunction,
"FunctionExpression:exit": checkForFunction,
"ArrowFunctionExpression:exit": checkForFunction
};

};

module.exports.schema = [
{
type: "object",
properties: {
props: {type: "boolean"}
},
additionalProperties: false
}
];
};

0 comments on commit f827f72

Please sign in to comment.