eslint-plugin-absolute 0.2.5 → 0.2.7
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.
- package/.absolutejs/eslint.cache.json +4 -4
- package/.absolutejs/prettier.cache.json +2 -2
- package/.absolutejs/tsconfig.tsbuildinfo +1 -1
- package/dist/index.js +164 -112
- package/package.json +1 -1
- package/src/rules/sort-keys-fixable.ts +264 -169
package/dist/index.js
CHANGED
|
@@ -187,6 +187,23 @@ var explicitObjectTypes = {
|
|
|
187
187
|
// src/rules/sort-keys-fixable.ts
|
|
188
188
|
var SORT_BEFORE = -1;
|
|
189
189
|
var PURE_CONSTRUCTORS = new Set(["Date"]);
|
|
190
|
+
var PURE_GLOBAL_IDENTIFIERS = new Set([
|
|
191
|
+
"Array",
|
|
192
|
+
"BigInt",
|
|
193
|
+
"Boolean",
|
|
194
|
+
"Date",
|
|
195
|
+
"Function",
|
|
196
|
+
"Map",
|
|
197
|
+
"Number",
|
|
198
|
+
"Object",
|
|
199
|
+
"Promise",
|
|
200
|
+
"RegExp",
|
|
201
|
+
"Set",
|
|
202
|
+
"String",
|
|
203
|
+
"Symbol",
|
|
204
|
+
"URL",
|
|
205
|
+
"undefined"
|
|
206
|
+
]);
|
|
190
207
|
var PURE_GLOBAL_FUNCTIONS = new Set(["Boolean", "Number", "String"]);
|
|
191
208
|
var PURE_MEMBER_METHODS = new Set([
|
|
192
209
|
"getDay",
|
|
@@ -219,42 +236,6 @@ var sortKeysFixable = {
|
|
|
219
236
|
const natural = option && typeof option.natural === "boolean" ? option.natural : false;
|
|
220
237
|
const minKeys = option && typeof option.minKeys === "number" ? option.minKeys : 2;
|
|
221
238
|
const variablesBeforeFunctions = option && typeof option.variablesBeforeFunctions === "boolean" ? option.variablesBeforeFunctions : false;
|
|
222
|
-
for (const statement of sourceCode.ast.body) {
|
|
223
|
-
if (statement.type === "ImportDeclaration" && statement.specifiers.length > 0) {
|
|
224
|
-
for (const specifier of statement.specifiers) {
|
|
225
|
-
topLevelBindings.set(specifier.local.name, {
|
|
226
|
-
kind: "import"
|
|
227
|
-
});
|
|
228
|
-
}
|
|
229
|
-
continue;
|
|
230
|
-
}
|
|
231
|
-
if (statement.type === "FunctionDeclaration" && statement.id) {
|
|
232
|
-
topLevelBindings.set(statement.id.name, {
|
|
233
|
-
kind: "function",
|
|
234
|
-
node: statement
|
|
235
|
-
});
|
|
236
|
-
continue;
|
|
237
|
-
}
|
|
238
|
-
if (statement.type !== "VariableDeclaration" || statement.kind !== "const") {
|
|
239
|
-
continue;
|
|
240
|
-
}
|
|
241
|
-
for (const declaration of statement.declarations) {
|
|
242
|
-
if (declaration.id.type !== "Identifier" || !declaration.init) {
|
|
243
|
-
continue;
|
|
244
|
-
}
|
|
245
|
-
if (declaration.init.type === "ArrowFunctionExpression" || declaration.init.type === "FunctionExpression") {
|
|
246
|
-
topLevelBindings.set(declaration.id.name, {
|
|
247
|
-
kind: "function",
|
|
248
|
-
node: declaration.init
|
|
249
|
-
});
|
|
250
|
-
continue;
|
|
251
|
-
}
|
|
252
|
-
topLevelBindings.set(declaration.id.name, {
|
|
253
|
-
kind: "value",
|
|
254
|
-
node: declaration.init
|
|
255
|
-
});
|
|
256
|
-
}
|
|
257
|
-
}
|
|
258
239
|
const compareKeys = (keyLeft, keyRight) => {
|
|
259
240
|
let left = keyLeft;
|
|
260
241
|
let right = keyRight;
|
|
@@ -269,63 +250,124 @@ var sortKeysFixable = {
|
|
|
269
250
|
}
|
|
270
251
|
return left.localeCompare(right);
|
|
271
252
|
};
|
|
272
|
-
const
|
|
273
|
-
if (
|
|
253
|
+
const addImportBindings = (statement) => {
|
|
254
|
+
if (statement.specifiers.length === 0) {
|
|
274
255
|
return;
|
|
275
256
|
}
|
|
276
|
-
|
|
277
|
-
|
|
257
|
+
for (const specifier of statement.specifiers) {
|
|
258
|
+
topLevelBindings.set(specifier.local.name, {
|
|
259
|
+
kind: "import"
|
|
260
|
+
});
|
|
261
|
+
}
|
|
262
|
+
};
|
|
263
|
+
const addVariableBinding = (declaration) => {
|
|
264
|
+
if (declaration.id.type !== "Identifier" || !declaration.init) {
|
|
278
265
|
return;
|
|
279
266
|
}
|
|
280
|
-
if (
|
|
281
|
-
|
|
267
|
+
if (declaration.init.type === "ArrowFunctionExpression" || declaration.init.type === "FunctionExpression") {
|
|
268
|
+
topLevelBindings.set(declaration.id.name, {
|
|
269
|
+
kind: "function",
|
|
270
|
+
node: declaration.init
|
|
271
|
+
});
|
|
282
272
|
return;
|
|
283
273
|
}
|
|
284
|
-
|
|
285
|
-
|
|
274
|
+
topLevelBindings.set(declaration.id.name, {
|
|
275
|
+
kind: "value",
|
|
276
|
+
node: declaration.init
|
|
277
|
+
});
|
|
278
|
+
};
|
|
279
|
+
const addTopLevelBindings = (statement) => {
|
|
280
|
+
if (statement.type === "ImportDeclaration") {
|
|
281
|
+
addImportBindings(statement);
|
|
286
282
|
return;
|
|
287
283
|
}
|
|
288
|
-
if (
|
|
289
|
-
|
|
290
|
-
|
|
291
|
-
|
|
292
|
-
|
|
293
|
-
|
|
294
|
-
|
|
284
|
+
if (statement.type === "FunctionDeclaration" && statement.id) {
|
|
285
|
+
topLevelBindings.set(statement.id.name, {
|
|
286
|
+
kind: "function",
|
|
287
|
+
node: statement
|
|
288
|
+
});
|
|
289
|
+
return;
|
|
290
|
+
}
|
|
291
|
+
if (statement.type !== "VariableDeclaration" || statement.kind !== "const") {
|
|
292
|
+
return;
|
|
293
|
+
}
|
|
294
|
+
for (const declaration of statement.declarations) {
|
|
295
|
+
addVariableBinding(declaration);
|
|
296
|
+
}
|
|
297
|
+
};
|
|
298
|
+
for (const statement of sourceCode.ast.body) {
|
|
299
|
+
addTopLevelBindings(statement);
|
|
300
|
+
}
|
|
301
|
+
const addBoundIdentifiers = (node, stableLocals) => {
|
|
302
|
+
if (!node) {
|
|
295
303
|
return;
|
|
296
304
|
}
|
|
297
|
-
|
|
298
|
-
|
|
299
|
-
|
|
300
|
-
|
|
301
|
-
|
|
305
|
+
switch (node.type) {
|
|
306
|
+
case "Identifier":
|
|
307
|
+
stableLocals.add(node.name);
|
|
308
|
+
return;
|
|
309
|
+
case "AssignmentPattern":
|
|
310
|
+
addBoundIdentifiers(node.left, stableLocals);
|
|
311
|
+
return;
|
|
312
|
+
case "RestElement":
|
|
313
|
+
addBoundIdentifiers(node.argument, stableLocals);
|
|
314
|
+
return;
|
|
315
|
+
case "ArrayPattern":
|
|
316
|
+
for (const element of node.elements.filter(Boolean)) {
|
|
317
|
+
addBoundIdentifiers(element, stableLocals);
|
|
318
|
+
}
|
|
319
|
+
break;
|
|
320
|
+
case "ObjectPattern":
|
|
321
|
+
for (const property of node.properties) {
|
|
322
|
+
const bindingNode = property.type === "RestElement" ? property.argument : property.value;
|
|
323
|
+
addBoundIdentifiers(bindingNode, stableLocals);
|
|
302
324
|
}
|
|
303
|
-
|
|
325
|
+
break;
|
|
326
|
+
default:
|
|
327
|
+
break;
|
|
328
|
+
}
|
|
329
|
+
};
|
|
330
|
+
const addFunctionParamBindings = (functionNode, stableLocals) => {
|
|
331
|
+
for (const parameter of functionNode.params) {
|
|
332
|
+
addBoundIdentifiers(parameter, stableLocals);
|
|
333
|
+
}
|
|
334
|
+
};
|
|
335
|
+
const addAncestorConstBindings = (ancestor, node, stableLocals) => {
|
|
336
|
+
const addDeclarationBindings = (statement) => {
|
|
337
|
+
if (statement.type !== "VariableDeclaration" || statement.kind !== "const") {
|
|
338
|
+
return;
|
|
304
339
|
}
|
|
340
|
+
for (const declaration of statement.declarations) {
|
|
341
|
+
addBoundIdentifiers(declaration.id, stableLocals);
|
|
342
|
+
}
|
|
343
|
+
};
|
|
344
|
+
for (const statement of ancestor.body) {
|
|
345
|
+
if (statement.range[0] >= node.range[0]) {
|
|
346
|
+
return;
|
|
347
|
+
}
|
|
348
|
+
addDeclarationBindings(statement);
|
|
349
|
+
}
|
|
350
|
+
};
|
|
351
|
+
const addAncestorBindingsForNode = (ancestor, node, stableLocals) => {
|
|
352
|
+
if (ancestor.type !== "Program" && ancestor.type !== "BlockStatement") {
|
|
353
|
+
return;
|
|
354
|
+
}
|
|
355
|
+
addAncestorConstBindings(ancestor, node, stableLocals);
|
|
356
|
+
};
|
|
357
|
+
const addFunctionBindingsForAncestor = (ancestor, stableLocals) => {
|
|
358
|
+
if (ancestor.type !== "FunctionDeclaration" && ancestor.type !== "FunctionExpression" && ancestor.type !== "ArrowFunctionExpression") {
|
|
359
|
+
return;
|
|
305
360
|
}
|
|
361
|
+
addFunctionParamBindings(ancestor, stableLocals);
|
|
306
362
|
};
|
|
307
363
|
const getStableLocalsForNode = (node) => {
|
|
308
364
|
const stableLocals = new Set;
|
|
309
365
|
const ancestors = sourceCode.getAncestors(node);
|
|
310
366
|
for (const ancestor of ancestors) {
|
|
311
|
-
|
|
312
|
-
for (const parameter of ancestor.params) {
|
|
313
|
-
addBoundIdentifiers(parameter, stableLocals);
|
|
314
|
-
}
|
|
315
|
-
}
|
|
367
|
+
addFunctionBindingsForAncestor(ancestor, stableLocals);
|
|
316
368
|
}
|
|
317
369
|
for (const ancestor of ancestors) {
|
|
318
|
-
|
|
319
|
-
continue;
|
|
320
|
-
}
|
|
321
|
-
for (const statement of ancestor.body) {
|
|
322
|
-
if (statement.range[0] >= node.range[0] || statement.type !== "VariableDeclaration" || statement.kind !== "const") {
|
|
323
|
-
break;
|
|
324
|
-
}
|
|
325
|
-
for (const declaration of statement.declarations) {
|
|
326
|
-
addBoundIdentifiers(declaration.id, stableLocals);
|
|
327
|
-
}
|
|
328
|
-
}
|
|
370
|
+
addAncestorBindingsForNode(ancestor, node, stableLocals);
|
|
329
371
|
}
|
|
330
372
|
return stableLocals;
|
|
331
373
|
};
|
|
@@ -339,6 +381,9 @@ var sortKeysFixable = {
|
|
|
339
381
|
return null;
|
|
340
382
|
};
|
|
341
383
|
const isStableIdentifier = (name, stableLocals) => {
|
|
384
|
+
if (PURE_GLOBAL_IDENTIFIERS.has(name)) {
|
|
385
|
+
return true;
|
|
386
|
+
}
|
|
342
387
|
if (stableLocals.has(name)) {
|
|
343
388
|
return true;
|
|
344
389
|
}
|
|
@@ -354,6 +399,39 @@ var sortKeysFixable = {
|
|
|
354
399
|
}
|
|
355
400
|
return false;
|
|
356
401
|
};
|
|
402
|
+
const isPureConstStatement = (statement, stableLocals, checkExpression) => {
|
|
403
|
+
if (statement.kind !== "const") {
|
|
404
|
+
return false;
|
|
405
|
+
}
|
|
406
|
+
for (const declaration of statement.declarations) {
|
|
407
|
+
if (declaration.id.type !== "Identifier" || !declaration.init) {
|
|
408
|
+
return false;
|
|
409
|
+
}
|
|
410
|
+
if (!checkExpression(declaration.init)) {
|
|
411
|
+
return false;
|
|
412
|
+
}
|
|
413
|
+
stableLocals.add(declaration.id.name);
|
|
414
|
+
}
|
|
415
|
+
return true;
|
|
416
|
+
};
|
|
417
|
+
const isPureFunctionStatement = (statement, stableLocals, checkExpression) => {
|
|
418
|
+
if (statement.type === "ReturnStatement") {
|
|
419
|
+
return !statement.argument || checkExpression(statement.argument);
|
|
420
|
+
}
|
|
421
|
+
if (statement.type === "VariableDeclaration") {
|
|
422
|
+
return isPureConstStatement(statement, stableLocals, checkExpression);
|
|
423
|
+
}
|
|
424
|
+
return false;
|
|
425
|
+
};
|
|
426
|
+
const isPureFunctionBody = (body, stableLocals, checkExpression) => {
|
|
427
|
+
for (const statement of body.body) {
|
|
428
|
+
const statementIsPure = isPureFunctionStatement(statement, stableLocals, checkExpression);
|
|
429
|
+
if (!statementIsPure) {
|
|
430
|
+
return false;
|
|
431
|
+
}
|
|
432
|
+
}
|
|
433
|
+
return true;
|
|
434
|
+
};
|
|
357
435
|
const isPureTopLevelFunction = (functionNode) => {
|
|
358
436
|
const cached = pureFunctionCache.get(functionNode);
|
|
359
437
|
if (cached !== undefined) {
|
|
@@ -364,44 +442,23 @@ var sortKeysFixable = {
|
|
|
364
442
|
}
|
|
365
443
|
pureFunctionInProgress.add(functionNode);
|
|
366
444
|
const stableLocals = new Set;
|
|
367
|
-
|
|
368
|
-
if (parameter.type === "Identifier") {
|
|
369
|
-
stableLocals.add(parameter.name);
|
|
370
|
-
}
|
|
371
|
-
}
|
|
372
|
-
let isPure = true;
|
|
445
|
+
addFunctionParamBindings(functionNode, stableLocals);
|
|
373
446
|
const checkExpression = (expression) => isPureRuntimeExpression(expression, stableLocals);
|
|
374
|
-
|
|
375
|
-
for (const statement of functionNode.body.body) {
|
|
376
|
-
if (statement.type === "ReturnStatement") {
|
|
377
|
-
if (statement.argument && !checkExpression(statement.argument)) {
|
|
378
|
-
isPure = false;
|
|
379
|
-
}
|
|
380
|
-
continue;
|
|
381
|
-
}
|
|
382
|
-
if (statement.type === "VariableDeclaration" && statement.kind === "const") {
|
|
383
|
-
for (const declaration of statement.declarations) {
|
|
384
|
-
if (declaration.id.type !== "Identifier" || !declaration.init || !checkExpression(declaration.init)) {
|
|
385
|
-
isPure = false;
|
|
386
|
-
break;
|
|
387
|
-
}
|
|
388
|
-
stableLocals.add(declaration.id.name);
|
|
389
|
-
}
|
|
390
|
-
if (!isPure) {
|
|
391
|
-
break;
|
|
392
|
-
}
|
|
393
|
-
continue;
|
|
394
|
-
}
|
|
395
|
-
isPure = false;
|
|
396
|
-
break;
|
|
397
|
-
}
|
|
398
|
-
} else {
|
|
399
|
-
isPure = checkExpression(functionNode.body);
|
|
400
|
-
}
|
|
447
|
+
const isPure = functionNode.body.type === "BlockStatement" ? isPureFunctionBody(functionNode.body, stableLocals, checkExpression) : checkExpression(functionNode.body);
|
|
401
448
|
pureFunctionInProgress.delete(functionNode);
|
|
402
449
|
pureFunctionCache.set(functionNode, isPure);
|
|
403
450
|
return isPure;
|
|
404
451
|
};
|
|
452
|
+
const isPureIdentifierCall = (callExpression) => {
|
|
453
|
+
if (callExpression.callee.type !== "Identifier") {
|
|
454
|
+
return false;
|
|
455
|
+
}
|
|
456
|
+
if (PURE_GLOBAL_FUNCTIONS.has(callExpression.callee.name)) {
|
|
457
|
+
return true;
|
|
458
|
+
}
|
|
459
|
+
const binding = topLevelBindings.get(callExpression.callee.name);
|
|
460
|
+
return binding?.kind === "function" ? isPureTopLevelFunction(binding.node) : false;
|
|
461
|
+
};
|
|
405
462
|
const isPureRuntimeExpression = (node, stableLocals) => {
|
|
406
463
|
if (!node || node.type === "PrivateIdentifier") {
|
|
407
464
|
return false;
|
|
@@ -465,11 +522,7 @@ var sortKeysFixable = {
|
|
|
465
522
|
return false;
|
|
466
523
|
}
|
|
467
524
|
if (node.callee.type === "Identifier") {
|
|
468
|
-
|
|
469
|
-
return true;
|
|
470
|
-
}
|
|
471
|
-
const binding = topLevelBindings.get(node.callee.name);
|
|
472
|
-
return binding?.kind === "function" && isPureTopLevelFunction(binding.node);
|
|
525
|
+
return isPureIdentifierCall(node);
|
|
473
526
|
}
|
|
474
527
|
if (node.callee.type !== "MemberExpression") {
|
|
475
528
|
return false;
|
|
@@ -484,7 +537,6 @@ var sortKeysFixable = {
|
|
|
484
537
|
return false;
|
|
485
538
|
}
|
|
486
539
|
};
|
|
487
|
-
const isSafeToReorderExpression = (node) => isPureRuntimeExpression(node, new Set);
|
|
488
540
|
const isSafeJSXAttributeValue = (value, scopeNode) => {
|
|
489
541
|
if (value === null) {
|
|
490
542
|
return true;
|
package/package.json
CHANGED