@hapi/eslint-plugin
Version:
ESLint plugin containing hapi style guide rules and config
76 lines (55 loc) • 2.04 kB
JavaScript
// Based on https://github.com/eslint/eslint/blob/master/lib/rules/no-var.js
;
const internals = {
scopeTypes: new Set(['Program', 'BlockStatement', 'SwitchStatement', 'ForStatement', 'ForInStatement', 'ForOfStatement'])
};
module.exports = {
meta: {
type: 'suggestion',
docs: {
description: 'require `let` or `const` instead of `var` when outside of try...catch',
category: 'ECMAScript 6',
recommended: true
},
schema: [],
messages: {
unexpectedVar: 'Unexpected var, use let or const instead.'
}
},
create(context) {
const sourceCode = context.sourceCode ?? context.getSourceCode();
const check = (node) => {
if (node.parent.parent &&
(node.parent.parent.type === 'TryStatement' ||
node.parent.parent.type === 'CatchClause')) {
const variables = sourceCode.getDeclaredVariables ? sourceCode.getDeclaredVariables(node, context) : context.getDeclaredVariables();
const scopeNode = internals.getScopeNode(node);
if (variables.some(internals.isUsedFromOutsideOf(scopeNode))) {
return;
}
}
context.report({ node, messageId: 'unexpectedVar' });
};
return {
'VariableDeclaration:exit'(node) {
if (node.kind === 'var') {
check(node);
}
}
};
}
};
internals.getScopeNode = function (node) {
if (internals.scopeTypes.has(node.type)) {
return node;
}
return internals.getScopeNode(node.parent);
};
internals.isUsedFromOutsideOf = function (scopeNode) {
const isOutsideOfScope = (reference) => {
const scope = scopeNode.range;
const id = reference.identifier.range;
return id[0] < scope[0] || id[1] > scope[1];
};
return (variable) => variable.references.some(isOutsideOfScope);
};