Socket
Socket
Sign inDemoInstall

eslint-plugin-unicorn

Package Overview
Dependencies
Maintainers
2
Versions
106
Alerts
File Explorer

Advanced tools

Socket logo

Install Socket

Detect and block malicious and high-risk dependencies

Install

eslint-plugin-unicorn - npm Package Compare versions

Comparing version 55.0.0 to 56.0.0

rules/ast/is-negative-one.js

46

package.json
{
"name": "eslint-plugin-unicorn",
"version": "55.0.0",
"version": "56.0.0",
"description": "More than 100 powerful ESLint rules",

@@ -54,9 +54,9 @@ "license": "MIT",

"dependencies": {
"@babel/helper-validator-identifier": "^7.24.5",
"@babel/helper-validator-identifier": "^7.24.7",
"@eslint-community/eslint-utils": "^4.4.0",
"ci-info": "^4.0.0",
"clean-regexp": "^1.0.0",
"core-js-compat": "^3.37.0",
"esquery": "^1.5.0",
"globals": "^15.7.0",
"core-js-compat": "^3.38.1",
"esquery": "^1.6.0",
"globals": "^15.9.0",
"indent-string": "^4.0.0",

@@ -69,37 +69,37 @@ "is-builtin-module": "^3.2.1",

"regjsparser": "^0.10.0",
"semver": "^7.6.1",
"semver": "^7.6.3",
"strip-indent": "^3.0.0"
},
"devDependencies": {
"@babel/code-frame": "^7.24.2",
"@babel/core": "^7.24.5",
"@babel/eslint-parser": "^7.24.5",
"@babel/code-frame": "^7.24.7",
"@babel/core": "^7.25.2",
"@babel/eslint-parser": "^7.25.1",
"@eslint/eslintrc": "^3.1.0",
"@lubien/fixture-beta-package": "^1.0.0-beta.1",
"@typescript-eslint/parser": "^8.0.0-alpha.12",
"@typescript-eslint/parser": "^8.4.0",
"ava": "^6.1.3",
"c8": "^9.1.0",
"c8": "^10.1.2",
"chalk": "^5.3.0",
"enquirer": "^2.4.1",
"eslint": "^9.6.0",
"eslint": "^9.10.0",
"eslint-ava-rule-tester": "^5.0.1",
"eslint-doc-generator": "1.7.0",
"eslint-plugin-eslint-plugin": "^6.1.0",
"eslint-plugin-eslint-plugin": "^6.2.0",
"eslint-plugin-internal-rules": "file:./scripts/internal-rules/",
"eslint-remote-tester": "^4.0.0",
"eslint-remote-tester": "^4.0.1",
"eslint-remote-tester-repositories": "^2.0.0",
"espree": "^10.0.1",
"espree": "^10.1.0",
"execa": "^8.0.1",
"listr": "^0.14.3",
"lodash-es": "^4.17.21",
"markdownlint-cli": "^0.40.0",
"markdownlint-cli": "^0.41.0",
"memoize": "^10.0.0",
"npm-package-json-lint": "^7.1.0",
"npm-run-all2": "^6.1.2",
"npm-package-json-lint": "^8.0.0",
"npm-run-all2": "^6.2.2",
"outdent": "^0.8.0",
"pretty-ms": "^9.0.0",
"typescript": "^5.4.5",
"vue-eslint-parser": "^9.4.2",
"xo": "^0.58.0",
"yaml": "^2.4.2"
"pretty-ms": "^9.1.0",
"typescript": "^5.5.4",
"vue-eslint-parser": "^9.4.3",
"xo": "^0.59.3",
"yaml": "^2.5.1"
},

@@ -106,0 +106,0 @@ "peerDependencies": {

@@ -113,6 +113,7 @@ # eslint-plugin-unicorn [![Coverage Status](https://codecov.io/gh/sindresorhus/eslint-plugin-unicorn/branch/main/graph/badge.svg)](https://codecov.io/gh/sindresorhus/eslint-plugin-unicorn/branch/main) [![npm version](https://img.shields.io/npm/v/eslint-plugin-unicorn.svg?style=flat)](https://npmjs.com/package/eslint-plugin-unicorn)

| :----------------------------------------------------------------------------------------------- | :---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | :- | :- | :- |
| [better-regex](docs/rules/better-regex.md) | Improve regexes by making them shorter, consistent, and safer. | ✅ | 🔧 | |
| [better-regex](docs/rules/better-regex.md) | Improve regexes by making them shorter, consistent, and safer. | | 🔧 | |
| [catch-error-name](docs/rules/catch-error-name.md) | Enforce a specific parameter name in catch clauses. | ✅ | 🔧 | |
| [consistent-destructuring](docs/rules/consistent-destructuring.md) | Use destructured variables over properties. | | 🔧 | 💡 |
| [consistent-empty-array-spread](docs/rules/consistent-empty-array-spread.md) | Prefer consistent types when spreading a ternary in an array literal. | ✅ | 🔧 | |
| [consistent-existence-index-check](docs/rules/consistent-existence-index-check.md) | Enforce consistent style for element existence checks with `indexOf()`, `lastIndexOf()`, `findIndex()`, and `findLastIndex()`. | ✅ | 🔧 | |
| [consistent-function-scoping](docs/rules/consistent-function-scoping.md) | Move function definitions to the highest possible scope. | ✅ | | |

@@ -193,2 +194,3 @@ | [custom-error-definition](docs/rules/custom-error-definition.md) | Enforce correct `Error` subclassing. | | 🔧 | |

| [prefer-export-from](docs/rules/prefer-export-from.md) | Prefer `export…from` when re-exporting. | ✅ | 🔧 | 💡 |
| [prefer-global-this](docs/rules/prefer-global-this.md) | Prefer `globalThis` over `window`, `self`, and `global`. | ✅ | 🔧 | |
| [prefer-includes](docs/rules/prefer-includes.md) | Prefer `.includes()` over `.indexOf()`, `.lastIndexOf()`, and `Array#some()` when checking for existence or non-existence. | ✅ | 🔧 | 💡 |

@@ -198,2 +200,3 @@ | [prefer-json-parse-buffer](docs/rules/prefer-json-parse-buffer.md) | Prefer reading a JSON file as a buffer. | | 🔧 | |

| [prefer-logical-operator-over-ternary](docs/rules/prefer-logical-operator-over-ternary.md) | Prefer using a logical operator over a ternary. | ✅ | | 💡 |
| [prefer-math-min-max](docs/rules/prefer-math-min-max.md) | Prefer `Math.min()` and `Math.max()` over ternaries for simple comparisons. | ✅ | 🔧 | |
| [prefer-math-trunc](docs/rules/prefer-math-trunc.md) | Enforce the use of `Math.trunc` instead of bitwise operators. | ✅ | 🔧 | 💡 |

@@ -210,3 +213,3 @@ | [prefer-modern-dom-apis](docs/rules/prefer-modern-dom-apis.md) | Prefer `.before()` over `.insertBefore()`, `.replaceWith()` over `.replaceChild()`, prefer one of `.before()`, `.after()`, `.append()` or `.prepend()` over `insertAdjacentText()` and `insertAdjacentElement()`. | ✅ | 🔧 | |

| [prefer-prototype-methods](docs/rules/prefer-prototype-methods.md) | Prefer borrowing methods from the prototype instead of the instance. | ✅ | 🔧 | |
| [prefer-query-selector](docs/rules/prefer-query-selector.md) | Prefer `.querySelector()` over `.getElementById()`, `.querySelectorAll()` over `.getElementsByClassName()` and `.getElementsByTagName()`. | ✅ | 🔧 | |
| [prefer-query-selector](docs/rules/prefer-query-selector.md) | Prefer `.querySelector()` over `.getElementById()`, `.querySelectorAll()` over `.getElementsByClassName()` and `.getElementsByTagName()` and `.getElementsByName()`. | ✅ | 🔧 | |
| [prefer-reflect-apply](docs/rules/prefer-reflect-apply.md) | Prefer `Reflect.apply()` over `Function#apply()`. | ✅ | 🔧 | |

@@ -213,0 +216,0 @@ | [prefer-regexp-test](docs/rules/prefer-regexp-test.md) | Prefer `RegExp#test()` over `String#match()` and `RegExp#exec()`. | ✅ | 🔧 | 💡 |

@@ -34,2 +34,3 @@ 'use strict';

isMethodCall: require('./is-method-call.js'),
isNegativeOne: require('./is-negative-one.js'),
isNewExpression,

@@ -36,0 +37,0 @@ isReferenceIdentifier: require('./is-reference-identifier.js'),

@@ -139,3 +139,3 @@ 'use strict';

description: 'Improve regexes by making them shorter, consistent, and safer.',
recommended: true,
recommended: false,
},

@@ -142,0 +142,0 @@ fixable: 'code',

@@ -5,5 +5,7 @@ 'use strict';

const MESSAGE_ID = 'no-reduce';
const MESSAGE_ID_REDUCE = 'reduce';
const MESSAGE_ID_REDUCE_RIGHT = 'reduceRight';
const messages = {
[MESSAGE_ID]: '`Array#{{method}}()` is not allowed',
[MESSAGE_ID_REDUCE]: '`Array#reduce()` is not allowed. Prefer other types of loop for readability.',
[MESSAGE_ID_REDUCE_RIGHT]: '`Array#reduceRight()` is not allowed. Prefer other types of loop for readability. You may want to call `Array#toReversed()` before looping it.',
};

@@ -108,4 +110,3 @@

node: methodNode,
messageId: MESSAGE_ID,
data: {method: methodNode.name},
messageId: methodNode.name,
};

