From e876900ba2cde20e9b3375fa00616f29480a45f6 Mon Sep 17 00:00:00 2001 From: Anix Date: Mon, 16 Mar 2020 08:46:05 +0000 Subject: [PATCH 01/11] Fix: yoda left string fix for exceptRange --- lib/rules/yoda.js | 2 +- tests/lib/rules/yoda.js | 26 +++++++++++++------------- 2 files changed, 14 insertions(+), 14 deletions(-) diff --git a/lib/rules/yoda.js b/lib/rules/yoda.js index c4ff3f81938..9d24fb2d963 100644 --- a/lib/rules/yoda.js +++ b/lib/rules/yoda.js @@ -248,7 +248,7 @@ module.exports = { return (node.operator === "&&" && (leftLiteral = getNormalizedLiteral(left.left)) && (rightLiteral = getNormalizedLiteral(right.right, Number.POSITIVE_INFINITY)) && - leftLiteral.value <= rightLiteral.value && + (typeof leftLiteral.value === "string" || leftLiteral.value <= rightLiteral.value) && same(left.right, right.left)); } diff --git a/tests/lib/rules/yoda.js b/tests/lib/rules/yoda.js index c0d76ca9b7c..6cd3cc78e26 100644 --- a/tests/lib/rules/yoda.js +++ b/tests/lib/rules/yoda.js @@ -49,6 +49,19 @@ ruleTester.run("yoda", rule, { { code: "if (`b` > `a` && \"b\" > \"a\") {}", options: ["always"], parserOptions: { ecmaVersion: 2015 } }, // Range exception + { + code: "if (\"a\" < x && x < MAX ) {}", + options: ["never", { exceptRange: true }] + }, + { + code: "if (1 < x && x < MAX ) {}", + options: ["never", { exceptRange: true }] + }, + { + code: "if (`green` < x.y && x.y < `blue`) {}", + options: ["never", { exceptRange: true }], + parserOptions: { ecmaVersion: 2015 } + }, { code: "if (0 < x && x <= 1) {}", options: ["never", { exceptRange: true }] @@ -641,19 +654,6 @@ ruleTester.run("yoda", rule, { } ] }, - { - code: "if (`green` < x.y && x.y < `blue`) {}", - output: "if (x.y > `green` && x.y < `blue`) {}", - options: ["never", { exceptRange: true }], - parserOptions: { ecmaVersion: 2015 }, - errors: [ - { - messageId: "expected", - data: { expectedSide: "right", operator: "<" }, - type: "BinaryExpression" - } - ] - }, { code: "if (3 == a) {}", output: "if (a == 3) {}", From 9e3eea6e3f327fe772b4390c8e7f730a6461591f Mon Sep 17 00:00:00 2001 From: Anix Date: Mon, 16 Mar 2020 08:55:39 +0000 Subject: [PATCH 02/11] Chore: aded string check for isOutsideTest yoda --- lib/rules/yoda.js | 2 +- tests/lib/rules/yoda.js | 5 +++++ 2 files changed, 6 insertions(+), 1 deletion(-) diff --git a/lib/rules/yoda.js b/lib/rules/yoda.js index 9d24fb2d963..cb2b64313d7 100644 --- a/lib/rules/yoda.js +++ b/lib/rules/yoda.js @@ -262,7 +262,7 @@ module.exports = { return (node.operator === "||" && (leftLiteral = getNormalizedLiteral(left.right, Number.NEGATIVE_INFINITY)) && (rightLiteral = getNormalizedLiteral(right.left)) && - leftLiteral.value <= rightLiteral.value && + (typeof leftLiteral.value === "string" || leftLiteral.value <= rightLiteral.value) && same(left.left, right.right)); } diff --git a/tests/lib/rules/yoda.js b/tests/lib/rules/yoda.js index 6cd3cc78e26..3bb268ea18e 100644 --- a/tests/lib/rules/yoda.js +++ b/tests/lib/rules/yoda.js @@ -57,6 +57,11 @@ ruleTester.run("yoda", rule, { code: "if (1 < x && x < MAX ) {}", options: ["never", { exceptRange: true }] }, + { + code: "if (x < `x` || `x` <= x) {}", + options: ["never", { exceptRange: true }], + parserOptions: { ecmaVersion: 2015 } + }, { code: "if (`green` < x.y && x.y < `blue`) {}", options: ["never", { exceptRange: true }], From bff8be6238da8c1499738ea99dd06dd46b2d0afa Mon Sep 17 00:00:00 2001 From: Anix Date: Thu, 19 Mar 2020 16:02:14 +0000 Subject: [PATCH 03/11] Fix: removed inconsistency btn never and always --- lib/rules/yoda.js | 44 +++++++--- tests/lib/rules/yoda.js | 172 ++++++++++++++++++++++++++++++++++------ 2 files changed, 182 insertions(+), 34 deletions(-) diff --git a/lib/rules/yoda.js b/lib/rules/yoda.js index cb2b64313d7..803624ab2e2 100644 --- a/lib/rules/yoda.js +++ b/lib/rules/yoda.js @@ -245,11 +245,23 @@ module.exports = { function isBetweenTest() { let leftLiteral, rightLiteral; - return (node.operator === "&&" && - (leftLiteral = getNormalizedLiteral(left.left)) && - (rightLiteral = getNormalizedLiteral(right.right, Number.POSITIVE_INFINITY)) && - (typeof leftLiteral.value === "string" || leftLiteral.value <= rightLiteral.value) && - same(left.right, right.left)); + if (node.operator === "&&") { + leftLiteral = getNormalizedLiteral(left.left); + rightLiteral = getNormalizedLiteral(right.right, Number.POSITIVE_INFINITY); + + if (leftLiteral && rightLiteral) { + + if (leftLiteral.value <= rightLiteral.value && same(left.right, right.left)) { + return true; + } + + if ((typeof leftLiteral.value === "string" && typeof rightLiteral.value !== "string") || + (typeof rightLiteral.value === "string" && typeof leftLiteral.value !== "string")) { + return true; + } + } + } + return false; } /** @@ -259,11 +271,23 @@ module.exports = { function isOutsideTest() { let leftLiteral, rightLiteral; - return (node.operator === "||" && - (leftLiteral = getNormalizedLiteral(left.right, Number.NEGATIVE_INFINITY)) && - (rightLiteral = getNormalizedLiteral(right.left)) && - (typeof leftLiteral.value === "string" || leftLiteral.value <= rightLiteral.value) && - same(left.left, right.right)); + if (node.operator === "||") { + leftLiteral = getNormalizedLiteral(left.right, Number.POSITIVE_INFINITY); + rightLiteral = getNormalizedLiteral(right.left); + + if (leftLiteral && rightLiteral) { + if ((rightLiteral.value <= leftLiteral.value) && same(left.left, right.right)) { + return true; + } + + if ((typeof leftLiteral.value === "string" && typeof rightLiteral.value !== "string") || + (typeof rightLiteral.value === "string" && typeof leftLiteral.value !== "string")) { + return true; + } + } + } + + return false; } /** diff --git a/tests/lib/rules/yoda.js b/tests/lib/rules/yoda.js index 3bb268ea18e..2d73339bd17 100644 --- a/tests/lib/rules/yoda.js +++ b/tests/lib/rules/yoda.js @@ -58,27 +58,20 @@ ruleTester.run("yoda", rule, { options: ["never", { exceptRange: true }] }, { - code: "if (x < `x` || `x` <= x) {}", - options: ["never", { exceptRange: true }], - parserOptions: { ecmaVersion: 2015 } + code: "if ('a' < x && x < MAX ) {}", + options: ["never", { exceptRange: true }] }, { - code: "if (`green` < x.y && x.y < `blue`) {}", + code: "if (x < `x` || `x` <= x) {}", options: ["never", { exceptRange: true }], parserOptions: { ecmaVersion: 2015 } }, { code: "if (0 < x && x <= 1) {}", options: ["never", { exceptRange: true }] - }, { - code: "if (x < 0 || 1 <= x) {}", - options: ["never", { exceptRange: true }] }, { code: "if (0 <= x && x < 1) {}", options: ["always", { exceptRange: true }] - }, { - code: "if (x <= 'bar' || 'foo' < x) {}", - options: ["always", { exceptRange: true }] }, { code: "if ('blue' < x.y && x.y < 'green') {}", options: ["never", { exceptRange: true }] @@ -99,9 +92,6 @@ ruleTester.run("yoda", rule, { }, { code: "if ((0 < a && a < 1) && b < 0) {}", options: ["never", { exceptRange: true }] - }, { - code: "if (a < 4 || (b[c[0]].d['e'] < 0 || 1 <= b[c[0]].d['e'])) {}", - options: ["never", { exceptRange: true }] }, { code: "if (-1 < x && x < 0) {}", options: ["never", { exceptRange: true }] @@ -131,18 +121,10 @@ ruleTester.run("yoda", rule, { code: "if (-1n < x && x <= 1n) {}", options: ["never", { exceptRange: true }], parserOptions: { ecmaVersion: 2020 } - }, { - code: "if (x < -1n || 1n <= x) {}", - options: ["never", { exceptRange: true }], - parserOptions: { ecmaVersion: 2020 } }, { code: "if (-1n <= x && x < 1n) {}", options: ["always", { exceptRange: true }], parserOptions: { ecmaVersion: 2020 } - }, { - code: "if (x < -1n || 1n <= x) {}", - options: ["always", { exceptRange: true }], - parserOptions: { ecmaVersion: 2020 } }, { code: "if (x < `1` || `1` < x) {}", options: ["always", { exceptRange: true }], @@ -152,14 +134,37 @@ ruleTester.run("yoda", rule, { options: ["never", { exceptRange: true }], parserOptions: { ecmaVersion: 2018 } }, { - code: "if (x <= `bar` || `foo` < x) {}", + code: "if ('a' < x && x < MAX ) {}", options: ["always", { exceptRange: true }], parserOptions: { ecmaVersion: 2015 } }, { - code: "if (`blue` < x.y && x.y < `green`) {}", + code: "if ('a' < x && x < MAX ) {}", + options: ["always"], + parserOptions: { ecmaVersion: 2015 } + }, { + code: "if (x <= 'foo' || 'bar' < x) {}", + options: ["always", { exceptRange: true }], + parserOptions: { ecmaVersion: 2015 } + }, { + code: "if (MIN < x && x < 'a' ) {}", options: ["never", { exceptRange: true }], parserOptions: { ecmaVersion: 2015 } }, { + code: "if (MIN < x && x < 'a' ) {}", + options: ["never"], + parserOptions: { ecmaVersion: 2015 } + }, + { + code: "if (`blue` < x.y && x.y < `green`) {}", + options: ["never", { exceptRange: true }], + parserOptions: { ecmaVersion: 2015 } + }, + { + code: "if ('a' < x && x < MAX ) {}", + options: ["never", { exceptRange: true }], + parserOptions: { ecmaVersion: 2015 } + }, + { code: "if (0 <= x[`y`] && x[`y`] <= 100) {}", options: ["never", { exceptRange: true }], parserOptions: { ecmaVersion: 2015 } @@ -167,8 +172,12 @@ ruleTester.run("yoda", rule, { code: "if (0 <= x[`y`] && x[\"y\"] <= 100) {}", options: ["never", { exceptRange: true }], parserOptions: { ecmaVersion: 2015 } + }, { + code: "if ('a' <= x && x < 'b') {}", + options: ["never", { exceptRange: true }] }, + // onlyEquality { code: "if (0 < x && x <= 1) {}", options: ["never", { onlyEquality: true }] }, { code: "if (x !== 'foo' && 'foo' !== x) {}", options: ["never", { onlyEquality: true }] }, @@ -177,7 +186,18 @@ ruleTester.run("yoda", rule, { { code: "if (x < `2` && x !== `-3`) {}", options: ["always", { onlyEquality: true }], parserOptions: { ecmaVersion: 2015 } } ], invalid: [ - + { + code: "if (x <= 'bar' || 'foo' < x) {}", + output: "if ('bar' >= x || 'foo' < x) {}", + options: ["always", { exceptRange: true }], + errors: [ + { + messageId: "expected", + data: { expectedSide: "left", operator: "<=" }, + type: "BinaryExpression" + } + ] + }, { code: "if (\"red\" == value) {}", output: "if (value == \"red\") {}", @@ -997,6 +1017,110 @@ ruleTester.run("yoda", rule, { type: "BinaryExpression" } ] + }, + { + code: "if (`green` < x.y && x.y < `blue`) {}", + output: "if (`green` < x.y && `blue` > x.y) {}", + options: ["always", { exceptRange: true }], + parserOptions: { ecmaVersion: 2015 }, + errors: [ + { + messageId: "expected", + data: { expectedSide: "left", operator: "<" }, + type: "BinaryExpression" + } + ] + }, + { + code: "if (x < -1n || 1n <= x) {}", + output: "if (x < -1n || x >= 1n) {}", + options: ["never", { exceptRange: true }], + parserOptions: { ecmaVersion: 2020 }, + errors: [ + { + messageId: "expected", + data: { expectedSide: "right", operator: "<=" }, + type: "BinaryExpression" + } + ] + }, + { + code: "if('a' <= x && x < 'b') {}", + output: "if('a' <= x && 'b' > x) {}", + options: ["always"], + errors: [ + { + messageId: "expected", + data: { expectedSide: "left", operator: "<" }, + type: "BinaryExpression" + } + ] + }, + { + code: "if (x < -1n || 1n <= x) {}", + output: "if (-1n > x || 1n <= x) {}", + options: ["always", { exceptRange: true }], + parserOptions: { ecmaVersion: 2020 }, + errors: [ + { + messageId: "expected", + data: { expectedSide: "left", operator: "<" }, + type: "BinaryExpression" + } + ] + }, + { + code: "if (x < 0 || 1 <= x) {}", + output: "if (x < 0 || x >= 1) {}", + options: ["never", { exceptRange: true }], + errors: [ + { + messageId: "expected", + data: { expectedSide: "right", operator: "<=" }, + type: "BinaryExpression" + } + ] + }, + { + code: "if ('b' <= x && x < 'a') {}", + output: "if (x >= 'b' && x < 'a') {}", + options: ["never", { exceptRange: true }], + errors: [ + { + messageId: "expected", + data: { expectedSide: "right", operator: "<=" }, + type: "BinaryExpression" + } + ] + }, + { + code: "if (a < 4 || (b[c[0]].d['e'] < 0 || 1 <= b[c[0]].d['e'])) {}", + output: "if (a < 4 || (b[c[0]].d['e'] < 0 || b[c[0]].d['e'] >= 1)) {}", + options: ["never", { exceptRange: true }], + errors: [ + { + messageId: "expected", + data: { expectedSide: "right", operator: "<=" }, + type: "BinaryExpression" + } + ] + }, + { + code: "if (a < 4 || (b[c[0]].d['e'] < 0 || 1 <= b[c[0]].d['e'])) {}", + output: "if (4 > a || (0 > b[c[0]].d['e'] || 1 <= b[c[0]].d['e'])) {}", + options: ["always", { exceptRange: true }], + errors: [ + { + messageId: "expected", + data: { expectedSide: "left", operator: "<" }, + type: "BinaryExpression" + }, + { + messageId: "expected", + data: { expectedSide: "left", operator: "<" }, + type: "BinaryExpression" + } + ] } ] }); From b335c4d1d3283cf20c7dc9511de5ecd2fbecc28a Mon Sep 17 00:00:00 2001 From: Anix Date: Fri, 20 Mar 2020 13:29:43 +0000 Subject: [PATCH 04/11] Chore: fixed false negatives --- lib/rules/yoda.js | 5 +- tests/lib/rules/yoda.js | 119 +++++++++++++--------------------------- 2 files changed, 41 insertions(+), 83 deletions(-) diff --git a/lib/rules/yoda.js b/lib/rules/yoda.js index 803624ab2e2..623cb520ad8 100644 --- a/lib/rules/yoda.js +++ b/lib/rules/yoda.js @@ -272,11 +272,12 @@ module.exports = { let leftLiteral, rightLiteral; if (node.operator === "||") { - leftLiteral = getNormalizedLiteral(left.right, Number.POSITIVE_INFINITY); + leftLiteral = getNormalizedLiteral(left.right, Number.NEGATIVE_INFINITY); rightLiteral = getNormalizedLiteral(right.left); if (leftLiteral && rightLiteral) { - if ((rightLiteral.value <= leftLiteral.value) && same(left.left, right.right)) { + + if ((leftLiteral.value <= rightLiteral.value) && same(left.left, right.right)) { return true; } diff --git a/tests/lib/rules/yoda.js b/tests/lib/rules/yoda.js index 2d73339bd17..a80b0bd5be1 100644 --- a/tests/lib/rules/yoda.js +++ b/tests/lib/rules/yoda.js @@ -83,6 +83,9 @@ ruleTester.run("yoda", rule, { code: "if (0 < x[''] && x[``] < 100) {}", options: ["never", { exceptRange: true }], parserOptions: { ecmaVersion: 2015 } + }, { + code: "if (a < 4 || (b[c[0]].d['e'] < 0 || 1 <= b[c[0]].d['e'])) {}", + options: ["never", { exceptRange: true }] }, { code: "if (0 <= x['y'] && x['y'] <= 100) {}", options: ["never", { exceptRange: true }] @@ -104,10 +107,12 @@ ruleTester.run("yoda", rule, { }, { code: "if (ZERO <= index && index < 100) {}", options: ["never", { exceptRange: true }] - }, { + }, + { code: "if (value <= MIN || 10 < value) {}", options: ["never", { exceptRange: true }] - }, { + }, + { code: "if (value <= 0 || MAX < value) {}", options: ["never", { exceptRange: true }] }, { @@ -141,11 +146,8 @@ ruleTester.run("yoda", rule, { code: "if ('a' < x && x < MAX ) {}", options: ["always"], parserOptions: { ecmaVersion: 2015 } - }, { - code: "if (x <= 'foo' || 'bar' < x) {}", - options: ["always", { exceptRange: true }], - parserOptions: { ecmaVersion: 2015 } - }, { + }, + { code: "if (MIN < x && x < 'a' ) {}", options: ["never", { exceptRange: true }], parserOptions: { ecmaVersion: 2015 } @@ -159,11 +161,6 @@ ruleTester.run("yoda", rule, { options: ["never", { exceptRange: true }], parserOptions: { ecmaVersion: 2015 } }, - { - code: "if ('a' < x && x < MAX ) {}", - options: ["never", { exceptRange: true }], - parserOptions: { ecmaVersion: 2015 } - }, { code: "if (0 <= x[`y`] && x[`y`] <= 100) {}", options: ["never", { exceptRange: true }], @@ -176,6 +173,32 @@ ruleTester.run("yoda", rule, { code: "if ('a' <= x && x < 'b') {}", options: ["never", { exceptRange: true }] }, + { + code: "if (x < -1n || 1n <= x) {}", + options: ["never", { exceptRange: true }], + parserOptions: { ecmaVersion: 2020 } + }, + { + code: "if (x < -1n || 1n <= x) {}", + options: ["always", { exceptRange: true }], + parserOptions: { ecmaVersion: 2020 } + }, + { + code: "if (1 < a && a <= 2) {}", + options: ["never", { exceptRange: true }] + }, + { + code: "if (x < -1 || 1 < x) {}", + options: ["never", { exceptRange: true }] + }, + { + code: "if (x <= 'bar' || 'foo' < x) {}", + options: ["always", { exceptRange: true }] + }, + { + code: "if (x < 0 || 1 <= x) {}", + options: ["never", { exceptRange: true }] + }, // onlyEquality @@ -187,8 +210,8 @@ ruleTester.run("yoda", rule, { ], invalid: [ { - code: "if (x <= 'bar' || 'foo' < x) {}", - output: "if ('bar' >= x || 'foo' < x) {}", + code: "if (x <= 'foo' || 'bar' < x) {}", + output: "if ('foo' >= x || 'bar' < x) {}", options: ["always", { exceptRange: true }], errors: [ { @@ -197,6 +220,7 @@ ruleTester.run("yoda", rule, { type: "BinaryExpression" } ] + }, { code: "if (\"red\" == value) {}", @@ -1031,19 +1055,6 @@ ruleTester.run("yoda", rule, { } ] }, - { - code: "if (x < -1n || 1n <= x) {}", - output: "if (x < -1n || x >= 1n) {}", - options: ["never", { exceptRange: true }], - parserOptions: { ecmaVersion: 2020 }, - errors: [ - { - messageId: "expected", - data: { expectedSide: "right", operator: "<=" }, - type: "BinaryExpression" - } - ] - }, { code: "if('a' <= x && x < 'b') {}", output: "if('a' <= x && 'b' > x) {}", @@ -1056,31 +1067,6 @@ ruleTester.run("yoda", rule, { } ] }, - { - code: "if (x < -1n || 1n <= x) {}", - output: "if (-1n > x || 1n <= x) {}", - options: ["always", { exceptRange: true }], - parserOptions: { ecmaVersion: 2020 }, - errors: [ - { - messageId: "expected", - data: { expectedSide: "left", operator: "<" }, - type: "BinaryExpression" - } - ] - }, - { - code: "if (x < 0 || 1 <= x) {}", - output: "if (x < 0 || x >= 1) {}", - options: ["never", { exceptRange: true }], - errors: [ - { - messageId: "expected", - data: { expectedSide: "right", operator: "<=" }, - type: "BinaryExpression" - } - ] - }, { code: "if ('b' <= x && x < 'a') {}", output: "if (x >= 'b' && x < 'a') {}", @@ -1092,35 +1078,6 @@ ruleTester.run("yoda", rule, { type: "BinaryExpression" } ] - }, - { - code: "if (a < 4 || (b[c[0]].d['e'] < 0 || 1 <= b[c[0]].d['e'])) {}", - output: "if (a < 4 || (b[c[0]].d['e'] < 0 || b[c[0]].d['e'] >= 1)) {}", - options: ["never", { exceptRange: true }], - errors: [ - { - messageId: "expected", - data: { expectedSide: "right", operator: "<=" }, - type: "BinaryExpression" - } - ] - }, - { - code: "if (a < 4 || (b[c[0]].d['e'] < 0 || 1 <= b[c[0]].d['e'])) {}", - output: "if (4 > a || (0 > b[c[0]].d['e'] || 1 <= b[c[0]].d['e'])) {}", - options: ["always", { exceptRange: true }], - errors: [ - { - messageId: "expected", - data: { expectedSide: "left", operator: "<" }, - type: "BinaryExpression" - }, - { - messageId: "expected", - data: { expectedSide: "left", operator: "<" }, - type: "BinaryExpression" - } - ] } ] }); From 1539805630dd2178fd34c832e117474ad40f33e2 Mon Sep 17 00:00:00 2001 From: Anix Date: Fri, 20 Mar 2020 17:37:47 +0000 Subject: [PATCH 05/11] Chore: fixed false negative string <= number --- lib/rules/yoda.js | 17 +++++++++++++---- tests/lib/rules/yoda.js | 17 +++++++++++++++++ 2 files changed, 30 insertions(+), 4 deletions(-) diff --git a/lib/rules/yoda.js b/lib/rules/yoda.js index 623cb520ad8..2785150c6d8 100644 --- a/lib/rules/yoda.js +++ b/lib/rules/yoda.js @@ -255,8 +255,13 @@ module.exports = { return true; } - if ((typeof leftLiteral.value === "string" && typeof rightLiteral.value !== "string") || - (typeof rightLiteral.value === "string" && typeof leftLiteral.value !== "string")) { + if ( + (typeof leftLiteral.value === "string" && + (typeof rightLiteral.value !== "string" && rightLiteral.value === Number.POSITIVE_INFINITY)) || + (typeof rightLiteral.value === "string" && + (typeof leftLiteral.value !== "string" && leftLiteral.value === Number.POSITIVE_INFINITY)) + ) { + return true; } } @@ -281,8 +286,12 @@ module.exports = { return true; } - if ((typeof leftLiteral.value === "string" && typeof rightLiteral.value !== "string") || - (typeof rightLiteral.value === "string" && typeof leftLiteral.value !== "string")) { + if ( + (typeof leftLiteral.value === "string" && + (typeof rightLiteral.value !== "string" && rightLiteral.value === Number.NEGATIVE_INFINITY)) || + (typeof rightLiteral.value === "string" && + (typeof leftLiteral.value !== "string" && leftLiteral.value === Number.NEGATIVE_INFINITY)) + ) { return true; } } diff --git a/tests/lib/rules/yoda.js b/tests/lib/rules/yoda.js index a80b0bd5be1..f0e239a1dc5 100644 --- a/tests/lib/rules/yoda.js +++ b/tests/lib/rules/yoda.js @@ -199,6 +199,10 @@ ruleTester.run("yoda", rule, { code: "if (x < 0 || 1 <= x) {}", options: ["never", { exceptRange: true }] }, + { + code: "if('a' <= x && x < MAX) {}", + options: ["never", { exceptRange: true }] + }, // onlyEquality @@ -1078,6 +1082,19 @@ ruleTester.run("yoda", rule, { type: "BinaryExpression" } ] + }, + { + code: "if('a' <= x && x < 1) {}", + output: "if(x >= 'a' && x < 1) {}", + options: ["never", { exceptRange: true }], + errors: [ + { + messageId: "expected", + data: { expectedSide: "right", operator: "<=" }, + type: "BinaryExpression" + } + ] } + ] }); From 9953a04be07dfcfbff67a8910f3c12cb4ed0d942 Mon Sep 17 00:00:00 2001 From: Anix Date: Sun, 22 Mar 2020 13:42:40 +0000 Subject: [PATCH 06/11] Chore: simplify range checks (yoda) --- lib/rules/yoda.js | 57 ++++++++++++++++------------------------------- 1 file changed, 19 insertions(+), 38 deletions(-) diff --git a/lib/rules/yoda.js b/lib/rules/yoda.js index 2785150c6d8..20f9ce8850b 100644 --- a/lib/rules/yoda.js +++ b/lib/rules/yoda.js @@ -78,8 +78,6 @@ function looksLikeLiteral(node) { /** * Attempts to derive a Literal node from nodes that are treated like literals. * @param {ASTNode} node Node to normalize. - * @param {number} [defaultValue] The default value to be returned if the node - * is not a Literal. * @returns {ASTNode} One of the following options. * 1. The original node if the node is already a Literal * 2. A normalized Literal node with the negative number as the value if the @@ -89,7 +87,7 @@ function looksLikeLiteral(node) { * 4. The Literal node which has the `defaultValue` argument if it exists. * 5. Otherwise `null`. */ -function getNormalizedLiteral(node, defaultValue) { +function getNormalizedLiteral(node) { if (node.type === "Literal") { return node; } @@ -110,14 +108,6 @@ function getNormalizedLiteral(node, defaultValue) { }; } - if (defaultValue) { - return { - type: "Literal", - value: defaultValue, - raw: String(defaultValue) - }; - } - return null; } @@ -247,23 +237,18 @@ module.exports = { if (node.operator === "&&") { leftLiteral = getNormalizedLiteral(left.left); - rightLiteral = getNormalizedLiteral(right.right, Number.POSITIVE_INFINITY); + rightLiteral = getNormalizedLiteral(right.right); - if (leftLiteral && rightLiteral) { - - if (leftLiteral.value <= rightLiteral.value && same(left.right, right.left)) { - return true; - } + if (leftLiteral === null && rightLiteral === null) { + return false; + } - if ( - (typeof leftLiteral.value === "string" && - (typeof rightLiteral.value !== "string" && rightLiteral.value === Number.POSITIVE_INFINITY)) || - (typeof rightLiteral.value === "string" && - (typeof leftLiteral.value !== "string" && leftLiteral.value === Number.POSITIVE_INFINITY)) - ) { + if (leftLiteral !== null && rightLiteral === null || rightLiteral !== null && leftLiteral === null) { + return true; + } - return true; - } + if (leftLiteral.value <= rightLiteral.value && same(left.right, right.left)) { + return true; } } return false; @@ -277,23 +262,19 @@ module.exports = { let leftLiteral, rightLiteral; if (node.operator === "||") { - leftLiteral = getNormalizedLiteral(left.right, Number.NEGATIVE_INFINITY); + leftLiteral = getNormalizedLiteral(left.right); rightLiteral = getNormalizedLiteral(right.left); - if (leftLiteral && rightLiteral) { + if (leftLiteral === null && rightLiteral === null) { + return false; + } - if ((leftLiteral.value <= rightLiteral.value) && same(left.left, right.right)) { - return true; - } + if (leftLiteral !== null && rightLiteral === null || rightLiteral !== null && leftLiteral === null) { + return true; + } - if ( - (typeof leftLiteral.value === "string" && - (typeof rightLiteral.value !== "string" && rightLiteral.value === Number.NEGATIVE_INFINITY)) || - (typeof rightLiteral.value === "string" && - (typeof leftLiteral.value !== "string" && leftLiteral.value === Number.NEGATIVE_INFINITY)) - ) { - return true; - } + if ((leftLiteral.value <= rightLiteral.value) && same(left.left, right.right)) { + return true; } } From 03cdf0d44de368ea5b0fac6348d90697d0ff37b3 Mon Sep 17 00:00:00 2001 From: Anix Date: Mon, 23 Mar 2020 10:57:42 +0000 Subject: [PATCH 07/11] Chore: fixed false negative and added test --- lib/rules/yoda.js | 8 ++++---- tests/lib/rules/yoda.js | 12 ++++++++++++ 2 files changed, 16 insertions(+), 4 deletions(-) diff --git a/lib/rules/yoda.js b/lib/rules/yoda.js index 20f9ce8850b..338849eabd5 100644 --- a/lib/rules/yoda.js +++ b/lib/rules/yoda.js @@ -235,7 +235,7 @@ module.exports = { function isBetweenTest() { let leftLiteral, rightLiteral; - if (node.operator === "&&") { + if (node.operator === "&&" && same(left.right, right.left)) { leftLiteral = getNormalizedLiteral(left.left); rightLiteral = getNormalizedLiteral(right.right); @@ -247,7 +247,7 @@ module.exports = { return true; } - if (leftLiteral.value <= rightLiteral.value && same(left.right, right.left)) { + if (leftLiteral.value <= rightLiteral.value) { return true; } } @@ -261,7 +261,7 @@ module.exports = { function isOutsideTest() { let leftLiteral, rightLiteral; - if (node.operator === "||") { + if (node.operator === "||" && same(left.left, right.right)) { leftLiteral = getNormalizedLiteral(left.right); rightLiteral = getNormalizedLiteral(right.left); @@ -273,7 +273,7 @@ module.exports = { return true; } - if ((leftLiteral.value <= rightLiteral.value) && same(left.left, right.right)) { + if ((leftLiteral.value <= rightLiteral.value)) { return true; } } diff --git a/tests/lib/rules/yoda.js b/tests/lib/rules/yoda.js index f0e239a1dc5..a149b06886e 100644 --- a/tests/lib/rules/yoda.js +++ b/tests/lib/rules/yoda.js @@ -1094,6 +1094,18 @@ ruleTester.run("yoda", rule, { type: "BinaryExpression" } ] + }, + { + code: "if (0 < a && b < max) {}", + output: "if (a > 0 && b < max) {}", + options: ["never", { exceptRange: true }], + errors: [ + { + messageId: "expected", + data: { expectedSide: "right", operator: "<" }, + type: "BinaryExpression" + } + ] } ] From 7fef15df918db01f4b3eda96e3e0c29dba4f3475 Mon Sep 17 00:00:00 2001 From: Anix Date: Mon, 23 Mar 2020 10:59:17 +0000 Subject: [PATCH 08/11] Chore: removed un-neccesary comment for defaultValue --- lib/rules/yoda.js | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/lib/rules/yoda.js b/lib/rules/yoda.js index 338849eabd5..dcf3ad8c2f3 100644 --- a/lib/rules/yoda.js +++ b/lib/rules/yoda.js @@ -84,8 +84,7 @@ function looksLikeLiteral(node) { * node represents a negative number literal. * 3. A normalized Literal node with the string as the value if the node is * a Template Literal without expression. - * 4. The Literal node which has the `defaultValue` argument if it exists. - * 5. Otherwise `null`. + * 4. Otherwise `null`. */ function getNormalizedLiteral(node) { if (node.type === "Literal") { From 659e6b7e5862e712c1d691fec4aa1376174a1313 Mon Sep 17 00:00:00 2001 From: Anix Date: Tue, 31 Mar 2020 08:12:20 +0000 Subject: [PATCH 09/11] Chore: removed un-neccesary checks --- lib/rules/yoda.js | 110 ++++++++++++++++++++++++++++++---------------- 1 file changed, 73 insertions(+), 37 deletions(-) diff --git a/lib/rules/yoda.js b/lib/rules/yoda.js index dcf3ad8c2f3..f1159e5255d 100644 --- a/lib/rules/yoda.js +++ b/lib/rules/yoda.js @@ -20,7 +20,7 @@ const astUtils = require("./utils/ast-utils"); * @returns {boolean} Whether or not it is a comparison operator. */ function isComparisonOperator(operator) { - return (/^(==|===|!=|!==|<|>|<=|>=)$/u).test(operator); + return /^(==|===|!=|!==|<|>|<=|>=)$/u.test(operator); } /** @@ -29,7 +29,7 @@ function isComparisonOperator(operator) { * @returns {boolean} Whether or not it is an equality operator. */ function isEqualityOperator(operator) { - return (/^(==|===)$/u).test(operator); + return /^(==|===)$/u.test(operator); } /** @@ -50,10 +50,12 @@ function isRangeTestOperator(operator) { * real literal and should be treated as such. */ function isNegativeNumericLiteral(node) { - return (node.type === "UnaryExpression" && + return ( + node.type === "UnaryExpression" && node.operator === "-" && node.prefix && - astUtils.isNumericLiteral(node.argument)); + astUtils.isNumericLiteral(node.argument) + ); } /** @@ -71,8 +73,7 @@ function isStaticTemplateLiteral(node) { * @returns {boolean} True if the node should be treated as a single Literal node. */ function looksLikeLiteral(node) { - return isNegativeNumericLiteral(node) || - isStaticTemplateLiteral(node); + return isNegativeNumericLiteral(node) || isStaticTemplateLiteral(node); } /** @@ -172,7 +173,7 @@ module.exports = { type: "suggestion", docs: { - description: "require or disallow \"Yoda\" conditions", + description: 'require or disallow "Yoda" conditions', category: "Best Practices", recommended: false, url: "https://eslint.org/docs/rules/yoda" @@ -200,16 +201,19 @@ module.exports = { fixable: "code", messages: { - expected: "Expected literal to be on the {{expectedSide}} side of {{operator}}." + expected: + "Expected literal to be on the {{expectedSide}} side of {{operator}}." } }, create(context) { // Default to "never" (!always) if no option - const always = (context.options[0] === "always"); - const exceptRange = (context.options[1] && context.options[1].exceptRange); - const onlyEquality = (context.options[1] && context.options[1].onlyEquality); + const always = context.options[0] === "always"; + const exceptRange = + context.options[1] && context.options[1].exceptRange; + const onlyEquality = + context.options[1] && context.options[1].onlyEquality; const sourceCode = context.getSourceCode(); @@ -232,17 +236,15 @@ module.exports = { * @returns {boolean} Whether node is a "between" range test. */ function isBetweenTest() { - let leftLiteral, rightLiteral; - if (node.operator === "&&" && same(left.right, right.left)) { - leftLiteral = getNormalizedLiteral(left.left); - rightLiteral = getNormalizedLiteral(right.right); + const leftLiteral = getNormalizedLiteral(left.left); + const rightLiteral = getNormalizedLiteral(right.right); if (leftLiteral === null && rightLiteral === null) { return false; } - if (leftLiteral !== null && rightLiteral === null || rightLiteral !== null && leftLiteral === null) { + if (rightLiteral === null || leftLiteral === null) { return true; } @@ -258,21 +260,19 @@ module.exports = { * @returns {boolean} Whether node is an "outside" range test. */ function isOutsideTest() { - let leftLiteral, rightLiteral; - if (node.operator === "||" && same(left.left, right.right)) { - leftLiteral = getNormalizedLiteral(left.right); - rightLiteral = getNormalizedLiteral(right.left); + const leftLiteral = getNormalizedLiteral(left.right); + const rightLiteral = getNormalizedLiteral(right.left); if (leftLiteral === null && rightLiteral === null) { return false; } - if (leftLiteral !== null && rightLiteral === null || rightLiteral !== null && leftLiteral === null) { + if (rightLiteral === null || leftLiteral === null) { return true; } - if ((leftLiteral.value <= rightLiteral.value)) { + if (leftLiteral.value <= rightLiteral.value) { return true; } } @@ -290,13 +290,15 @@ module.exports = { return astUtils.isParenthesised(sourceCode, node); } - return (node.type === "LogicalExpression" && + return ( + node.type === "LogicalExpression" && left.type === "BinaryExpression" && right.type === "BinaryExpression" && isRangeTestOperator(left.operator) && isRangeTestOperator(right.operator) && (isBetweenTest() || isOutsideTest()) && - isParenWrapped()); + isParenWrapped() + ); } const OPERATOR_FLIP_MAP = { @@ -317,21 +319,52 @@ module.exports = { */ function getFlippedString(node) { const tokenBefore = sourceCode.getTokenBefore(node); - const operatorToken = sourceCode.getFirstTokenBetween(node.left, node.right, token => token.value === node.operator); - const textBeforeOperator = sourceCode.getText().slice(sourceCode.getTokenBefore(operatorToken).range[1], operatorToken.range[0]); - const textAfterOperator = sourceCode.getText().slice(operatorToken.range[1], sourceCode.getTokenAfter(operatorToken).range[0]); - const leftText = sourceCode.getText().slice(node.range[0], sourceCode.getTokenBefore(operatorToken).range[1]); + const operatorToken = sourceCode.getFirstTokenBetween( + node.left, + node.right, + token => token.value === node.operator + ); + const textBeforeOperator = sourceCode + .getText() + .slice( + sourceCode.getTokenBefore(operatorToken).range[1], + operatorToken.range[0] + ); + const textAfterOperator = sourceCode + .getText() + .slice( + operatorToken.range[1], + sourceCode.getTokenAfter(operatorToken).range[0] + ); + const leftText = sourceCode + .getText() + .slice( + node.range[0], + sourceCode.getTokenBefore(operatorToken).range[1] + ); const firstRightToken = sourceCode.getTokenAfter(operatorToken); - const rightText = sourceCode.getText().slice(firstRightToken.range[0], node.range[1]); + const rightText = sourceCode + .getText() + .slice(firstRightToken.range[0], node.range[1]); let prefix = ""; - if (tokenBefore && tokenBefore.range[1] === node.range[0] && - !astUtils.canTokensBeAdjacent(tokenBefore, firstRightToken)) { + if ( + tokenBefore && + tokenBefore.range[1] === node.range[0] && + !astUtils.canTokensBeAdjacent(tokenBefore, firstRightToken) + ) { prefix = " "; } - return prefix + rightText + textBeforeOperator + OPERATOR_FLIP_MAP[operatorToken.value] + textAfterOperator + leftText; + return ( + prefix + + rightText + + textBeforeOperator + + OPERATOR_FLIP_MAP[operatorToken.value] + + textAfterOperator + + leftText + ); } //-------------------------------------------------------------------------- @@ -345,8 +378,12 @@ module.exports = { // If `expectedLiteral` is not a literal, and `expectedNonLiteral` is a literal, raise an error. if ( - (expectedNonLiteral.type === "Literal" || looksLikeLiteral(expectedNonLiteral)) && - !(expectedLiteral.type === "Literal" || looksLikeLiteral(expectedLiteral)) && + (expectedNonLiteral.type === "Literal" || + looksLikeLiteral(expectedNonLiteral)) && + !( + expectedLiteral.type === "Literal" || + looksLikeLiteral(expectedLiteral) + ) && !(!isEqualityOperator(node.operator) && onlyEquality) && isComparisonOperator(node.operator) && !(exceptRange && isRangeTest(context.getAncestors().pop())) @@ -358,12 +395,11 @@ module.exports = { operator: node.operator, expectedSide: always ? "left" : "right" }, - fix: fixer => fixer.replaceText(node, getFlippedString(node)) + fix: fixer => + fixer.replaceText(node, getFlippedString(node)) }); } - } }; - } }; From 6688f364ab5fa608368af410e717f6e31981ac09 Mon Sep 17 00:00:00 2001 From: Anix Date: Sat, 4 Apr 2020 05:10:08 +0000 Subject: [PATCH 10/11] Chore: added removed tests --- tests/lib/rules/yoda.js | 235 +++++++++++++++++++++++++++++----------- 1 file changed, 173 insertions(+), 62 deletions(-) diff --git a/tests/lib/rules/yoda.js b/tests/lib/rules/yoda.js index a149b06886e..961aabf0082 100644 --- a/tests/lib/rules/yoda.js +++ b/tests/lib/rules/yoda.js @@ -19,38 +19,93 @@ const ruleTester = new RuleTester(); ruleTester.run("yoda", rule, { valid: [ - // "never" mode - { code: "if (value === \"red\") {}", options: ["never"] }, + { code: 'if (value === "red") {}', options: ["never"] }, { code: "if (value === value) {}", options: ["never"] }, { code: "if (value != 5) {}", options: ["never"] }, { code: "if (5 & foo) {}", options: ["never"] }, { code: "if (5 === 4) {}", options: ["never"] }, - { code: "if (value === `red`) {}", options: ["never"], parserOptions: { ecmaVersion: 2015 } }, - { code: "if (`red` === `red`) {}", options: ["never"], parserOptions: { ecmaVersion: 2015 } }, - { code: "if (`${foo}` === `red`) {}", options: ["never"], parserOptions: { ecmaVersion: 2015 } }, - { code: "if (`${\"\"}` === `red`) {}", options: ["never"], parserOptions: { ecmaVersion: 2015 } }, - { code: "if (`${\"red\"}` === foo) {}", options: ["never"], parserOptions: { ecmaVersion: 2015 } }, - { code: "if (b > `a` && b > `a`) {}", options: ["never"], parserOptions: { ecmaVersion: 2015 } }, - { code: "if (`b` > `a` && \"b\" > \"a\") {}", options: ["never"], parserOptions: { ecmaVersion: 2015 } }, + { + code: "if (value === `red`) {}", + options: ["never"], + parserOptions: { ecmaVersion: 2015 } + }, + { + code: "if (`red` === `red`) {}", + options: ["never"], + parserOptions: { ecmaVersion: 2015 } + }, + { + code: "if (`${foo}` === `red`) {}", + options: ["never"], + parserOptions: { ecmaVersion: 2015 } + }, + { + code: 'if (`${""}` === `red`) {}', + options: ["never"], + parserOptions: { ecmaVersion: 2015 } + }, + { + code: 'if (`${"red"}` === foo) {}', + options: ["never"], + parserOptions: { ecmaVersion: 2015 } + }, + { + code: "if (b > `a` && b > `a`) {}", + options: ["never"], + parserOptions: { ecmaVersion: 2015 } + }, + { + code: 'if (`b` > `a` && "b" > "a") {}', + options: ["never"], + parserOptions: { ecmaVersion: 2015 } + }, // "always" mode - { code: "if (\"blue\" === value) {}", options: ["always"] }, + { code: 'if ("blue" === value) {}', options: ["always"] }, { code: "if (value === value) {}", options: ["always"] }, { code: "if (4 != value) {}", options: ["always"] }, { code: "if (foo & 4) {}", options: ["always"] }, { code: "if (5 === 4) {}", options: ["always"] }, - { code: "if (`red` === value) {}", options: ["always"], parserOptions: { ecmaVersion: 2015 } }, - { code: "if (`red` === `red`) {}", options: ["always"], parserOptions: { ecmaVersion: 2015 } }, - { code: "if (`red` === `${foo}`) {}", options: ["always"], parserOptions: { ecmaVersion: 2015 } }, - { code: "if (`red` === `${\"\"}`) {}", options: ["always"], parserOptions: { ecmaVersion: 2015 } }, - { code: "if (foo === `${\"red\"}`) {}", options: ["always"], parserOptions: { ecmaVersion: 2015 } }, - { code: "if (`a` > b && `a` > b) {}", options: ["always"], parserOptions: { ecmaVersion: 2015 } }, - { code: "if (`b` > `a` && \"b\" > \"a\") {}", options: ["always"], parserOptions: { ecmaVersion: 2015 } }, + { + code: "if (`red` === value) {}", + options: ["always"], + parserOptions: { ecmaVersion: 2015 } + }, + { + code: "if (`red` === `red`) {}", + options: ["always"], + parserOptions: { ecmaVersion: 2015 } + }, + { + code: "if (`red` === `${foo}`) {}", + options: ["always"], + parserOptions: { ecmaVersion: 2015 } + }, + { + code: 'if (`red` === `${""}`) {}', + options: ["always"], + parserOptions: { ecmaVersion: 2015 } + }, + { + code: 'if (foo === `${"red"}`) {}', + options: ["always"], + parserOptions: { ecmaVersion: 2015 } + }, + { + code: "if (`a` > b && `a` > b) {}", + options: ["always"], + parserOptions: { ecmaVersion: 2015 } + }, + { + code: 'if (`b` > `a` && "b" > "a") {}', + options: ["always"], + parserOptions: { ecmaVersion: 2015 } + }, // Range exception { - code: "if (\"a\" < x && x < MAX ) {}", + code: 'if ("a" < x && x < MAX ) {}', options: ["never", { exceptRange: true }] }, { @@ -69,42 +124,55 @@ ruleTester.run("yoda", rule, { { code: "if (0 < x && x <= 1) {}", options: ["never", { exceptRange: true }] - }, { + }, + { code: "if (0 <= x && x < 1) {}", options: ["always", { exceptRange: true }] - }, { + }, + { code: "if ('blue' < x.y && x.y < 'green') {}", options: ["never", { exceptRange: true }] - }, { + }, + { code: "if (0 < x[``] && x[``] < 100) {}", options: ["never", { exceptRange: true }], parserOptions: { ecmaVersion: 2015 } - }, { + }, + { code: "if (0 < x[''] && x[``] < 100) {}", options: ["never", { exceptRange: true }], parserOptions: { ecmaVersion: 2015 } - }, { - code: "if (a < 4 || (b[c[0]].d['e'] < 0 || 1 <= b[c[0]].d['e'])) {}", + }, + { + code: + "if (a < 4 || (b[c[0]].d['e'] < 0 || 1 <= b[c[0]].d['e'])) {}", options: ["never", { exceptRange: true }] - }, { + }, + { code: "if (0 <= x['y'] && x['y'] <= 100) {}", options: ["never", { exceptRange: true }] - }, { + }, + { code: "if (a < 0 && (0 < b && b < 1)) {}", options: ["never", { exceptRange: true }] - }, { + }, + { code: "if ((0 < a && a < 1) && b < 0) {}", options: ["never", { exceptRange: true }] - }, { + }, + { code: "if (-1 < x && x < 0) {}", options: ["never", { exceptRange: true }] - }, { + }, + { code: "if (0 <= this.prop && this.prop <= 1) {}", options: ["never", { exceptRange: true }] - }, { + }, + { code: "if (0 <= index && index < list.length) {}", options: ["never", { exceptRange: true }] - }, { + }, + { code: "if (ZERO <= index && index < 100) {}", options: ["never", { exceptRange: true }] }, @@ -115,34 +183,47 @@ ruleTester.run("yoda", rule, { { code: "if (value <= 0 || MAX < value) {}", options: ["never", { exceptRange: true }] - }, { - code: "if (0 <= a.b && a[\"b\"] <= 100) {}", + }, + { + code: 'if (0 <= a.b && a["b"] <= 100) {}', options: ["never", { exceptRange: true }] - }, { + }, + { code: "if (0 <= a.b && a[`b`] <= 100) {}", options: ["never", { exceptRange: true }], parserOptions: { ecmaVersion: 2015 } - }, { + }, + { code: "if (-1n < x && x <= 1n) {}", options: ["never", { exceptRange: true }], parserOptions: { ecmaVersion: 2020 } - }, { + }, + { code: "if (-1n <= x && x < 1n) {}", options: ["always", { exceptRange: true }], parserOptions: { ecmaVersion: 2020 } - }, { + }, + { code: "if (x < `1` || `1` < x) {}", options: ["always", { exceptRange: true }], parserOptions: { ecmaVersion: 2020 } - }, { + }, + { code: "if (1 <= a['/(?0)/'] && a[/(?0)/] <= 100) {}", options: ["never", { exceptRange: true }], parserOptions: { ecmaVersion: 2018 } - }, { + }, + { + code: "if (x <= `bar` || `foo` < x) {}", + options: ["always", { exceptRange: true }], + parserOptions: { ecmaVersion: 2015 } + }, + { code: "if ('a' < x && x < MAX ) {}", options: ["always", { exceptRange: true }], parserOptions: { ecmaVersion: 2015 } - }, { + }, + { code: "if ('a' < x && x < MAX ) {}", options: ["always"], parserOptions: { ecmaVersion: 2015 } @@ -151,7 +232,8 @@ ruleTester.run("yoda", rule, { code: "if (MIN < x && x < 'a' ) {}", options: ["never", { exceptRange: true }], parserOptions: { ecmaVersion: 2015 } - }, { + }, + { code: "if (MIN < x && x < 'a' ) {}", options: ["never"], parserOptions: { ecmaVersion: 2015 } @@ -165,11 +247,13 @@ ruleTester.run("yoda", rule, { code: "if (0 <= x[`y`] && x[`y`] <= 100) {}", options: ["never", { exceptRange: true }], parserOptions: { ecmaVersion: 2015 } - }, { - code: "if (0 <= x[`y`] && x[\"y\"] <= 100) {}", + }, + { + code: 'if (0 <= x[`y`] && x["y"] <= 100) {}', options: ["never", { exceptRange: true }], parserOptions: { ecmaVersion: 2015 } - }, { + }, + { code: "if ('a' <= x && x < 'b') {}", options: ["never", { exceptRange: true }] }, @@ -204,13 +288,29 @@ ruleTester.run("yoda", rule, { options: ["never", { exceptRange: true }] }, - // onlyEquality - { code: "if (0 < x && x <= 1) {}", options: ["never", { onlyEquality: true }] }, - { code: "if (x !== 'foo' && 'foo' !== x) {}", options: ["never", { onlyEquality: true }] }, - { code: "if (x < 2 && x !== -3) {}", options: ["always", { onlyEquality: true }] }, - { code: "if (x !== `foo` && `foo` !== x) {}", options: ["never", { onlyEquality: true }], parserOptions: { ecmaVersion: 2015 } }, - { code: "if (x < `2` && x !== `-3`) {}", options: ["always", { onlyEquality: true }], parserOptions: { ecmaVersion: 2015 } } + { + code: "if (0 < x && x <= 1) {}", + options: ["never", { onlyEquality: true }] + }, + { + code: "if (x !== 'foo' && 'foo' !== x) {}", + options: ["never", { onlyEquality: true }] + }, + { + code: "if (x < 2 && x !== -3) {}", + options: ["always", { onlyEquality: true }] + }, + { + code: "if (x !== `foo` && `foo` !== x) {}", + options: ["never", { onlyEquality: true }], + parserOptions: { ecmaVersion: 2015 } + }, + { + code: "if (x < `2` && x !== `-3`) {}", + options: ["always", { onlyEquality: true }], + parserOptions: { ecmaVersion: 2015 } + } ], invalid: [ { @@ -224,11 +324,10 @@ ruleTester.run("yoda", rule, { type: "BinaryExpression" } ] - }, { - code: "if (\"red\" == value) {}", - output: "if (value == \"red\") {}", + code: 'if ("red" == value) {}', + output: 'if (value == "red") {}', options: ["never"], errors: [ { @@ -288,8 +387,8 @@ ruleTester.run("yoda", rule, { ] }, { - code: "if (\"red\" <= value) {}", - output: "if (value >= \"red\") {}", + code: 'if ("red" <= value) {}', + output: 'if (value >= "red") {}', options: ["never"], errors: [ { @@ -326,8 +425,8 @@ ruleTester.run("yoda", rule, { ] }, { - code: "if (`red` <= `${\"red\"}`) {}", - output: "if (`${\"red\"}` >= `red`) {}", + code: 'if (`red` <= `${"red"}`) {}', + output: 'if (`${"red"}` >= `red`) {}', options: ["never"], parserOptions: { ecmaVersion: 2015 }, errors: [ @@ -387,8 +486,8 @@ ruleTester.run("yoda", rule, { ] }, { - code: "if (value == \"red\") {}", - output: "if (\"red\" == value) {}", + code: 'if (value == "red") {}', + output: 'if ("red" == value) {}', options: ["always"], errors: [ { @@ -437,8 +536,8 @@ ruleTester.run("yoda", rule, { ] }, { - code: "if (`${\"red\"}` <= `red`) {}", - output: "if (`red` >= `${\"red\"}`) {}", + code: 'if (`${"red"}` <= `red`) {}', + output: 'if (`red` >= `${"red"}`) {}', options: ["always"], parserOptions: { ecmaVersion: 2015 }, errors: [ @@ -545,6 +644,19 @@ ruleTester.run("yoda", rule, { type: "BinaryExpression" } ] + }, + { + code: "if (`green` < x.y && x.y < `blue`) {}", + output: "if (x.y > `green` && x.y < `blue`) {}", + options: ["never", { exceptRange: true }], + parserOptions: { ecmaVersion: 2015 }, + errors: [ + { + messageId: "expected", + data: { expectedSide: "right", operator: "<" }, + type: "BinaryExpression" + } + ] }, { code: "if (0 <= a[b] && a['b'] < 1) {}", @@ -1107,6 +1219,5 @@ ruleTester.run("yoda", rule, { } ] } - ] }); From 50a443d26b63170704f9a713f351d371e7101154 Mon Sep 17 00:00:00 2001 From: Anix Date: Sat, 4 Apr 2020 05:16:02 +0000 Subject: [PATCH 11/11] Chore: linting fixes --- tests/lib/rules/yoda.js | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/tests/lib/rules/yoda.js b/tests/lib/rules/yoda.js index 961aabf0082..43449401873 100644 --- a/tests/lib/rules/yoda.js +++ b/tests/lib/rules/yoda.js @@ -19,6 +19,7 @@ const ruleTester = new RuleTester(); ruleTester.run("yoda", rule, { valid: [ + // "never" mode { code: 'if (value === "red") {}', options: ["never"] }, { code: "if (value === value) {}", options: ["never"] }, @@ -645,7 +646,7 @@ ruleTester.run("yoda", rule, { } ] }, - { + { code: "if (`green` < x.y && x.y < `blue`) {}", output: "if (x.y > `green` && x.y < `blue`) {}", options: ["never", { exceptRange: true }],