diff --git a/lib/rules/comma-dangle.js b/lib/rules/comma-dangle.js index 9518da90e9e..89d8cabcc37 100644 --- a/lib/rules/comma-dangle.js +++ b/lib/rules/comma-dangle.js @@ -50,7 +50,7 @@ function normalizeOptions(optionValue, ecmaVersion) { objects: optionValue, imports: optionValue, exports: optionValue, - functions: (!ecmaVersion || ecmaVersion < 8) ? "ignore" : optionValue + functions: ecmaVersion < 2017 ? "ignore" : optionValue }; } if (typeof optionValue === "object" && optionValue !== null) { @@ -134,7 +134,7 @@ module.exports = { }, create(context) { - const options = normalizeOptions(context.options[0], context.parserOptions.ecmaVersion); + const options = normalizeOptions(context.options[0], context.languageOptions.ecmaVersion); const sourceCode = context.getSourceCode(); diff --git a/lib/rules/func-name-matching.js b/lib/rules/func-name-matching.js index 391b2a27836..69b47c286a3 100644 --- a/lib/rules/func-name-matching.js +++ b/lib/rules/func-name-matching.js @@ -44,7 +44,7 @@ function isModuleExports(pattern) { * @returns {boolean} True if the string is a valid identifier */ function isIdentifier(name, ecmaVersion) { - if (ecmaVersion >= 6) { + if (ecmaVersion >= 2015) { return esutils.keyword.isIdentifierES6(name); } return esutils.keyword.isIdentifierES5(name); @@ -104,7 +104,7 @@ module.exports = { const nameMatches = typeof context.options[0] === "string" ? context.options[0] : "always"; const considerPropertyDescriptor = options.considerPropertyDescriptor; const includeModuleExports = options.includeCommonJSModuleExports; - const ecmaVersion = context.parserOptions && context.parserOptions.ecmaVersion ? context.parserOptions.ecmaVersion : 5; + const ecmaVersion = context.languageOptions.ecmaVersion; /** * Check whether node is a certain CallExpression. diff --git a/lib/rules/no-misleading-character-class.js b/lib/rules/no-misleading-character-class.js index 667d066e81c..5649f2e37fe 100644 --- a/lib/rules/no-misleading-character-class.js +++ b/lib/rules/no-misleading-character-class.js @@ -193,15 +193,15 @@ module.exports = { * ecmaVersion doesn't support the `u` flag. */ function isValidWithUnicodeFlag(pattern) { - const { ecmaVersion } = context.parserOptions; + const { ecmaVersion } = context.languageOptions; - // ecmaVersion is unknown or it doesn't support the 'u' flag - if (typeof ecmaVersion !== "number" || ecmaVersion <= 5) { + // ecmaVersion <= 5 doesn't support the 'u' flag + if (ecmaVersion <= 5) { return false; } const validator = new RegExpValidator({ - ecmaVersion: Math.min(ecmaVersion + 2009, REGEXPP_LATEST_ECMA_VERSION) + ecmaVersion: Math.min(ecmaVersion, REGEXPP_LATEST_ECMA_VERSION) }); try { diff --git a/lib/rules/prefer-regex-literals.js b/lib/rules/prefer-regex-literals.js index f30eddbf8c5..02e2f5f44a0 100644 --- a/lib/rules/prefer-regex-literals.js +++ b/lib/rules/prefer-regex-literals.js @@ -248,14 +248,14 @@ module.exports = { /** * Returns a ecmaVersion compatible for regexpp. - * @param {any} ecmaVersion The ecmaVersion to convert. + * @param {number} ecmaVersion The ecmaVersion to convert. * @returns {import("regexpp/ecma-versions").EcmaVersion} The resulting ecmaVersion compatible for regexpp. */ function getRegexppEcmaVersion(ecmaVersion) { - if (typeof ecmaVersion !== "number" || ecmaVersion <= 5) { + if (ecmaVersion <= 5) { return 5; } - return Math.min(ecmaVersion + 2009, REGEXPP_LATEST_ECMA_VERSION); + return Math.min(ecmaVersion, REGEXPP_LATEST_ECMA_VERSION); } /** @@ -320,7 +320,7 @@ module.exports = { flags = getStringValue(node.arguments[1]); } - const regexppEcmaVersion = getRegexppEcmaVersion(context.parserOptions.ecmaVersion); + const regexppEcmaVersion = getRegexppEcmaVersion(context.languageOptions.ecmaVersion); const RegExpValidatorInstance = new RegExpValidator({ ecmaVersion: regexppEcmaVersion }); try { diff --git a/tests/lib/rules/comma-dangle.js b/tests/lib/rules/comma-dangle.js index b02a74a5528..da301dfcaef 100644 --- a/tests/lib/rules/comma-dangle.js +++ b/tests/lib/rules/comma-dangle.js @@ -12,7 +12,8 @@ const path = require("path"), { unIndent } = require("../../_utils"), rule = require("../../../lib/rules/comma-dangle"), - { RuleTester } = require("../../../lib/rule-tester"); + { RuleTester } = require("../../../lib/rule-tester"), + FlatRuleTester = require("../../../lib/rule-tester/flat-rule-tester"); //------------------------------------------------------------------------------ // Helpers @@ -279,6 +280,14 @@ ruleTester.run("comma-dangle", rule, { code: "function foo(a,\nb) {}", options: ["always-multiline"] }, + { + code: "foo(a,\nb\n)", + options: ["always-multiline"] + }, + { + code: "function foo(a,\nb\n) {}", + options: ["always-multiline"] + }, { code: "foo(a,\nb)", options: ["always-multiline"] @@ -321,6 +330,16 @@ ruleTester.run("comma-dangle", rule, { options: ["always-multiline"], parserOptions: { ecmaVersion: 7 } }, + { + code: "function foo(a,\nb\n) {}", + options: ["always-multiline"], + parserOptions: { ecmaVersion: 7 } + }, + { + code: "foo(a,\nb\n)", + options: ["always-multiline"], + parserOptions: { ecmaVersion: 7 } + }, { code: "function foo(a,\nb) {}", options: ["only-multiline"], @@ -1853,3 +1872,100 @@ let d = 0;export {d,}; } ] }); + +const flatRuleTester = new FlatRuleTester(); + +// https://github.com/eslint/eslint/issues/16442 +flatRuleTester.run("comma-dangle", rule, { + valid: [ + { + code: "function f(\n a,\n b\n) {}", + options: ["always-multiline"], + languageOptions: { + ecmaVersion: 5, + sourceType: "script" + } + }, + { + code: "f(\n a,\n b\n);", + options: ["always-multiline"], + languageOptions: { + ecmaVersion: 5, + sourceType: "script" + } + }, + { + code: "function f(\n a,\n b\n) {}", + options: ["always-multiline"], + languageOptions: { + ecmaVersion: 2016 + } + }, + { + code: "f(\n a,\n b\n);", + options: ["always-multiline"], + languageOptions: { + ecmaVersion: 2016 + } + } + ], + + invalid: [ + { + code: "function f(\n a,\n b\n) {}", + output: "function f(\n a,\n b,\n) {}", + options: ["always-multiline"], + languageOptions: { + ecmaVersion: 2017 + }, + errors: [{ + messageId: "missing", + type: "Identifier", + line: 3, + column: 3 + }] + }, + { + code: "f(\n a,\n b\n);", + output: "f(\n a,\n b,\n);", + options: ["always-multiline"], + languageOptions: { + ecmaVersion: 2017 + }, + errors: [{ + messageId: "missing", + type: "Identifier", + line: 3, + column: 3 + }] + }, + { + code: "function f(\n a,\n b\n) {}", + output: "function f(\n a,\n b,\n) {}", + options: ["always-multiline"], + languageOptions: { + ecmaVersion: "latest" + }, + errors: [{ + messageId: "missing", + type: "Identifier", + line: 3, + column: 3 + }] + }, + { + code: "f(\n a,\n b\n);", + output: "f(\n a,\n b,\n);", + options: ["always-multiline"], + languageOptions: { + ecmaVersion: "latest" + }, + errors: [{ + messageId: "missing", + type: "Identifier", + line: 3, + column: 3 + }] + } + ] +}); diff --git a/tests/lib/rules/func-name-matching.js b/tests/lib/rules/func-name-matching.js index 7e215254410..c020066e752 100644 --- a/tests/lib/rules/func-name-matching.js +++ b/tests/lib/rules/func-name-matching.js @@ -10,7 +10,8 @@ //------------------------------------------------------------------------------ const rule = require("../../../lib/rules/func-name-matching"), - { RuleTester } = require("../../../lib/rule-tester"); + { RuleTester } = require("../../../lib/rule-tester"), + FlatRuleTester = require("../../../lib/rule-tester/flat-rule-tester"); //------------------------------------------------------------------------------ // Tests @@ -504,7 +505,8 @@ ruleTester.run("func-name-matching", rule, { code: "class C { #x; foo() { a.b.#x = function y() {}; } }", options: ["never"], parserOptions: { ecmaVersion: 2022 } - } + }, + "var obj = { '\\u1885': function foo() {} };" // not a valid identifier in es5 ], invalid: [ { @@ -878,6 +880,39 @@ ruleTester.run("func-name-matching", rule, { errors: [ { messageId: "notMatchProperty", data: { funcName: "x", name: "x" } } ] + }, + { + code: "var obj = { '\\u1885': function foo() {} };", // valid identifier in es2015 + parserOptions: { ecmaVersion: 6 }, + errors: [ + { messageId: "matchProperty", data: { funcName: "foo", name: "\u1885" } } + ] + } + ] +}); + +const flatRuleTester = new FlatRuleTester(); + +flatRuleTester.run("func-name-matching", rule, { + valid: [ + { + code: "var obj = { '\\u1885': function foo() {} };", // not a valid identifier in es5 + languageOptions: { + ecmaVersion: 5, + sourceType: "script" + } + } + ], + + invalid: [ + { + code: "var obj = { '\\u1885': function foo() {} };", // valid identifier in es2015 + languageOptions: { + ecmaVersion: 2015 + }, + errors: [ + { messageId: "matchProperty", data: { funcName: "foo", name: "\u1885" } } + ] } ] }); diff --git a/tests/lib/rules/no-misleading-character-class.js b/tests/lib/rules/no-misleading-character-class.js index 0aaf34e5942..5cc5cba5261 100644 --- a/tests/lib/rules/no-misleading-character-class.js +++ b/tests/lib/rules/no-misleading-character-class.js @@ -9,7 +9,8 @@ //------------------------------------------------------------------------------ const rule = require("../../../lib/rules/no-misleading-character-class"), - { RuleTester } = require("../../../lib/rule-tester"); + { RuleTester } = require("../../../lib/rule-tester"), + FlatRuleTester = require("../../../lib/rule-tester/flat-rule-tester"); //------------------------------------------------------------------------------ // Tests @@ -622,3 +623,33 @@ ruleTester.run("no-misleading-character-class", rule, { } ] }); + +const flatRuleTester = new FlatRuleTester(); + +flatRuleTester.run("no-misleading-character-class", rule, { + valid: [], + + invalid: [ + { + code: "var r = /[👍]/", + languageOptions: { + ecmaVersion: 5, + sourceType: "script" + }, + errors: [{ + messageId: "surrogatePairWithoutUFlag", + suggestions: null // ecmaVersion doesn't support the 'u' flag + }] + }, + { + code: "var r = /[👍]/", + languageOptions: { + ecmaVersion: 2015 + }, + errors: [{ + messageId: "surrogatePairWithoutUFlag", + suggestions: [{ messageId: "suggestUnicodeFlag", output: "var r = /[👍]/u" }] + }] + } + ] +}); diff --git a/tests/lib/rules/prefer-regex-literals.js b/tests/lib/rules/prefer-regex-literals.js index f2982cbfb72..429df4fd46d 100644 --- a/tests/lib/rules/prefer-regex-literals.js +++ b/tests/lib/rules/prefer-regex-literals.js @@ -10,7 +10,8 @@ //------------------------------------------------------------------------------ const rule = require("../../../lib/rules/prefer-regex-literals"); -const { RuleTester } = require("../../../lib/rule-tester"); +const { RuleTester } = require("../../../lib/rule-tester"), + FlatRuleTester = require("../../../lib/rule-tester/flat-rule-tester"); //------------------------------------------------------------------------------ // Tests @@ -2474,3 +2475,27 @@ ruleTester.run("prefer-regex-literals", rule, { } ] }); + +const flatRuleTester = new FlatRuleTester(); + +flatRuleTester.run("prefer-regex-literals", rule, { + valid: [], + + invalid: [ + { + code: "var regex = new RegExp('foo', 'u');", + languageOptions: { + ecmaVersion: 2015 + }, + errors: [{ + messageId: "unexpectedRegExp", + suggestions: [ + { + messageId: "replaceWithLiteral", + output: "var regex = /foo/u;" + } + ] + }] + } + ] +});