@eslint-react/var 2.0.0-next.146 → 2.0.0-next.148

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (3) hide show
  1. package/dist/index.d.ts +60 -55
  2. package/dist/index.js +242 -231
  3. package/package.json +8 -8
package/dist/index.d.ts CHANGED
@@ -1,6 +1,8 @@
1
- import { unit } from '@eslint-react/eff';
2
- import { Scope, Variable } from '@typescript-eslint/scope-manager';
3
- import { TSESTree } from '@typescript-eslint/types';
1
+ import { unit } from "@eslint-react/eff";
2
+ import { Scope, Variable } from "@typescript-eslint/scope-manager";
3
+ import { TSESTree } from "@typescript-eslint/types";
4
+
5
+ //#region src/var-collect.d.ts
4
6
 
5
7
  /**
6
8
  * Get all variables from the given scope up to the global scope
@@ -9,42 +11,43 @@ import { TSESTree } from '@typescript-eslint/types';
9
11
  */
10
12
  declare function getVariables(initialScope: Scope): Variable[];
11
13
  declare const findVariable: {
12
- (initialScope: Scope): (nameOrNode: string | TSESTree.Identifier | unit) => Variable | unit;
13
- (nameOrNode: string | TSESTree.Identifier | unit, initialScope: Scope): Variable | unit;
14
+ (initialScope: Scope): (nameOrNode: string | TSESTree.Identifier | unit) => Variable | unit;
15
+ (nameOrNode: string | TSESTree.Identifier | unit, initialScope: Scope): Variable | unit;
14
16
  };
15
17
  declare function findPropertyInProperties(name: string, properties: (TSESTree.Property | TSESTree.RestElement | TSESTree.SpreadElement)[], initialScope: Scope, seen?: Set<string>): (typeof properties)[number] | unit;
16
-
18
+ //#endregion
19
+ //#region src/var-construction.d.ts
17
20
  declare const ConstructionDetectionHint: {
18
- None: bigint;
19
- StrictCallExpression: bigint;
21
+ None: bigint;
22
+ StrictCallExpression: bigint;
20
23
  };
21
24
  type Construction = {
22
- kind: "ArrayExpression";
23
- node: TSESTree.ArrayExpression;
25
+ kind: "ArrayExpression";
26
+ node: TSESTree.ArrayExpression;
24
27
  } | {
25
- kind: "CallExpression";
26
- node: TSESTree.CallExpression;
28
+ kind: "CallExpression";
29
+ node: TSESTree.CallExpression;
27
30
  } | {
28
- kind: "ClassExpression";
29
- node: TSESTree.ClassExpression;
31
+ kind: "ClassExpression";
32
+ node: TSESTree.ClassExpression;
30
33
  } | {
31
- kind: "FunctionDeclaration";
32
- node: TSESTree.FunctionDeclaration;
34
+ kind: "FunctionDeclaration";
35
+ node: TSESTree.FunctionDeclaration;
33
36
  } | {
34
- kind: "FunctionExpression";
35
- node: TSESTree.FunctionExpression | TSESTree.ArrowFunctionExpression;
37
+ kind: "FunctionExpression";
38
+ node: TSESTree.FunctionExpression | TSESTree.ArrowFunctionExpression;
36
39
  } | {
37
- kind: "JSXElement";
38
- node: TSESTree.JSXElement | TSESTree.JSXFragment;
40
+ kind: "JSXElement";
41
+ node: TSESTree.JSXElement | TSESTree.JSXFragment;
39
42
  } | {
40
- kind: "NewExpression";
41
- node: TSESTree.NewExpression;
43
+ kind: "NewExpression";
44
+ node: TSESTree.NewExpression;
42
45
  } | {
43
- kind: "ObjectExpression";
44
- node: TSESTree.ObjectExpression;
46
+ kind: "ObjectExpression";
47
+ node: TSESTree.ObjectExpression;
45
48
  } | {
46
- kind: "RegExpLiteral";
47
- node: TSESTree.RegExpLiteral;
49
+ kind: "RegExpLiteral";
50
+ node: TSESTree.RegExpLiteral;
48
51
  };
49
52
  /**
50
53
  * Detects the construction type of a given node.
@@ -54,39 +57,44 @@ type Construction = {
54
57
  * @returns The construction type of the node, or `_` if not found.
55
58
  */