@@ -112,0 +113,0 @@ }

@@ -266,3 +266,3 @@ 'use strict';

const {sourceCode} = context;
const {scopeManager, text: sourceCodeText} = sourceCode;
const {scopeManager} = sourceCode;

@@ -343,3 +343,4 @@ return {

const shouldFix = !someVariablesLeakOutOfTheLoop(node, [indexVariable, elementVariable].filter(Boolean), forScope);
const shouldFix = !someVariablesLeakOutOfTheLoop(node, [indexVariable, elementVariable].filter(Boolean), forScope)
&& !elementNode?.id.typeAnnotation;

@@ -349,3 +350,2 @@ if (shouldFix) {

const shouldGenerateIndex = isIndexVariableUsedElsewhereInTheLoopBody(indexVariable, bodyScope, arrayIdentifierName);
const index = indexIdentifierName;

@@ -359,3 +359,2 @@ const element = elementIdentifierName

let removeDeclaration = true;
let typeAnnotation;

@@ -369,11 +368,3 @@ if (elementNode) {

declarationType = element.type === 'VariableDeclarator' ? elementNode.kind : elementNode.parent.kind;
if (elementNode.id.typeAnnotation && shouldGenerateIndex) {
declarationElement = sourceCodeText.slice(elementNode.id.range[0], elementNode.id.typeAnnotation.range[0]).trim();
typeAnnotation = sourceCode.getText(
elementNode.id.typeAnnotation,
-1, // Skip leading `:`
).trim();
} else {
declarationElement = sourceCode.getText(elementNode.id);
}
declarationElement = sourceCode.getText(elementNode.id);
}

@@ -384,8 +375,3 @@ }

if (shouldGenerateIndex) {
parts.push(` [${index}, ${declarationElement}]`);
if (typeAnnotation) {
parts.push(`: [number, ${typeAnnotation}]`);
}
parts.push(` of ${array}.entries()`);
parts.push(` [${index}, ${declarationElement}] of ${array}.entries()`);
} else {

@@ -392,0 +378,0 @@ parts.push(` ${declarationElement} of ${array}`);

@@ -12,3 +12,3 @@ 'use strict';

const messages = {
[MESSAGE_ID_ERROR]: 'Do not use `new Array()`.',
[MESSAGE_ID_ERROR]: '`new Array()` is unclear in intent; use either `[x]` or `Array.from({length: x})`',
[MESSAGE_ID_LENGTH]: 'The argument is the length of array.',

@@ -15,0 +15,0 @@ [MESSAGE_ID_ONLY_ELEMENT]: 'The argument is the only element of array.',

@@ -65,2 +65,4 @@ 'use strict';

|| /^set[A-Z]/.test(name)
// React 19 useRef
|| name === 'useRef'

@@ -67,0 +69,0 @@ // https://vuejs.org/api/reactivity-core.html#ref

'use strict';
const isMethodNamed = require('./utils/is-method-named.js');
const simpleArraySearchRule = require('./shared/simple-array-search-rule.js');
const {isLiteral} = require('./ast/index.js');
const {isLiteral, isNegativeOne} = require('./ast/index.js');

@@ -13,3 +13,2 @@ const MESSAGE_ID = 'prefer-includes';

const isIgnoredTarget = node => node.type === 'Identifier' && ignoredVariables.has(node.name);
const isNegativeOne = node => node.type === 'UnaryExpression' && node.operator === '-' && node.argument && node.argument.type === 'Literal' && node.argument.value === 1;
const isLiteralZero = node => isLiteral(node, 0);

@@ -16,0 +15,0 @@ const isNegativeResult = node => ['===', '==', '<'].includes(node.operator);

@@ -14,2 +14,3 @@ 'use strict';

['getElementsByTagName', 'querySelectorAll'],
['getElementsByName', 'querySelectorAll'],
]);

@@ -19,2 +20,3 @@

const getReplacementForClass = value => value.match(/\S+/g).map(className => `.${className}`).join('');
const getReplacementForName = (value, originQuote) => `[name=${wrapQuoted(value, originQuote)}]`;

@@ -27,2 +29,20 @@ const getQuotedReplacement = (node, value) => {

const wrapQuoted = (value, originalQuote) => {
switch (originalQuote) {
case '\'': {
return `"${value}"`;
}
case '"': {
return `'${value}'`;
}
case '`': {
return `'${value}'`;
}
// No default
}
};
function * getLiteralFix(fixer, node, identifierName) {

@@ -38,2 +58,7 @@ let replacement = node.raw;

if (identifierName === 'getElementsByName') {
const quoted = node.raw.charAt(0);
replacement = getQuotedReplacement(node, getReplacementForName(node.value, quoted));
}
yield fixer.replaceText(node, replacement);

@@ -60,2 +85,10 @@ }

}
if (identifierName === 'getElementsByName') {
const quoted = node.raw ? node.raw.charAt(0) : '"';
yield fixer.replaceText(
templateElement,
getReplacementForName(templateElement.value.cooked, quoted),
);
}
}

