]>
git.proxmox.com Git - pve-eslint.git/blob - eslint/lib/rules/id-denylist.js
2 * @fileoverview Rule that warns when identifier names that are
3 * specified in the configuration are used.
4 * @author Keith Cirkel (http://keithcirkel.co.uk)
9 //------------------------------------------------------------------------------
11 //------------------------------------------------------------------------------
14 * Checks whether the given node represents assignment target in a normal assignment or destructuring.
15 * @param {ASTNode} node The node to check.
16 * @returns {boolean} `true` if the node is assignment target.
18 function isAssignmentTarget(node
) {
19 const parent
= node
.parent
;
25 parent
.type
=== "AssignmentExpression" &&
30 parent
.type
=== "ArrayPattern" ||
31 parent
.type
=== "RestElement" ||
33 parent
.type
=== "Property" &&
34 parent
.value
=== node
&&
35 parent
.parent
.type
=== "ObjectPattern"
38 parent
.type
=== "AssignmentPattern" &&
45 * Checks whether the given node represents an imported name that is renamed in the same import/export specifier.
48 * import { a as b } from 'mod'; // node `a` is renamed import
49 * export { a as b } from 'mod'; // node `a` is renamed import
50 * @param {ASTNode} node `Identifier` node to check.
51 * @returns {boolean} `true` if the node is a renamed import.
53 function isRenamedImport(node
) {
54 const parent
= node
.parent
;
58 parent
.type
=== "ImportSpecifier" &&
59 parent
.imported
!== parent
.local
&&
60 parent
.imported
=== node
63 parent
.type
=== "ExportSpecifier" &&
64 parent
.parent
.source
&& // re-export
65 parent
.local
!== parent
.exported
&&
72 * Checks whether the given node is an ObjectPattern destructuring.
75 * const { a : b } = foo;
76 * @param {ASTNode} node `Identifier` node to check.
77 * @returns {boolean} `true` if the node is in an ObjectPattern destructuring.
79 function isPropertyNameInDestructuring(node
) {
80 const parent
= node
.parent
;
85 parent
.type
=== "Property" &&
86 parent
.parent
.type
=== "ObjectPattern" &&
92 //------------------------------------------------------------------------------
94 //------------------------------------------------------------------------------
96 /** @type {import('../shared/types').Rule} */
102 description
: "Disallow specified identifiers",
104 url
: "https://eslint.org/docs/latest/rules/id-denylist"
115 restricted
: "Identifier '{{name}}' is restricted.",
116 restrictedPrivate
: "Identifier '#{{name}}' is restricted."
122 const denyList
= new Set(context
.options
);
123 const reportedNodes
= new Set();
124 const sourceCode
= context
.sourceCode
;
129 * Checks whether the given name is restricted.
130 * @param {string} name The name to check.
131 * @returns {boolean} `true` if the name is restricted.
134 function isRestricted(name
) {
135 return denyList
.has(name
);
139 * Checks whether the given node represents a reference to a global variable that is not declared in the source code.
140 * These identifiers will be allowed, as it is assumed that user has no control over the names of external global variables.
141 * @param {ASTNode} node `Identifier` node to check.
142 * @returns {boolean} `true` if the node is a reference to a global variable.
144 function isReferenceToGlobalVariable(node
) {
145 const variable
= globalScope
.set.get(node
.name
);
147 return variable
&& variable
.defs
.length
=== 0 &&
148 variable
.references
.some(ref
=> ref
.identifier
=== node
);
152 * Determines whether the given node should be checked.
153 * @param {ASTNode} node `Identifier` node.
154 * @returns {boolean} `true` if the node should be checked.
156 function shouldCheck(node
) {
157 const parent
= node
.parent
;
160 * Member access has special rules for checking property names.
161 * Read access to a property with a restricted name is allowed, because it can be on an object that user has no control over.
162 * Write access isn't allowed, because it potentially creates a new property with a restricted name.
165 parent
.type
=== "MemberExpression" &&
166 parent
.property
=== node
&&
169 return isAssignmentTarget(parent
);
173 parent
.type
!== "CallExpression" &&
174 parent
.type
!== "NewExpression" &&
175 !isRenamedImport(node
) &&
176 !isPropertyNameInDestructuring(node
) &&
177 !isReferenceToGlobalVariable(node
)
182 * Reports an AST node as a rule violation.
183 * @param {ASTNode} node The node to report.
187 function report(node
) {
190 * We used the range instead of the node because it's possible
191 * for the same identifier to be represented by two different
192 * nodes, with the most clear example being shorthand properties:
194 * In this case, "foo" is represented by one node for the name
195 * and one for the value. The only way to know they are the same
196 * is to look at the range.
198 if (!reportedNodes
.has(node
.range
.toString())) {
199 const isPrivate
= node
.type
=== "PrivateIdentifier";
203 messageId
: isPrivate
? "restrictedPrivate" : "restricted",
208 reportedNodes
.add(node
.range
.toString());
215 globalScope
= sourceCode
.getScope(node
);
222 if (isRestricted(node
.name
) && shouldCheck(node
)) {