56
59
  declare function getConstruction(node: TSESTree.Node | unit, initialScope: Scope, hint?: bigint): Construction | unit;
57
-
60
+ //#endregion
61
+ //#region src/var-declarator-id.d.ts
58
62
  declare function getVariableDeclaratorId(node: TSESTree.Node | unit, prev?: TSESTree.Node): TSESTree.BindingName | TSESTree.Expression | unit;
59
-
63
+ //#endregion
64
+ //#region src/var-init-node.d.ts
60
65
  declare function getVariableInitNode(variable: Variable | unit, at: number): unit | TSESTree.ClassDeclaration | TSESTree.ClassDeclarationWithName | TSESTree.ClassDeclarationWithOptionalName | TSESTree.Expression | TSESTree.FunctionDeclaration | TSESTree.FunctionDeclarationWithName | TSESTree.FunctionDeclarationWithOptionalName;
61
-
66
+ //#endregion
67
+ //#region src/var-scope.d.ts
62
68
  declare function getChidScopes(scope: Scope): readonly Scope[];
63
-
69
+ //#endregion
70
+ //#region src/var-value.d.ts
64
71
  type LazyValue = {
65
- kind: "lazy";
66
- node: TSESTree.Node;
67
- initialScope: Scope | unit;
72
+ kind: "lazy";
73
+ node: TSESTree.Node;
74
+ initialScope: Scope | unit;
68
75
  } | {
69
- kind: "none";
70
- node: TSESTree.Node;
71
- initialScope: Scope | unit;
76
+ kind: "none";
77
+ node: TSESTree.Node;
78
+ initialScope: Scope | unit;
72
79
  } | {
73
- kind: "some";
74
- node: TSESTree.Node;
75
- value: unknown;
76
- initialScope: Scope | unit;
80
+ kind: "some";
81
+ node: TSESTree.Node;
82
+ value: unknown;
83
+ initialScope: Scope | unit;
77
84
  };
78
85
  declare function toStaticValue(lazyValue: LazyValue): {
79
- readonly kind: "none";
80
- readonly node: TSESTree.Node;
81
- readonly initialScope: Scope | undefined;
82
- readonly value?: never;
86
+ readonly kind: "none";
87
+ readonly node: TSESTree.Node;
88
+ readonly initialScope: Scope | undefined;
89
+ readonly value?: never;
83
90
  } | {
84
- readonly kind: "some";
85
- readonly node: TSESTree.Node;
86
- readonly initialScope: Scope | undefined;
87
- readonly value: unknown;
91
+ readonly kind: "some";
92
+ readonly node: TSESTree.Node;
93
+ readonly initialScope: Scope | undefined;
94
+ readonly value: unknown;
88
95
  };
89
-
96
+ //#endregion
97
+ //#region src/var-value-equal.d.ts
90
98
  /**
91
99
  * Determines whether node value equals to another node value
92
100
  * @param a node to compare
@@ -94,9 +102,6 @@ declare function toStaticValue(lazyValue: LazyValue): {
94
102
  * @param initialScopes initial scopes of the two nodes
95
103
  * @returns `true` if node value equal
96
104
  */
97
- declare function isNodeValueEqual(a: TSESTree.Node, b: TSESTree.Node, initialScopes: [
98
- aScope: Scope,
99
- bScope: Scope
100
- ]): boolean;
101
-
102
- export { type Construction, ConstructionDetectionHint, type LazyValue, findPropertyInProperties, findVariable, getChidScopes, getConstruction, getVariableDeclaratorId, getVariableInitNode, getVariables, isNodeValueEqual, toStaticValue };
105
+ declare function isNodeValueEqual(a: TSESTree.Node, b: TSESTree.Node, initialScopes: [aScope: Scope, bScope: Scope]): boolean;
106
+ //#endregion
107
+ export { Construction, ConstructionDetectionHint, LazyValue, findPropertyInProperties, findVariable, getChidScopes, getConstruction, getVariableDeclaratorId, getVariableInitNode, getVariables, isNodeValueEqual, toStaticValue };
package/dist/index.js CHANGED
@@ -1,256 +1,267 @@
1
- import { dual, unit } from '@eslint-react/eff';
2
- import { DefinitionType, ScopeType } from '@typescript-eslint/scope-manager';
3
- import { AST_NODE_TYPES } from '@typescript-eslint/types';
4
- import * as ASTUtils from '@typescript-eslint/utils/ast-utils';
5
- import { getStaticValue } from '@typescript-eslint/utils/ast-utils';
6
- import * as AST from '@eslint-react/ast';
1
+ import { dual, unit } from "@eslint-react/eff";
2
+ import { DefinitionType, ScopeType } from "@typescript-eslint/scope-manager";
3
+ import { AST_NODE_TYPES } from "@typescript-eslint/types";
4
+ import * as ASTUtils from "@typescript-eslint/utils/ast-utils";
5
+ import { getStaticValue } from "@typescript-eslint/utils/ast-utils";
6
+ import * as AST from "@eslint-react/ast";
7
7
 