@@ -99,3 +132,3 @@ }

!isMethodCall(node, {
methods: ['getElementById', 'getElementsByClassName', 'getElementsByTagName'],
methods: ['getElementById', 'getElementsByClassName', 'getElementsByTagName', 'getElementsByName'],
argumentsLength: 1,

@@ -136,3 +169,3 @@ optionalCall: false,

docs: {
description: 'Prefer `.querySelector()` over `.getElementById()`, `.querySelectorAll()` over `.getElementsByClassName()` and `.getElementsByTagName()`.',
description: 'Prefer `.querySelector()` over `.getElementById()`, `.querySelectorAll()` over `.getElementsByClassName()` and `.getElementsByTagName()` and `.getElementsByName()`.',
recommended: true,

@@ -139,0 +172,0 @@ },

'use strict';
const {getStaticValue} = require('@eslint-community/eslint-utils');
const {getParenthesizedText, getParenthesizedRange} = require('./utils/parentheses.js');
const isNumber = require('./utils/is-number.js');
const {replaceArgument} = require('./fix/index.js');

@@ -67,9 +66,2 @@ const {isNumberLiteral, isMethodCall} = require('./ast/index.js');

if (argumentNodes.every(node => isNumber(node, scope))) {
const firstArgumentText = getParenthesizedText(firstArgument, sourceCode);
yield fixer.insertTextBeforeRange(secondArgumentRange, `${firstArgumentText} + `);
return;
}
return abort();

@@ -76,0 +68,0 @@ }

@@ -7,4 +7,4 @@ 'use strict';

@param {string} name - The variable name to be resolve.
@param {Scope} scope - The scope to look for the variable in.
@returns {Variable?} - The found variable, if any.
@param {import('eslint').Scope.Scope} scope - The scope to look for the variable in.
@returns {import('eslint').Scope.Variable | void} - The found variable, if any.
*/

@@ -11,0 +11,0 @@ module.exports = function resolveVariableName(name, scope) {

SocketSocket SOC 2 Logo

Product

  • Package Alerts
  • Integrations
  • Docs
  • Pricing
  • FAQ
  • Roadmap
  • Changelog

Packages

npm

Stay in touch

Get open source security insights delivered straight into your inbox.


  • Terms
  • Privacy
  • Security

Made with ⚡️ by Socket Inc