forked from sindresorhus/eslint-plugin-unicorn
-
-
Notifications
You must be signed in to change notification settings - Fork 0
/
boolean.js
83 lines (72 loc) · 1.64 KB
/
boolean.js
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
'use strict';
const isLogicNot = node =>
node &&
node.type === 'UnaryExpression' &&
node.operator === '!';
const isLogicNotArgument = node =>
isLogicNot(node.parent) &&
node.parent.argument === node;
const isBooleanCallArgument = node =>
isBooleanCall(node.parent) &&
node.parent.arguments[0] === node;
const isBooleanCall = node =>
node &&
node.type === 'CallExpression' &&
node.callee &&
node.callee.type === 'Identifier' &&
node.callee.name === 'Boolean' &&
node.arguments.length === 1;
/**
Check if the value of node is a `boolean`.
@param {Node} node
@returns {boolean}
*/
function isBooleanNode(node) {
if (
isLogicNot(node) ||
isLogicNotArgument(node) ||
isBooleanCall(node) ||
isBooleanCallArgument(node)
) {
return true;
}
const {parent} = node;
if (
(
parent.type === 'IfStatement' ||
parent.type === 'ConditionalExpression' ||
parent.type === 'WhileStatement' ||
parent.type === 'DoWhileStatement' ||
parent.type === 'ForStatement'
) &&
parent.test === node
) {
return true;
}
if (parent.type === 'LogicalExpression') {
return isBooleanNode(parent);
}
return false;
}
/**
Get the boolean type-casting ancestor.
@typedef {{ node: Node, isNegative: boolean }} Result
@param {Node} node
@returns {Result}
*/
function getBooleanAncestor(node) {
let isNegative = false;
// eslint-disable-next-line no-constant-condition
while (true) {
if (isLogicNotArgument(node)) {
isNegative = !isNegative;
node = node.parent;
} else if (isBooleanCallArgument(node)) {
node = node.parent;
} else {
break;
}
}
return {node, isNegative};
}
module.exports = {isBooleanNode, getBooleanAncestor};