8
- // src/var-collect.ts
8
+ //#region src/var-init-node.ts
9
9
  function getVariableInitNode(variable, at) {
10
- if (variable == null) return unit;
11
- const def = variable.defs.at(at);
12
- if (def == null) return unit;
13
- switch (true) {
14
- case (def.type === DefinitionType.FunctionName && def.node.type === AST_NODE_TYPES.FunctionDeclaration):
15
- return def.node;
16
- case (def.type === DefinitionType.ClassName && def.node.type === AST_NODE_TYPES.ClassDeclaration):
17
- return def.node;
18
- case ("init" in def.node && def.node.init != null && !("declarations" in def.node.init)):
19
- return def.node.init;
20
- default:
21
- return unit;
22
- }
10
+ if (variable == null) return unit;
11
+ const def = variable.defs.at(at);
12
+ if (def == null) return unit;
13
+ switch (true) {
14
+ case def.type === DefinitionType.FunctionName && def.node.type === AST_NODE_TYPES.FunctionDeclaration: return def.node;
15
+ case def.type === DefinitionType.ClassName && def.node.type === AST_NODE_TYPES.ClassDeclaration: return def.node;
16
+ case "init" in def.node && def.node.init != null && !("declarations" in def.node.init): return def.node.init;
17
+ default: return unit;
18
+ }
23
19
  }
24
20
 
25
- // src/var-collect.ts
21
+ //#endregion
22
+ //#region src/var-collect.ts
23
+ /**
24
+ * Get all variables from the given scope up to the global scope
25
+ * @param initialScope The scope to start from
26
+ * @returns All variables from the given scope up to the global scope
27
+ */
26
28
  function getVariables(initialScope) {
27
- let scope = initialScope;
28
- const variables = [...scope.variables];
29
- while (scope.type !== ScopeType.global) {
30
- scope = scope.upper;
31
- variables.push(...scope.variables);
32
- }
33
- return variables.reverse();
29
+ let scope = initialScope;
30
+ const variables = [...scope.variables];
31
+ while (scope.type !== ScopeType.global) {
32
+ scope = scope.upper;
33
+ variables.push(...scope.variables);
34
+ }
35
+ return variables.reverse();
34
36
  }
