Skip to content

Commit 26c87d8

Browse files
committed
Fix no-global-jquery returning false positive for var assignment #85
1 parent cf0e27b commit 26c87d8

File tree

4 files changed

+80
-28
lines changed

4 files changed

+80
-28
lines changed

lib/rules/no-global-jquery.js

Lines changed: 14 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -4,18 +4,22 @@
44
'use strict';
55

66
const { getEmberImportBinding } = require('../utils/imports');
7+
const {
8+
isJQueryCallee,
9+
isVariableAssigmentJquery,
10+
JQUERY_ALIASES
11+
} = require('../utils/jquery');
712
const { collectObjectPatternBindings } = require('../utils/destructed-binding');
813

914
const MESSAGE = 'Do not use global `$` or `jQuery`.';
10-
const ALIASES = ['$', 'jQuery'];
1115

1216
/**
1317
* Determines if this expression matches a global jQuery invocation, either `$` or `jQuery`.
1418
* @param {ASTNode} node The identifier node.
1519
* @returns {Boolean} Returns true if the expression matches, otherwise false.
1620
*/
1721
function isGlobalJquery(node) {
18-
return node.callee && ALIASES.includes(node.callee.name);
22+
return node.callee && JQUERY_ALIASES.includes(node.callee.name);
1923
}
2024

2125
module.exports = {
@@ -30,6 +34,7 @@ module.exports = {
3034
create(context) {
3135
let emberImportBinding;
3236
let destructuredAssignment = null;
37+
let jQueryLocalName = null;
3338

3439
function isDestructured(node) {
3540
return node && node.callee && node.callee.name === destructuredAssignment;
@@ -48,8 +53,14 @@ module.exports = {
4853
}
4954
},
5055

56+
VariableDeclarator(node) {
57+
jQueryLocalName = isVariableAssigmentJquery(node);
58+
},
59+
5160
CallExpression(node) {
52-
if (!isDestructured(node) && isGlobalJquery(node)) {
61+
if (jQueryLocalName && !isJQueryCallee(node, jQueryLocalName)) {
62+
return;
63+
} else if (!isDestructured(node) && isGlobalJquery(node)) {
5364
context.report(node, MESSAGE);
5465
}
5566
}

lib/rules/no-jquery-methods.js

Lines changed: 3 additions & 25 deletions
Original file line numberDiff line numberDiff line change
@@ -4,24 +4,12 @@
44
'use strict';
55

66
const { get } = require('../utils/get');
7-
const JQUERY_ALIASES = ['$', 'jQuery'];
7+
const { isJQueryCallee, isVariableAssigmentJquery } = require('../utils/jquery');
88

99
function getMessage(blackListName) {
1010
return `The use of jQuery's ${blackListName} method has been deprecated.`;
1111
}
1212

13-
function isJQueryCaller(node, name = null) {
14-
const calleePropertyNameisJquery = get(node, 'object.callee.property.name') === '$';
15-
const calleeNameIsJquery = get(node, 'object.callee.name') === '$';
16-
const calleeNameIsLocalJquery = get(node, 'object.callee.name') === name;
17-
const ObjectNameisLocalJquery = get(node, 'object.name') === name;
18-
19-
return calleePropertyNameisJquery
20-
|| calleeNameIsJquery
21-
|| calleeNameIsLocalJquery
22-
|| ObjectNameisLocalJquery;
23-
}
24-
2513
function getLocalImportName(node, sourceName) {
2614
if (get(node, 'source.value').includes(sourceName)) {
2715
return get(node, 'specifiers').map((specifier) => specifier.local.name);
@@ -52,17 +40,7 @@ module.exports = {
5240
},
5341

5442
VariableDeclarator(node) {
55-
const varDecIDName = get(node, 'id.name');
56-
// Get the name of what was assigned to the variable.
57-
const varAssignment = get(node, 'init.callee.property.name')
58-
|| get(node, 'init.property.name')
59-
|| get(node, 'init.name')
60-
|| '';
61-
const varAssignmentIsJquery = JQUERY_ALIASES.includes(varAssignment);
62-
63-
if (varAssignmentIsJquery) {
64-
jQueryLocalName = varDecIDName;
65-
}
43+
jQueryLocalName = isVariableAssigmentJquery(node);
6644
},
6745

6846
CallExpression(node) {
@@ -82,7 +60,7 @@ module.exports = {
8260
let blackListName = BLACKLIST.includes(propertyName) ? propertyName : false;
8361
let isThisExpression = get(node, 'object.type').includes('ThisExpression');
8462

85-
if (!isThisExpression && blackListName && isJQueryCaller(node, jQueryLocalName)) {
63+
if (!isThisExpression && blackListName && isJQueryCallee(node, jQueryLocalName)) {
8664
context.report({ node: node.property, message: getMessage(blackListName) });
8765
}
8866
}

lib/utils/jquery.js

Lines changed: 33 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,33 @@
1+
const { get } = require('../utils/get');
2+
3+
const JQUERY_ALIASES = ['$', 'jQuery'];
4+
5+
function isJQueryCallee(node, name = null) {
6+
const calleePropertyNameisJquery = get(node, 'object.callee.property.name') === '$';
7+
const calleeNameIsJquery = get(node, 'object.callee.name') === '$';
8+
const calleeNameIsLocalJquery = get(node, 'object.callee.name') === name;
9+
const ObjectNameisLocalJquery = get(node, 'object.name') === name;
10+
11+
return calleePropertyNameisJquery
12+
|| calleeNameIsJquery
13+
|| calleeNameIsLocalJquery
14+
|| ObjectNameisLocalJquery;
15+
}
16+
17+
function isVariableAssigmentJquery(node) {
18+
const varDecIDName = get(node, 'id.name');
19+
// Get the name of what was assigned to the variable.
20+
const varAssignment = get(node, 'init.callee.property.name')
21+
|| get(node, 'init.property.name')
22+
|| get(node, 'init.name')
23+
|| '';
24+
const varAssignmentIsJquery = JQUERY_ALIASES.includes(varAssignment);
25+
26+
return varAssignmentIsJquery ? varDecIDName : null;
27+
}
28+
29+
module.exports = {
30+
isJQueryCallee,
31+
isVariableAssigmentJquery,
32+
JQUERY_ALIASES
33+
};

tests/lib/rules/no-global-jquery.js

Lines changed: 30 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,36 @@ const parserOptions = {
99

1010
ruleTester.run('no-global-jquery', rule, {
1111
valid: [
12+
{
13+
code: `
14+
import Ember from 'ember';
15+
const $ = Ember.$;
16+
17+
export default Ember.Component({
18+
func() {
19+
$('.class').focus();
20+
}
21+
});`,
22+
parserOptions,
23+
errors: [{
24+
message: MESSAGE
25+
}]
26+
},
27+
{
28+
code: `
29+
import Ember from 'ember';
30+
const jQuery = Ember.$;
31+
32+
export default Ember.Component({
33+
func() {
34+
jQuery('.class').focus();
35+
}
36+
});`,
37+
parserOptions,
38+
errors: [{
39+
message: MESSAGE
40+
}]
41+
},
1242
{
1343
code: `
1444
export default Ember.Component({

0 commit comments

Comments
 (0)