From 1cb6e4a36f85efdcd2dcb1165571fb0b8cdaf25e Mon Sep 17 00:00:00 2001 From: Daniel Bartholomae Date: Sat, 10 Dec 2022 11:09:17 +0100 Subject: [PATCH 01/14] refactor: extract error list into a function Suggestions will be different for different errors, so a constant object won't work anymore --- tests/lib/rules/no-return-await.js | 70 +++++++++++++++++------------- 1 file changed, 39 insertions(+), 31 deletions(-) diff --git a/tests/lib/rules/no-return-await.js b/tests/lib/rules/no-return-await.js index 508d7cb8528..d03486b99d3 100644 --- a/tests/lib/rules/no-return-await.js +++ b/tests/lib/rules/no-return-await.js @@ -16,8 +16,16 @@ const { RuleTester } = require("../../../lib/rule-tester"); // Tests //------------------------------------------------------------------------------ -// pending https://github.com/eslint/espree/issues/304, the type should be "Keyword" -const errors = [{ messageId: "redundantUseOfAwait", type: "Identifier" }]; +/** + * Creates the list of errors that should be found by this rule + * @returns {Array} the list of errors + */ +function createErrorList() { + + // pending https://github.com/eslint/espree/issues/304, the type should be "Keyword" + return [{ messageId: "redundantUseOfAwait", type: "Identifier" }]; +} + const ruleTester = new RuleTester({ parserOptions: { ecmaVersion: 2017 } }); @@ -138,99 +146,99 @@ ruleTester.run("no-return-await", rule, { invalid: [ { code: "\nasync function foo() {\n\treturn await bar();\n}\n", - errors + errors: createErrorList() }, { code: "\nasync function foo() {\n\treturn (a, await bar());\n}\n", - errors + errors: createErrorList() }, { code: "\nasync function foo() {\n\treturn (a, b, await bar());\n}\n", - errors + errors: createErrorList() }, { code: "\nasync function foo() {\n\treturn (a && await bar());\n}\n", - errors + errors: createErrorList() }, { code: "\nasync function foo() {\n\treturn (a && b && await bar());\n}\n", - errors + errors: createErrorList() }, { code: "\nasync function foo() {\n\treturn (a || await bar());\n}\n", - errors + errors: createErrorList() }, { code: "\nasync function foo() {\n\treturn (a, b, (c, d, await bar()));\n}\n", - errors + errors: createErrorList() }, { code: "\nasync function foo() {\n\treturn (a, b, (c && await bar()));\n}\n", - errors + errors: createErrorList() }, { code: "\nasync function foo() {\n\treturn (await baz(), b, await bar());\n}\n", - errors + errors: createErrorList() }, { code: "\nasync function foo() {\n\treturn (baz() ? await bar() : b);\n}\n", - errors + errors: createErrorList() }, { code: "\nasync function foo() {\n\treturn (baz() ? a : await bar());\n}\n", - errors + errors: createErrorList() }, { code: "\nasync function foo() {\n\treturn (baz() ? (a, await bar()) : b);\n}\n", - errors + errors: createErrorList() }, { code: "\nasync function foo() {\n\treturn (baz() ? a : (b, await bar()));\n}\n", - errors + errors: createErrorList() }, { code: "\nasync function foo() {\n\treturn (baz() ? (a && await bar()) : b);\n}\n", - errors + errors: createErrorList() }, { code: "\nasync function foo() {\n\treturn (baz() ? a : (b && await bar()));\n}\n", - errors + errors: createErrorList() }, { code: "\nasync () => { return await bar(); }\n", - errors + errors: createErrorList() }, { code: "\nasync () => await bar()\n", - errors + errors: createErrorList() }, { code: "\nasync () => (a, b, await bar())\n", - errors + errors: createErrorList() }, { code: "\nasync () => (a && await bar())\n", - errors + errors: createErrorList() }, { code: "\nasync () => (baz() ? await bar() : b)\n", - errors + errors: createErrorList() }, { code: "\nasync () => (baz() ? a : (b, await bar()))\n", - errors + errors: createErrorList() }, { code: "\nasync () => (baz() ? a : (b && await bar()))\n", - errors + errors: createErrorList() }, { code: "\nasync function foo() {\nif (a) {\n\t\tif (b) {\n\t\t\treturn await bar();\n\t\t}\n\t}\n}\n", - errors + errors: createErrorList() }, { code: "\nasync () => {\nif (a) {\n\t\tif (b) {\n\t\t\treturn await bar();\n\t\t}\n\t}\n}\n", - errors + errors: createErrorList() }, { code: ` @@ -241,7 +249,7 @@ ruleTester.run("no-return-await", rule, { } } `, - errors + errors: createErrorList() }, { code: ` @@ -252,7 +260,7 @@ ruleTester.run("no-return-await", rule, { } } `, - errors + errors: createErrorList() }, { code: ` @@ -262,7 +270,7 @@ ruleTester.run("no-return-await", rule, { } } catch (e) {} `, - errors + errors: createErrorList() }, { code: ` @@ -270,7 +278,7 @@ ruleTester.run("no-return-await", rule, { async () => await bar(); } catch (e) {} `, - errors + errors: createErrorList() }, { code: ` @@ -284,7 +292,7 @@ ruleTester.run("no-return-await", rule, { } } `, - errors + errors: createErrorList() } ] }); From 60fe835e3af5fa7bb41ed253c619f6970b69f05c Mon Sep 17 00:00:00 2001 From: Daniel Bartholomae Date: Sat, 10 Dec 2022 11:35:11 +0100 Subject: [PATCH 02/14] feat: suggest removing await in no-return-await --- lib/rules/no-return-await.js | 16 +++- tests/lib/rules/no-return-await.js | 114 +++++++++++++++++++++-------- 2 files changed, 98 insertions(+), 32 deletions(-) diff --git a/lib/rules/no-return-await.js b/lib/rules/no-return-await.js index 3007c8c877d..9ee05638e4b 100644 --- a/lib/rules/no-return-await.js +++ b/lib/rules/no-return-await.js @@ -13,6 +13,7 @@ const astUtils = require("./utils/ast-utils"); /** @type {import('../shared/types').Rule} */ module.exports = { meta: { + hasSuggestions: true, type: "suggestion", docs: { @@ -29,6 +30,7 @@ module.exports = { ], messages: { + removeAwait: "Remove await after return statement.", redundantUseOfAwait: "Redundant use of `await` on a return value." } }, @@ -44,7 +46,19 @@ module.exports = { context.report({ node: context.getSourceCode().getFirstToken(node), loc: node.loc, - messageId: "redundantUseOfAwait" + messageId: "redundantUseOfAwait", + suggest: [ + { + messageId: "removeAwait", + data: { type: "block" }, + fix(fixer) { + const range = [node.range[0], node.range[0] + 6]; + + return fixer.replaceTextRange(range, ""); + } + } + ] + }); } diff --git a/tests/lib/rules/no-return-await.js b/tests/lib/rules/no-return-await.js index d03486b99d3..c46dcb57ad2 100644 --- a/tests/lib/rules/no-return-await.js +++ b/tests/lib/rules/no-return-await.js @@ -18,12 +18,20 @@ const { RuleTester } = require("../../../lib/rule-tester"); /** * Creates the list of errors that should be found by this rule + * @param {Object} options Options for creating errors + * @param {string} options.suggestionOutput The suggested output * @returns {Array} the list of errors */ -function createErrorList() { +function createErrorList({ suggestionOutput: output }) { // pending https://github.com/eslint/espree/issues/304, the type should be "Keyword" - return [{ messageId: "redundantUseOfAwait", type: "Identifier" }]; + return [{ + messageId: "redundantUseOfAwait", + type: "Identifier", + suggestions: [{ + messageId: "removeAwait", data: { type: "block" }, output + }] + }]; } @@ -146,99 +154,99 @@ ruleTester.run("no-return-await", rule, { invalid: [ { code: "\nasync function foo() {\n\treturn await bar();\n}\n", - errors: createErrorList() + errors: createErrorList({ suggestionOutput: "\nasync function foo() {\n\treturn bar();\n}\n" }) }, { code: "\nasync function foo() {\n\treturn (a, await bar());\n}\n", - errors: createErrorList() + errors: createErrorList({ suggestionOutput: "\nasync function foo() {\n\treturn (a, bar());\n}\n" }) }, { code: "\nasync function foo() {\n\treturn (a, b, await bar());\n}\n", - errors: createErrorList() + errors: createErrorList({ suggestionOutput: "\nasync function foo() {\n\treturn (a, b, bar());\n}\n" }) }, { code: "\nasync function foo() {\n\treturn (a && await bar());\n}\n", - errors: createErrorList() + errors: createErrorList({ suggestionOutput: "\nasync function foo() {\n\treturn (a && bar());\n}\n" }) }, { code: "\nasync function foo() {\n\treturn (a && b && await bar());\n}\n", - errors: createErrorList() + errors: createErrorList({ suggestionOutput: "\nasync function foo() {\n\treturn (a && b && bar());\n}\n" }) }, { code: "\nasync function foo() {\n\treturn (a || await bar());\n}\n", - errors: createErrorList() + errors: createErrorList({ suggestionOutput: "\nasync function foo() {\n\treturn (a || bar());\n}\n" }) }, { code: "\nasync function foo() {\n\treturn (a, b, (c, d, await bar()));\n}\n", - errors: createErrorList() + errors: createErrorList({ suggestionOutput: "\nasync function foo() {\n\treturn (a, b, (c, d, bar()));\n}\n" }) }, { code: "\nasync function foo() {\n\treturn (a, b, (c && await bar()));\n}\n", - errors: createErrorList() + errors: createErrorList({ suggestionOutput: "\nasync function foo() {\n\treturn (a, b, (c && bar()));\n}\n" }) }, { code: "\nasync function foo() {\n\treturn (await baz(), b, await bar());\n}\n", - errors: createErrorList() + errors: createErrorList({ suggestionOutput: "\nasync function foo() {\n\treturn (await baz(), b, bar());\n}\n" }) }, { code: "\nasync function foo() {\n\treturn (baz() ? await bar() : b);\n}\n", - errors: createErrorList() + errors: createErrorList({ suggestionOutput: "\nasync function foo() {\n\treturn (baz() ? bar() : b);\n}\n" }) }, { code: "\nasync function foo() {\n\treturn (baz() ? a : await bar());\n}\n", - errors: createErrorList() + errors: createErrorList({ suggestionOutput: "\nasync function foo() {\n\treturn (baz() ? a : bar());\n}\n" }) }, { code: "\nasync function foo() {\n\treturn (baz() ? (a, await bar()) : b);\n}\n", - errors: createErrorList() + errors: createErrorList({ suggestionOutput: "\nasync function foo() {\n\treturn (baz() ? (a, bar()) : b);\n}\n" }) }, { code: "\nasync function foo() {\n\treturn (baz() ? a : (b, await bar()));\n}\n", - errors: createErrorList() + errors: createErrorList({ suggestionOutput: "\nasync function foo() {\n\treturn (baz() ? a : (b, bar()));\n}\n" }) }, { code: "\nasync function foo() {\n\treturn (baz() ? (a && await bar()) : b);\n}\n", - errors: createErrorList() + errors: createErrorList({ suggestionOutput: "\nasync function foo() {\n\treturn (baz() ? (a && bar()) : b);\n}\n" }) }, { code: "\nasync function foo() {\n\treturn (baz() ? a : (b && await bar()));\n}\n", - errors: createErrorList() + errors: createErrorList({ suggestionOutput: "\nasync function foo() {\n\treturn (baz() ? a : (b && bar()));\n}\n" }) }, { code: "\nasync () => { return await bar(); }\n", - errors: createErrorList() + errors: createErrorList({ suggestionOutput: "\nasync () => { return bar(); }\n" }) }, { code: "\nasync () => await bar()\n", - errors: createErrorList() + errors: createErrorList({ suggestionOutput: "\nasync () => bar()\n" }) }, { code: "\nasync () => (a, b, await bar())\n", - errors: createErrorList() + errors: createErrorList({ suggestionOutput: "\nasync () => (a, b, bar())\n" }) }, { code: "\nasync () => (a && await bar())\n", - errors: createErrorList() + errors: createErrorList({ suggestionOutput: "\nasync () => (a && bar())\n" }) }, { code: "\nasync () => (baz() ? await bar() : b)\n", - errors: createErrorList() + errors: createErrorList({ suggestionOutput: "\nasync () => (baz() ? bar() : b)\n" }) }, { code: "\nasync () => (baz() ? a : (b, await bar()))\n", - errors: createErrorList() + errors: createErrorList({ suggestionOutput: "\nasync () => (baz() ? a : (b, bar()))\n" }) }, { code: "\nasync () => (baz() ? a : (b && await bar()))\n", - errors: createErrorList() + errors: createErrorList({ suggestionOutput: "\nasync () => (baz() ? a : (b && bar()))\n" }) }, { code: "\nasync function foo() {\nif (a) {\n\t\tif (b) {\n\t\t\treturn await bar();\n\t\t}\n\t}\n}\n", - errors: createErrorList() + errors: createErrorList({ suggestionOutput: "\nasync function foo() {\nif (a) {\n\t\tif (b) {\n\t\t\treturn bar();\n\t\t}\n\t}\n}\n" }) }, { code: "\nasync () => {\nif (a) {\n\t\tif (b) {\n\t\t\treturn await bar();\n\t\t}\n\t}\n}\n", - errors: createErrorList() + errors: createErrorList({ suggestionOutput: "\nasync () => {\nif (a) {\n\t\tif (b) {\n\t\t\treturn bar();\n\t\t}\n\t}\n}\n" }) }, { code: ` @@ -249,7 +257,16 @@ ruleTester.run("no-return-await", rule, { } } `, - errors: createErrorList() + errors: createErrorList({ + suggestionOutput: ` + async function foo() { + try {} + finally { + return bar(); + } + } + ` + }) }, { code: ` @@ -260,7 +277,16 @@ ruleTester.run("no-return-await", rule, { } } `, - errors: createErrorList() + errors: createErrorList({ + suggestionOutput: ` + async function foo() { + try {} + catch (e) { + return bar(); + } + } + ` + }) }, { code: ` @@ -270,7 +296,15 @@ ruleTester.run("no-return-await", rule, { } } catch (e) {} `, - errors: createErrorList() + errors: createErrorList({ + suggestionOutput: ` + try { + async function foo() { + return bar(); + } + } catch (e) {} + ` + }) }, { code: ` @@ -278,7 +312,13 @@ ruleTester.run("no-return-await", rule, { async () => await bar(); } catch (e) {} `, - errors: createErrorList() + errors: createErrorList({ + suggestionOutput: ` + try { + async () => bar(); + } catch (e) {} + ` + }) }, { code: ` @@ -292,7 +332,19 @@ ruleTester.run("no-return-await", rule, { } } `, - errors: createErrorList() + errors: createErrorList({ + suggestionOutput: ` + async function foo() { + try {} + catch (e) { + try {} + catch (e) { + return bar(); + } + } + } + ` + }) } ] }); From 04675b3b0c44f5219ff7a664587730e4e78e2573 Mon Sep 17 00:00:00 2001 From: Daniel Bartholomae Date: Sat, 10 Dec 2022 16:49:22 +0100 Subject: [PATCH 03/14] Fix suggestion message Co-authored-by: Milos Djermanovic --- lib/rules/no-return-await.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/rules/no-return-await.js b/lib/rules/no-return-await.js index 9ee05638e4b..539807ceed9 100644 --- a/lib/rules/no-return-await.js +++ b/lib/rules/no-return-await.js @@ -30,7 +30,7 @@ module.exports = { ], messages: { - removeAwait: "Remove await after return statement.", + removeAwait: "Remove `await` after `return`.", redundantUseOfAwait: "Redundant use of `await` on a return value." } }, From 4a14630f4f745c6421aeaf470dad47c473c90fe1 Mon Sep 17 00:00:00 2001 From: Daniel Bartholomae Date: Sun, 11 Dec 2022 13:46:02 +0100 Subject: [PATCH 04/14] refactor: remove unused data --- lib/rules/no-return-await.js | 1 - tests/lib/rules/no-return-await.js | 2 +- 2 files changed, 1 insertion(+), 2 deletions(-) diff --git a/lib/rules/no-return-await.js b/lib/rules/no-return-await.js index 539807ceed9..ec788995bb1 100644 --- a/lib/rules/no-return-await.js +++ b/lib/rules/no-return-await.js @@ -50,7 +50,6 @@ module.exports = { suggest: [ { messageId: "removeAwait", - data: { type: "block" }, fix(fixer) { const range = [node.range[0], node.range[0] + 6]; diff --git a/tests/lib/rules/no-return-await.js b/tests/lib/rules/no-return-await.js index c46dcb57ad2..0724ccfbc16 100644 --- a/tests/lib/rules/no-return-await.js +++ b/tests/lib/rules/no-return-await.js @@ -29,7 +29,7 @@ function createErrorList({ suggestionOutput: output }) { messageId: "redundantUseOfAwait", type: "Identifier", suggestions: [{ - messageId: "removeAwait", data: { type: "block" }, output + messageId: "removeAwait", output }] }]; } From 1d20ef1cd78975c13f27dcae7b7a2c3231f981de Mon Sep 17 00:00:00 2001 From: Daniel Bartholomae Date: Sun, 11 Dec 2022 14:27:37 +0100 Subject: [PATCH 05/14] fix: only trim after await if there is a space --- lib/rules/no-return-await.js | 9 ++++++++- tests/lib/rules/no-return-await.js | 4 ++++ 2 files changed, 12 insertions(+), 1 deletion(-) diff --git a/lib/rules/no-return-await.js b/lib/rules/no-return-await.js index ec788995bb1..7d4e293bde1 100644 --- a/lib/rules/no-return-await.js +++ b/lib/rules/no-return-await.js @@ -43,6 +43,13 @@ module.exports = { * @returns {void} */ function reportUnnecessaryAwait(node) { + const sourceCodeText = context.getSourceCode().text; + const startOfAwait = node.range[0]; + const endOfAwait = startOfAwait + "await".length; + const characterAfterAwait = sourceCodeText.slice(endOfAwait, endOfAwait + 1); + + const trimLength = characterAfterAwait === " " ? 1 : 0; + context.report({ node: context.getSourceCode().getFirstToken(node), loc: node.loc, @@ -51,7 +58,7 @@ module.exports = { { messageId: "removeAwait", fix(fixer) { - const range = [node.range[0], node.range[0] + 6]; + const range = [startOfAwait, endOfAwait + trimLength]; return fixer.replaceTextRange(range, ""); } diff --git a/tests/lib/rules/no-return-await.js b/tests/lib/rules/no-return-await.js index 0724ccfbc16..dfd0fa19be1 100644 --- a/tests/lib/rules/no-return-await.js +++ b/tests/lib/rules/no-return-await.js @@ -156,6 +156,10 @@ ruleTester.run("no-return-await", rule, { code: "\nasync function foo() {\n\treturn await bar();\n}\n", errors: createErrorList({ suggestionOutput: "\nasync function foo() {\n\treturn bar();\n}\n" }) }, + { + code: "\nasync function foo() {\n\treturn await(bar());\n}\n", + errors: createErrorList({ suggestionOutput: "\nasync function foo() {\n\treturn (bar());\n}\n" }) + }, { code: "\nasync function foo() {\n\treturn (a, await bar());\n}\n", errors: createErrorList({ suggestionOutput: "\nasync function foo() {\n\treturn (a, bar());\n}\n" }) From 5cfaa84b61095b8e247e91c9f35b4e4f5db91db6 Mon Sep 17 00:00:00 2001 From: Daniel Bartholomae Date: Sun, 11 Dec 2022 14:45:43 +0100 Subject: [PATCH 06/14] refactor: allow expecting no suggestion --- tests/lib/rules/no-return-await.js | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/tests/lib/rules/no-return-await.js b/tests/lib/rules/no-return-await.js index dfd0fa19be1..ae6e4354f83 100644 --- a/tests/lib/rules/no-return-await.js +++ b/tests/lib/rules/no-return-await.js @@ -22,15 +22,15 @@ const { RuleTester } = require("../../../lib/rule-tester"); * @param {string} options.suggestionOutput The suggested output * @returns {Array} the list of errors */ -function createErrorList({ suggestionOutput: output }) { +function createErrorList({ suggestionOutput: output } = {}) { // pending https://github.com/eslint/espree/issues/304, the type should be "Keyword" return [{ messageId: "redundantUseOfAwait", type: "Identifier", - suggestions: [{ + suggestions: output ? [{ messageId: "removeAwait", output - }] + }] : null }]; } From 80bb8d7c1f44d6c683262cb3f6c3091e7153ffed Mon Sep 17 00:00:00 2001 From: Daniel Bartholomae Date: Sun, 11 Dec 2022 14:50:00 +0100 Subject: [PATCH 07/14] refactor: move code for fixing into fix function --- lib/rules/no-return-await.js | 15 ++++++++------- 1 file changed, 8 insertions(+), 7 deletions(-) diff --git a/lib/rules/no-return-await.js b/lib/rules/no-return-await.js index 7d4e293bde1..37982656fd2 100644 --- a/lib/rules/no-return-await.js +++ b/lib/rules/no-return-await.js @@ -43,13 +43,6 @@ module.exports = { * @returns {void} */ function reportUnnecessaryAwait(node) { - const sourceCodeText = context.getSourceCode().text; - const startOfAwait = node.range[0]; - const endOfAwait = startOfAwait + "await".length; - const characterAfterAwait = sourceCodeText.slice(endOfAwait, endOfAwait + 1); - - const trimLength = characterAfterAwait === " " ? 1 : 0; - context.report({ node: context.getSourceCode().getFirstToken(node), loc: node.loc, @@ -58,6 +51,14 @@ module.exports = { { messageId: "removeAwait", fix(fixer) { + const sourceCodeText = context.getSourceCode().text; + + const startOfAwait = node.range[0]; + const endOfAwait = startOfAwait + "await".length; + + const characterAfterAwait = sourceCodeText.slice(endOfAwait, endOfAwait + 1); + const trimLength = characterAfterAwait === " " ? 1 : 0; + const range = [startOfAwait, endOfAwait + trimLength]; return fixer.replaceTextRange(range, ""); From ee4087d97b1ccf0960c3787304f172c9650cdf41 Mon Sep 17 00:00:00 2001 From: Daniel Bartholomae Date: Sun, 11 Dec 2022 15:01:45 +0100 Subject: [PATCH 08/14] fix: do not suggest a fix if await and awaited expression are not on th same line --- lib/rules/no-return-await.js | 6 ++++++ tests/lib/rules/no-return-await.js | 29 ++++++++++++++++++++++++++++- 2 files changed, 34 insertions(+), 1 deletion(-) diff --git a/lib/rules/no-return-await.js b/lib/rules/no-return-await.js index 37982656fd2..1212a980fdf 100644 --- a/lib/rules/no-return-await.js +++ b/lib/rules/no-return-await.js @@ -51,6 +51,12 @@ module.exports = { { messageId: "removeAwait", fix(fixer) { + const areAwaitAndAwaitedExpressionOnTheSameLine = node.loc.start.line === node.argument.loc.start.line; + + if (!areAwaitAndAwaitedExpressionOnTheSameLine) { + return null; + } + const sourceCodeText = context.getSourceCode().text; const startOfAwait = node.range[0]; diff --git a/tests/lib/rules/no-return-await.js b/tests/lib/rules/no-return-await.js index ae6e4354f83..3d0077a274d 100644 --- a/tests/lib/rules/no-return-await.js +++ b/tests/lib/rules/no-return-await.js @@ -30,7 +30,7 @@ function createErrorList({ suggestionOutput: output } = {}) { type: "Identifier", suggestions: output ? [{ messageId: "removeAwait", output - }] : null + }] : [] }]; } @@ -349,6 +349,33 @@ ruleTester.run("no-return-await", rule, { } ` }) + }, + { + code: ` + async function foo() { + return await new Promise(resolve => { + resolve(5); + }); + } + `, + errors: createErrorList({ + suggestionOutput: ` + async function foo() { + return new Promise(resolve => { + resolve(5); + }); + } + ` + }) + }, + { + code: ` + async function foo() { + return await // Test + 5; + } + `, + errors: createErrorList() } ] }); From abd1d489ad26a517df72e16eb0762286e67d3a13 Mon Sep 17 00:00:00 2001 From: Daniel Bartholomae Date: Wed, 14 Dec 2022 19:36:38 +0100 Subject: [PATCH 09/14] Simplify suggestion message Co-authored-by: Milos Djermanovic --- lib/rules/no-return-await.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/rules/no-return-await.js b/lib/rules/no-return-await.js index 1212a980fdf..525758b5460 100644 --- a/lib/rules/no-return-await.js +++ b/lib/rules/no-return-await.js @@ -30,7 +30,7 @@ module.exports = { ], messages: { - removeAwait: "Remove `await` after `return`.", + removeAwait: "Remove redundant `await`.", redundantUseOfAwait: "Redundant use of `await` on a return value." } }, From 2a257d6b62ea55a5fbd61b7d0ad1962820e396a9 Mon Sep 17 00:00:00 2001 From: Daniel Bartholomae Date: Wed, 14 Dec 2022 19:40:59 +0100 Subject: [PATCH 10/14] Simplify single-character access Co-authored-by: Milos Djermanovic --- lib/rules/no-return-await.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/rules/no-return-await.js b/lib/rules/no-return-await.js index 525758b5460..7e12aad89ba 100644 --- a/lib/rules/no-return-await.js +++ b/lib/rules/no-return-await.js @@ -62,7 +62,7 @@ module.exports = { const startOfAwait = node.range[0]; const endOfAwait = startOfAwait + "await".length; - const characterAfterAwait = sourceCodeText.slice(endOfAwait, endOfAwait + 1); + const characterAfterAwait = sourceCodeText[endOfAwait]; const trimLength = characterAfterAwait === " " ? 1 : 0; const range = [startOfAwait, endOfAwait + trimLength]; From ab271b186baa03188f107aa9c1d5e971b75bc45b Mon Sep 17 00:00:00 2001 From: Daniel Bartholomae Date: Wed, 14 Dec 2022 19:41:16 +0100 Subject: [PATCH 11/14] Simplify removing a range Co-authored-by: Milos Djermanovic --- lib/rules/no-return-await.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/rules/no-return-await.js b/lib/rules/no-return-await.js index 7e12aad89ba..d17c486aa70 100644 --- a/lib/rules/no-return-await.js +++ b/lib/rules/no-return-await.js @@ -67,7 +67,7 @@ module.exports = { const range = [startOfAwait, endOfAwait + trimLength]; - return fixer.replaceTextRange(range, ""); + return fixer.removeRange(range); } } ] From 23318401d890df5b1aa037bd67effd0fe202cb57 Mon Sep 17 00:00:00 2001 From: Daniel Bartholomae Date: Thu, 15 Dec 2022 22:20:37 +0100 Subject: [PATCH 12/14] feat: suggest removing await when expression starts with ( --- lib/rules/no-return-await.js | 5 ++++- tests/lib/rules/no-return-await.js | 18 ++++++++++++++++++ 2 files changed, 22 insertions(+), 1 deletion(-) diff --git a/lib/rules/no-return-await.js b/lib/rules/no-return-await.js index d17c486aa70..26eaedda00c 100644 --- a/lib/rules/no-return-await.js +++ b/lib/rules/no-return-await.js @@ -51,7 +51,10 @@ module.exports = { { messageId: "removeAwait", fix(fixer) { - const areAwaitAndAwaitedExpressionOnTheSameLine = node.loc.start.line === node.argument.loc.start.line; + const sourceCode = context.getSourceCode(); + const [awaitToken, tokenAfterAwait] = sourceCode.getTokens(node); + + const areAwaitAndAwaitedExpressionOnTheSameLine = awaitToken.loc.start.line === tokenAfterAwait.loc.start.line; if (!areAwaitAndAwaitedExpressionOnTheSameLine) { return null; diff --git a/tests/lib/rules/no-return-await.js b/tests/lib/rules/no-return-await.js index 3d0077a274d..b9184a0a532 100644 --- a/tests/lib/rules/no-return-await.js +++ b/tests/lib/rules/no-return-await.js @@ -368,6 +368,24 @@ ruleTester.run("no-return-await", rule, { ` }) }, + { + code: ` + async () => { + return await ( + foo() + ) + }; + `, + errors: createErrorList({ + suggestionOutput: ` + async () => { + return ( + foo() + ) + }; + ` + }) + }, { code: ` async function foo() { From 725423ad5bfec3342f1fa574e0232492289b9343 Mon Sep 17 00:00:00 2001 From: Daniel Bartholomae Date: Thu, 15 Dec 2022 22:20:59 +0100 Subject: [PATCH 13/14] refactor: use awaitToken to determine await range --- lib/rules/no-return-await.js | 7 ++----- 1 file changed, 2 insertions(+), 5 deletions(-) diff --git a/lib/rules/no-return-await.js b/lib/rules/no-return-await.js index 26eaedda00c..956dfc6a79a 100644 --- a/lib/rules/no-return-await.js +++ b/lib/rules/no-return-await.js @@ -60,12 +60,9 @@ module.exports = { return null; } - const sourceCodeText = context.getSourceCode().text; + const [startOfAwait, endOfAwait] = awaitToken.range; - const startOfAwait = node.range[0]; - const endOfAwait = startOfAwait + "await".length; - - const characterAfterAwait = sourceCodeText[endOfAwait]; + const characterAfterAwait = sourceCode.text[endOfAwait]; const trimLength = characterAfterAwait === " " ? 1 : 0; const range = [startOfAwait, endOfAwait + trimLength]; From 6160c18bdc5382dd1dfd78de05b352a132aa71fa Mon Sep 17 00:00:00 2001 From: Daniel Bartholomae Date: Fri, 16 Dec 2022 12:33:51 +0100 Subject: [PATCH 14/14] fix: use more performant way to identify tokens --- lib/rules/no-return-await.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/rules/no-return-await.js b/lib/rules/no-return-await.js index 956dfc6a79a..ecfd6697a13 100644 --- a/lib/rules/no-return-await.js +++ b/lib/rules/no-return-await.js @@ -52,7 +52,7 @@ module.exports = { messageId: "removeAwait", fix(fixer) { const sourceCode = context.getSourceCode(); - const [awaitToken, tokenAfterAwait] = sourceCode.getTokens(node); + const [awaitToken, tokenAfterAwait] = sourceCode.getFirstTokens(node, 2); const areAwaitAndAwaitedExpressionOnTheSameLine = awaitToken.loc.start.line === tokenAfterAwait.loc.start.line;