From 303028b85742fac6b7baf28e45aafd26e6512d0d Mon Sep 17 00:00:00 2001 From: Pig Fang Date: Wed, 20 May 2020 16:01:45 +0800 Subject: [PATCH 1/4] Fix: fix false positives of no-new-func --- lib/rules/no-new-func.js | 37 +++++++++++++++++----------------- tests/lib/rules/no-new-func.js | 9 ++++++++- 2 files changed, 26 insertions(+), 20 deletions(-) diff --git a/lib/rules/no-new-func.js b/lib/rules/no-new-func.js index d1360e9dee0..1cd32b5a862 100644 --- a/lib/rules/no-new-func.js +++ b/lib/rules/no-new-func.js @@ -29,26 +29,25 @@ module.exports = { create(context) { - //-------------------------------------------------------------------------- - // Helpers - //-------------------------------------------------------------------------- - - /** - * Reports a node. - * @param {ASTNode} node The node to report - * @returns {void} - * @private - */ - function report(node) { - context.report({ - node, - messageId: "noFunctionConstructor" - }); - } - return { - "NewExpression[callee.name = 'Function']": report, - "CallExpression[callee.name = 'Function']": report + "Program:exit"() { + const globalScope = context.getScope(); + const variable = globalScope.set.get("Function"); + + if (variable && variable.defs.length === 0) { + variable.references.forEach(ref => { + const node = ref.identifier; + const { parent } = node; + + if (parent && (parent.type === "NewExpression" || parent.type === "CallExpression")) { + context.report({ + node: parent, + messageId: "noFunctionConstructor" + }); + } + }); + } + } }; } diff --git a/tests/lib/rules/no-new-func.js b/tests/lib/rules/no-new-func.js index bcb35e343ec..8f3766e2b0c 100644 --- a/tests/lib/rules/no-new-func.js +++ b/tests/lib/rules/no-new-func.js @@ -21,7 +21,14 @@ const ruleTester = new RuleTester(); ruleTester.run("no-new-func", rule, { valid: [ "var a = new _function(\"b\", \"c\", \"return b+c\");", - "var a = _function(\"b\", \"c\", \"return b+c\");" + "var a = _function(\"b\", \"c\", \"return b+c\");", + { + code: "class Function {}; new Function()", + parserOptions: { + ecmaVersion: 2015 + } + }, + "function Function() {}; Function()" ], invalid: [ { From 9fd98ce5fce4a01e76fea459a2212d1f31c9b022 Mon Sep 17 00:00:00 2001 From: Pig Fang Date: Thu, 21 May 2020 09:08:13 +0800 Subject: [PATCH 2/4] add more tests --- tests/lib/rules/no-new-func.js | 26 +++++++++++++++++++++++++- 1 file changed, 25 insertions(+), 1 deletion(-) diff --git a/tests/lib/rules/no-new-func.js b/tests/lib/rules/no-new-func.js index 8f3766e2b0c..9c5c88bf302 100644 --- a/tests/lib/rules/no-new-func.js +++ b/tests/lib/rules/no-new-func.js @@ -28,7 +28,14 @@ ruleTester.run("no-new-func", rule, { ecmaVersion: 2015 } }, - "function Function() {}; Function()" + { + code: "const fn = () => { class Function {}; new Function() }", + parserOptions: { + ecmaVersion: 2015 + } + }, + "function Function() {}; Function()", + "var fn = function () { function Function() {}; Function() }" ], invalid: [ { @@ -44,6 +51,23 @@ ruleTester.run("no-new-func", rule, { messageId: "noFunctionConstructor", type: "CallExpression" }] + }, + { + code: "const fn = () => { class Function {} }; new Function('', '')", + parserOptions: { + ecmaVersion: 2015 + }, + errors: [{ + messageId: "noFunctionConstructor", + type: "NewExpression" + }] + }, + { + code: "var fn = function () { function Function() {} }; Function('', '')", + errors: [{ + messageId: "noFunctionConstructor", + type: "CallExpression" + }] } ] }); From 5bd6ed47b53ebe0adec70f8ec51c1353d7be2ba6 Mon Sep 17 00:00:00 2001 From: Pig Fang Date: Thu, 21 May 2020 18:56:12 +0800 Subject: [PATCH 3/4] fix false positive --- lib/rules/no-new-func.js | 8 +++++++- tests/lib/rules/no-new-func.js | 4 +++- 2 files changed, 10 insertions(+), 2 deletions(-) diff --git a/lib/rules/no-new-func.js b/lib/rules/no-new-func.js index 1cd32b5a862..8399f852a1c 100644 --- a/lib/rules/no-new-func.js +++ b/lib/rules/no-new-func.js @@ -39,7 +39,13 @@ module.exports = { const node = ref.identifier; const { parent } = node; - if (parent && (parent.type === "NewExpression" || parent.type === "CallExpression")) { + if ( + parent && + ( + parent.type === "NewExpression" || + (parent.type === "CallExpression" && node === parent.callee) + ) + ) { context.report({ node: parent, messageId: "noFunctionConstructor" diff --git a/tests/lib/rules/no-new-func.js b/tests/lib/rules/no-new-func.js index 9c5c88bf302..50163ac020e 100644 --- a/tests/lib/rules/no-new-func.js +++ b/tests/lib/rules/no-new-func.js @@ -35,7 +35,9 @@ ruleTester.run("no-new-func", rule, { } }, "function Function() {}; Function()", - "var fn = function () { function Function() {}; Function() }" + "var fn = function () { function Function() {}; Function() }", + "var x = function Function() { Function(); }", + "call(Function)" ], invalid: [ { From 9169998fb2579fcfcc231ffbfafd65f38c96d9fa Mon Sep 17 00:00:00 2001 From: Pig Fang Date: Thu, 21 May 2020 22:22:01 +0800 Subject: [PATCH 4/4] fix --- lib/rules/no-new-func.js | 6 ++---- tests/lib/rules/no-new-func.js | 3 ++- 2 files changed, 4 insertions(+), 5 deletions(-) diff --git a/lib/rules/no-new-func.js b/lib/rules/no-new-func.js index 8399f852a1c..9af4e31cabf 100644 --- a/lib/rules/no-new-func.js +++ b/lib/rules/no-new-func.js @@ -41,10 +41,8 @@ module.exports = { if ( parent && - ( - parent.type === "NewExpression" || - (parent.type === "CallExpression" && node === parent.callee) - ) + (parent.type === "NewExpression" || parent.type === "CallExpression") && + node === parent.callee ) { context.report({ node: parent, diff --git a/tests/lib/rules/no-new-func.js b/tests/lib/rules/no-new-func.js index 50163ac020e..aa0542090e2 100644 --- a/tests/lib/rules/no-new-func.js +++ b/tests/lib/rules/no-new-func.js @@ -37,7 +37,8 @@ ruleTester.run("no-new-func", rule, { "function Function() {}; Function()", "var fn = function () { function Function() {}; Function() }", "var x = function Function() { Function(); }", - "call(Function)" + "call(Function)", + "new Class(Function)" ], invalid: [ {