Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: use context.languageOptions.ecmaVersion in core rules #16458

Merged
merged 1 commit into from Oct 31, 2022
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
4 changes: 2 additions & 2 deletions lib/rules/comma-dangle.js
Expand Up @@ -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) {
Expand Down Expand Up @@ -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();

Expand Down
4 changes: 2 additions & 2 deletions lib/rules/func-name-matching.js
Expand Up @@ -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);
Expand Down Expand Up @@ -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.
Expand Down
8 changes: 4 additions & 4 deletions lib/rules/no-misleading-character-class.js
Expand Up @@ -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 {
Expand Down
8 changes: 4 additions & 4 deletions lib/rules/prefer-regex-literals.js
Expand Up @@ -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);
}

/**
Expand Down Expand Up @@ -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 {
Expand Down
118 changes: 117 additions & 1 deletion tests/lib/rules/comma-dangle.js
Expand Up @@ -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
Expand Down Expand Up @@ -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"]
Expand Down Expand Up @@ -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"],
Expand Down Expand Up @@ -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
}]
}
]
});
39 changes: 37 additions & 2 deletions tests/lib/rules/func-name-matching.js
Expand Up @@ -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
Expand Down Expand Up @@ -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: [
{
Expand Down Expand Up @@ -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" } }
]
}
]
});
33 changes: 32 additions & 1 deletion tests/lib/rules/no-misleading-character-class.js
Expand Up @@ -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
Expand Down Expand Up @@ -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" }]
}]
}
]
});
27 changes: 26 additions & 1 deletion tests/lib/rules/prefer-regex-literals.js
Expand Up @@ -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
Expand Down Expand Up @@ -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;"
}
]
}]
}
]
});