35
- var findVariable2 = dual(2, (nameOrNode, initialScope) => {
36
- if (nameOrNode == null) return unit;
37
- return ASTUtils.findVariable(initialScope, nameOrNode) ?? unit;
37
+ const findVariable = dual(2, (nameOrNode, initialScope) => {
38
+ if (nameOrNode == null) return unit;
39
+ return ASTUtils.findVariable(initialScope, nameOrNode) ?? unit;
38
40
  });
39
41
  function findPropertyInProperties(name, properties, initialScope, seen = /* @__PURE__ */ new Set()) {
40
- return properties.findLast((prop) => {
41
- if (prop.type === AST_NODE_TYPES.Property) {
42
- return "name" in prop.key && prop.key.name === name;
43
- }
44
- if (prop.type === AST_NODE_TYPES.SpreadElement) {
45
- switch (prop.argument.type) {
46
- case AST_NODE_TYPES.Identifier: {
47
- if (seen.has(prop.argument.name)) return false;
48
- const variable = findVariable2(prop.argument.name, initialScope);
49
- const variableNode = getVariableInitNode(variable, 0);
50
- if (variableNode?.type === AST_NODE_TYPES.ObjectExpression) {
51
- seen.add(prop.argument.name);
52
- return findPropertyInProperties(
53
- name,
54
- variableNode.properties,
55
- initialScope,
56
- seen
57
- ) != null;
58
- }
59
- return false;
60
- }
61
- case AST_NODE_TYPES.ObjectExpression: {
62
- return findPropertyInProperties(
63
- name,
64
- prop.argument.properties,
65
- initialScope,
66
- seen
67
- ) != null;
68
- }
69
- default:
70
- return false;
71
- }
72
- }
73
- return false;
74
- });
42
+ return properties.findLast((prop) => {
43
+ if (prop.type === AST_NODE_TYPES.Property) return "name" in prop.key && prop.key.name === name;
44
+ if (prop.type === AST_NODE_TYPES.SpreadElement) switch (prop.argument.type) {
45
+ case AST_NODE_TYPES.Identifier: {
46
+ if (seen.has(prop.argument.name)) return false;
47
+ const variable = findVariable(prop.argument.name, initialScope);
48
+ const variableNode = getVariableInitNode(variable, 0);
49
+ if (variableNode?.type === AST_NODE_TYPES.ObjectExpression) {
50
+ seen.add(prop.argument.name);
51
+ return findPropertyInProperties(name, variableNode.properties, initialScope, seen) != null;
52
+ }
53
+ return false;
54
+ }
55
+ case AST_NODE_TYPES.ObjectExpression: return findPropertyInProperties(name, prop.argument.properties, initialScope, seen) != null;
56
+ default: return false;
57
+ }
58
+ return false;
59
+ });
75
60
  }
76
- var ConstructionDetectionHint = {
77
- None: 0n,
78
- StrictCallExpression: 1n << 0n
61
+
62
+ //#endregion
63
+ //#region src/var-construction.ts
64
+ const ConstructionDetectionHint = {
65
+ None: 0n,
66
+ StrictCallExpression: 1n << 0n
79
67
  };
68
+ /**
69
+ * Detects the construction type of a given node.
70
+ * @param node The node to check.
71
+ * @param initialScope The initial scope to check for variable declarations.
72
+ * @param hint Optional hint to control the detection behavior.
73
+ * @returns The construction type of the node, or `_` if not found.
74
+ */
80
75
  function getConstruction(node, initialScope, hint = ConstructionDetectionHint.None) {
81
- if (node == null) return unit;
82
- switch (node.type) {
83
- case AST_NODE_TYPES.JSXElement:
84
- case AST_NODE_TYPES.JSXFragment:
85
- return { kind: "JSXElement", node };
86
- case AST_NODE_TYPES.ArrayExpression:
87
- return { kind: "ArrayExpression", node };
88
- case AST_NODE_TYPES.ObjectExpression:
89
- return { kind: "ObjectExpression", node };
90
- case AST_NODE_TYPES.ClassExpression:
91
- return { kind: "ClassExpression", node };
92
- case AST_NODE_TYPES.NewExpression:
93
- return { kind: "NewExpression", node };
94
- case AST_NODE_TYPES.FunctionExpression:
95
- case AST_NODE_TYPES.ArrowFunctionExpression:
96
- return { kind: "FunctionExpression", node };
97
- case AST_NODE_TYPES.CallExpression: {
98
- if (hint & ConstructionDetectionHint.StrictCallExpression) {
99
- return { kind: "CallExpression", node };
100
- }
101
- return unit;
102
- }
103
- case AST_NODE_TYPES.MemberExpression: {
104
- if (!("object" in node)) return unit;
105
- return getConstruction(node.object, initialScope, hint);
106
- }
107
- case AST_NODE_TYPES.AssignmentExpression:
108
- case AST_NODE_TYPES.AssignmentPattern: {
109
- if (!("right" in node)) return unit;
110
- return getConstruction(node.right, initialScope, hint);
111
- }
112
- case AST_NODE_TYPES.LogicalExpression: {
113
- const lvc = getConstruction(node.left, initialScope, hint);
114
- if (lvc == null) return unit;
115
- return getConstruction(node.right, initialScope, hint);
116
- }
117
- case AST_NODE_TYPES.ConditionalExpression: {
118
- const cvc = getConstruction(node.consequent, initialScope, hint);
119
- if (cvc == null) return unit;
120
- return getConstruction(node.alternate, initialScope, hint);
121
- }
122
- case AST_NODE_TYPES.Identifier: {
123
- if (!("name" in node) || typeof node.name !== "string") {
124
- return unit;
125
- }
126
- const variable = initialScope.set.get(node.name);
127
- const variableNode = getVariableInitNode(variable, -1);
128
- return getConstruction(variableNode, initialScope, hint);
129
- }
130
- case AST_NODE_TYPES.Literal: {
131
- if ("regex" in node) {
132
- return { kind: "RegExpLiteral", node };
133
- }
134
- return unit;
135
- }
136
- default: {
137
- if (!("expression" in node) || typeof node.expression !== "object") {
138
- return unit;
139
- }
140
- return getConstruction(node.expression, initialScope, hint);
141
- }
142
- }
76
+ if (node == null) return unit;
77
+ switch (node.type) {
78
+ case AST_NODE_TYPES.JSXElement:
79
+ case AST_NODE_TYPES.JSXFragment: return {
80
+ kind: "JSXElement",
81
+ node
82
+ };
83
+ case AST_NODE_TYPES.ArrayExpression: return {
84
+ kind: "ArrayExpression",
85
+ node
86
+ };
87
+ case AST_NODE_TYPES.ObjectExpression: return {
88
+ kind: "ObjectExpression",
89
+ node
90
+ };
91
+ case AST_NODE_TYPES.ClassExpression: return {
92
+ kind: "ClassExpression",
93
+ node
94
+ };
95
+ case AST_NODE_TYPES.NewExpression: return {
96
+ kind: "NewExpression",
97
+ node
98
+ };
99
+ case AST_NODE_TYPES.FunctionExpression:
100
+ case AST_NODE_TYPES.ArrowFunctionExpression: return {
101
+ kind: "FunctionExpression",
102
+ node
103
+ };
104
+ case AST_NODE_TYPES.CallExpression:
105
+ if (hint & ConstructionDetectionHint.StrictCallExpression) return {
106
+ kind: "CallExpression",
107
+ node
108
+ };
109
+ return unit;
110
+ case AST_NODE_TYPES.MemberExpression:
111
+ if (!("object" in node)) return unit;
112
+ return getConstruction(node.object, initialScope, hint);
113
+ case AST_NODE_TYPES.AssignmentExpression:
114
+ case AST_NODE_TYPES.AssignmentPattern:
115
+ if (!("right" in node)) return unit;
116
+ return getConstruction(node.right, initialScope, hint);
117
+ case AST_NODE_TYPES.LogicalExpression: {
118
+ const lvc = getConstruction(node.left, initialScope, hint);
119
+ if (lvc == null) return unit;
120
+ return getConstruction(node.right, initialScope, hint);
121
+ }
122
+ case AST_NODE_TYPES.ConditionalExpression: {
123
+ const cvc = getConstruction(node.consequent, initialScope, hint);
124
+ if (cvc == null) return unit;
125
+ return getConstruction(node.alternate, initialScope, hint);
126
+ }
127
+ case AST_NODE_TYPES.Identifier: {
128
+ if (!("name" in node) || typeof node.name !== "string") return unit;
129
+ const variable = initialScope.set.get(node.name);
130
+ const variableNode = getVariableInitNode(variable, -1);
131
+ return getConstruction(variableNode, initialScope, hint);
132
+ }
133
+ case AST_NODE_TYPES.Literal:
134
+ if ("regex" in node) return {
135
+ kind: "RegExpLiteral",
136
+ node
137
+ };
138
+ return unit;
139
+ default:
140
+ if (!("expression" in node) || typeof node.expression !== "object") return unit;
141
+ return getConstruction(node.expression, initialScope, hint);
142
+ }
143
143
  }
144
+
145
+ //#endregion
146
+ //#region src/var-declarator-id.ts
144
147
  function getVariableDeclaratorId(node, prev) {
145
- if (node == null) return unit;
146
- switch (true) {
147
- case (node.type === AST_NODE_TYPES.VariableDeclarator && node.init === prev):
148
- return node.id;
149
- case (node.type === AST_NODE_TYPES.AssignmentExpression && node.right === prev):
150
- return node.left;
151
- case (node.type === AST_NODE_TYPES.BlockStatement || node.type === AST_NODE_TYPES.Program || node.parent === node):
152
- return unit;
153
- default:
154
- return getVariableDeclaratorId(node.parent, node);
155
- }
148
+ if (node == null) return unit;
149
+ switch (true) {
150
+ case node.type === AST_NODE_TYPES.VariableDeclarator && node.init === prev: return node.id;
151
+ case node.type === AST_NODE_TYPES.AssignmentExpression && node.right === prev: return node.left;
152
+ case node.type === AST_NODE_TYPES.BlockStatement || node.type === AST_NODE_TYPES.Program || node.parent === node: return unit;
153
+ default: return getVariableDeclaratorId(node.parent, node);
154
+ }
156
155
  }
157
156
 
158
- // src/var-scope.ts
157
+ //#endregion
158
+ //#region src/var-scope.ts
159
159
  function getChidScopes(scope) {
160
- const scopes = [scope];
161
- for (const childScope of scope.childScopes) {
162
- scopes.push(...getChidScopes(childScope));
163
- }
164
- return scopes;
160
+ const scopes = [scope];
161
+ for (const childScope of scope.childScopes) scopes.push(...getChidScopes(childScope));
162
+ return scopes;
165
163
  }
164
+
165
+ //#endregion
166
+ //#region src/var-value.ts
166
167
  function toStaticValue(lazyValue) {
167
- const { kind, node, initialScope } = lazyValue;
168
- if (kind !== "lazy") {
169
- return lazyValue;
170
- }
171
- const staticValue = initialScope == null ? getStaticValue(node) : getStaticValue(node, initialScope);
172
- return staticValue == null ? { kind: "none", node, initialScope } : { kind: "some", node, initialScope, value: staticValue.value };
168
+ const { kind, node, initialScope } = lazyValue;
169
+ if (kind !== "lazy") return lazyValue;
170
+ const staticValue = initialScope == null ? getStaticValue(node) : getStaticValue(node, initialScope);
171
+ return staticValue == null ? {
172
+ kind: "none",
173
+ node,
174
+ initialScope
175
+ } : {
176
+ kind: "some",
177
+ node,
178
+ initialScope,
179
+ value: staticValue.value
180
+ };
173
181
  }
174
- var thisBlockTypes = [
175
- AST_NODE_TYPES.FunctionDeclaration,
176
- AST_NODE_TYPES.FunctionExpression,
177
- AST_NODE_TYPES.ClassBody,
178
- AST_NODE_TYPES.Program
182
+
183
+ //#endregion
184
+ //#region src/var-value-equal.ts
185
+ const thisBlockTypes = [
186
+ AST_NODE_TYPES.FunctionDeclaration,
187
+ AST_NODE_TYPES.FunctionExpression,
188
+ AST_NODE_TYPES.ClassBody,
189
+ AST_NODE_TYPES.Program
179
190
  ];
191
+ /**
192
+ * Determines whether node value equals to another node value
193
+ * @param a node to compare
194
+ * @param b node to compare
195
+ * @param initialScopes initial scopes of the two nodes
196
+ * @returns `true` if node value equal
197
+ */
180
198
  function isNodeValueEqual(a, b, initialScopes) {
181
- const [aScope, bScope] = initialScopes;
182
- switch (true) {
183
- case a === b: {
184
- return true;
185
- }
186
- case (a.type === AST_NODE_TYPES.Literal && b.type === AST_NODE_TYPES.Literal): {
187
- return a.value === b.value;
188
- }
189
- case (a.type === AST_NODE_TYPES.TemplateElement && b.type === AST_NODE_TYPES.TemplateElement): {
190
- return a.value.cooked === b.value.cooked;
191
- }
192
- case (a.type === AST_NODE_TYPES.Identifier && b.type === AST_NODE_TYPES.Identifier): {
193
- const aVar = findVariable2(a, aScope);
194
- const bVar = findVariable2(b, bScope);
195
- const aVarNode = getVariableInitNodeLoose(aVar, 0);
196
- const bVarNode = getVariableInitNodeLoose(bVar, 0);
197
- const aVarNodeParent = aVarNode?.parent;
198
- const bVarNodeParent = bVarNode?.parent;
199
- const aDef = aVar?.defs.at(0);
200
- const bDef = bVar?.defs.at(0);
201
- const aDefParentParent = aDef?.parent?.parent;
202
- const bDefParentParent = bDef?.parent?.parent;
203
- switch (true) {
204
- case (aVarNodeParent?.type === AST_NODE_TYPES.CallExpression && bVarNodeParent?.type === AST_NODE_TYPES.CallExpression && AST.isFunction(aVarNode) && AST.isFunction(bVarNode)): {
205
- if (!AST.isNodeEqual(aVarNodeParent.callee, bVarNodeParent.callee)) {
206
- return false;
207
- }
208
- const aParams = aVarNode.params;
209
- const bParams = bVarNode.params;
210
- const aPos = aParams.findIndex((x) => AST.isNodeEqual(x, a));
211
- const bPos = bParams.findIndex((x) => AST.isNodeEqual(x, b));
212
- return aPos !== -1 && bPos !== -1 && aPos === bPos;
213
- }
214
- case (aDefParentParent?.type === AST_NODE_TYPES.ForOfStatement && bDefParentParent?.type === AST_NODE_TYPES.ForOfStatement): {
215
- const aLeft = aDefParentParent.left;
216
- const bLeft = bDefParentParent.left;
217
- if (aLeft.type !== bLeft.type) {
218
- return false;
219
- }
220
- const aRight = aDefParentParent.right;
221
- const bRight = bDefParentParent.right;
222
- return AST.isNodeEqual(aRight, bRight);
223
- }
224
- default: {
225
- return aVar != null && bVar != null && aVar === bVar;
226
- }
227
- }
228
- }
229
- case (a.type === AST_NODE_TYPES.MemberExpression && b.type === AST_NODE_TYPES.MemberExpression): {
230
- return AST.isNodeEqual(a.property, b.property) && isNodeValueEqual(a.object, b.object, initialScopes);
231
- }
232
- case (a.type === AST_NODE_TYPES.ThisExpression && b.type === AST_NODE_TYPES.ThisExpression): {
233
- if (aScope.block === bScope.block) {
234
- return true;
235
- }
236
- const aFunction = AST.findParentNode(a, AST.isOneOf(thisBlockTypes));
237
- const bFunction = AST.findParentNode(b, AST.isOneOf(thisBlockTypes));
238
- return aFunction === bFunction;
239
- }
240
- default: {
241
- const aStatic = toStaticValue({ kind: "lazy", node: a, initialScope: aScope });
242
- const bStatic = toStaticValue({ kind: "lazy", node: b, initialScope: bScope });
243
- return aStatic.kind !== "none" && bStatic.kind !== "none" && aStatic.value === bStatic.value;
244
- }
245
- }
199
+ const [aScope, bScope] = initialScopes;
200
+ switch (true) {
201
+ case a === b: return true;
202
+ case a.type === AST_NODE_TYPES.Literal && b.type === AST_NODE_TYPES.Literal: return a.value === b.value;
203
+ case a.type === AST_NODE_TYPES.TemplateElement && b.type === AST_NODE_TYPES.TemplateElement: return a.value.cooked === b.value.cooked;
204
+ case a.type === AST_NODE_TYPES.Identifier && b.type === AST_NODE_TYPES.Identifier: {
205
+ const aVar = findVariable(a, aScope);
206
+ const bVar = findVariable(b, bScope);
207
+ const aVarNode = getVariableInitNodeLoose(aVar, 0);
208
+ const bVarNode = getVariableInitNodeLoose(bVar, 0);
209
+ const aVarNodeParent = aVarNode?.parent;
210
+ const bVarNodeParent = bVarNode?.parent;
211
+ const aDef = aVar?.defs.at(0);
212
+ const bDef = bVar?.defs.at(0);
213
+ const aDefParentParent = aDef?.parent?.parent;
214
+ const bDefParentParent = bDef?.parent?.parent;
215
+ switch (true) {
216
+ case aVarNodeParent?.type === AST_NODE_TYPES.CallExpression && bVarNodeParent?.type === AST_NODE_TYPES.CallExpression && AST.isFunction(aVarNode) && AST.isFunction(bVarNode): {
217
+ if (!AST.isNodeEqual(aVarNodeParent.callee, bVarNodeParent.callee)) return false;
218
+ const aParams = aVarNode.params;
219
+ const bParams = bVarNode.params;
220
+ const aPos = aParams.findIndex((x) => AST.isNodeEqual(x, a));
221
+ const bPos = bParams.findIndex((x) => AST.isNodeEqual(x, b));
222
+ return aPos !== -1 && bPos !== -1 && aPos === bPos;
223
+ }
224
+ case aDefParentParent?.type === AST_NODE_TYPES.ForOfStatement && bDefParentParent?.type === AST_NODE_TYPES.ForOfStatement: {
225
+ const aLeft = aDefParentParent.left;
226
+ const bLeft = bDefParentParent.left;
227
+ if (aLeft.type !== bLeft.type) return false;
228
+ const aRight = aDefParentParent.right;
229
+ const bRight = bDefParentParent.right;
230
+ return AST.isNodeEqual(aRight, bRight);
231
+ }
232
+ default: return aVar != null && bVar != null && aVar === bVar;
233
+ }
234
+ }
235
+ case a.type === AST_NODE_TYPES.MemberExpression && b.type === AST_NODE_TYPES.MemberExpression: return AST.isNodeEqual(a.property, b.property) && isNodeValueEqual(a.object, b.object, initialScopes);
236
+ case a.type === AST_NODE_TYPES.ThisExpression && b.type === AST_NODE_TYPES.ThisExpression: {
237
+ if (aScope.block === bScope.block) return true;
238
+ const aFunction = AST.findParentNode(a, AST.isOneOf(thisBlockTypes));
239
+ const bFunction = AST.findParentNode(b, AST.isOneOf(thisBlockTypes));
240
+ return aFunction === bFunction;
241
+ }
242
+ default: {
243
+ const aStatic = toStaticValue({
244
+ kind: "lazy",
245
+ node: a,
246
+ initialScope: aScope
247
+ });
248
+ const bStatic = toStaticValue({
249
+ kind: "lazy",
250
+ node: b,
251
+ initialScope: bScope
252
+ });
253
+ return aStatic.kind !== "none" && bStatic.kind !== "none" && aStatic.value === bStatic.value;
254
+ }
255
+ }
246
256
  }
247
257
  function getVariableInitNodeLoose(variable, at) {
248
- if (variable == null) return unit;
249
- const node = getVariableInitNode(variable, at);
250
- if (node != null) return node;
251
- const def = variable.defs.at(at);
252
- if (def?.type === DefinitionType.Parameter && AST.isFunction(def.node)) return def.node;
253
- return unit;
258
+ if (variable == null) return unit;
259
+ const node = getVariableInitNode(variable, at);
260
+ if (node != null) return node;
261
+ const def = variable.defs.at(at);
262
+ if (def?.type === DefinitionType.Parameter && AST.isFunction(def.node)) return def.node;
263
+ return unit;
254
264
  }
255
265
 
256
- export { ConstructionDetectionHint, findPropertyInProperties, findVariable2 as findVariable, getChidScopes, getConstruction, getVariableDeclaratorId, getVariableInitNode, getVariables, isNodeValueEqual, toStaticValue };
266
+ //#endregion
267
+ export { ConstructionDetectionHint, findPropertyInProperties, findVariable, getChidScopes, getConstruction, getVariableDeclaratorId, getVariableInitNode, getVariables, isNodeValueEqual, toStaticValue };
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@eslint-react/var",
3
- "version": "2.0.0-next.146",
3
+ "version": "2.0.0-next.148",
4
4
  "description": "ESLint React's TSESTree AST utility module for static analysis of variables.",
5
5
  "homepage": "https://github.com/Rel1cx/eslint-react",
6
6
  "bugs": {
@@ -27,23 +27,23 @@
27
27
  "./package.json"
28
28
  ],
29
29
  "dependencies": {
30
- "@typescript-eslint/scope-manager": "^8.40.0",
31
- "@typescript-eslint/types": "^8.40.0",
32
- "@typescript-eslint/utils": "^8.40.0",
30
+ "@typescript-eslint/scope-manager": "^8.41.0",
31
+ "@typescript-eslint/types": "^8.41.0",
32
+ "@typescript-eslint/utils": "^8.41.0",
33
33
  "string-ts": "^2.2.1",
34
34
  "ts-pattern": "^5.8.0",
35
- "@eslint-react/ast": "2.0.0-next.146",
36
- "@eslint-react/eff": "2.0.0-next.146"
35
+ "@eslint-react/eff": "2.0.0-next.148",
36
+ "@eslint-react/ast": "2.0.0-next.148"
37
37
  },
38
38
  "devDependencies": {
39
- "tsup": "^8.5.0",
39
+ "tsdown": "^0.14.2",
40
40
  "@local/configs": "0.0.0"
41
41
  },
42
42
  "engines": {
43
43
  "node": ">=20.19.0"
44
44
  },
45
45
  "scripts": {
46
- "build": "tsup",
46
+ "build": "tsdown --dts-resolve",
47
47
  "lint:publish": "publint",
48
48
  "lint:ts": "tsc --noEmit"
49
49
  }