From a3c04a7e9356d177ab2cab82934467e209612c82 Mon Sep 17 00:00:00 2001 From: Alexander Kamushkin <132259666+alexander-kamushkin-sonarsource@users.noreply.github.com> Date: Wed, 13 Sep 2023 08:51:17 +0200 Subject: [PATCH] =?UTF-8?q?Create=20rule=20S6757=20(`react/no-this-in-sfc?= =?UTF-8?q?=E2=80=8B=E2=80=8B`):=20`this`=20should=20not=20be=20used=20in?= =?UTF-8?q?=20functional=20components=20(#4155)?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../js/file-for-rules/javascript-S1172.json | 3 ++ .../js/file-for-rules/javascript-S139.json | 3 ++ .../js/file-for-rules/javascript-S1451.json | 3 ++ .../js/file-for-rules/javascript-S3798.json | 3 ++ .../js/file-for-rules/javascript-S6757.json | 5 +++ .../javascript-S6757.json | 19 ++++++++++ .../react-cloud-music/javascript-S6757.json | 8 ++++ its/sources/file-for-rules/S6757.js | 7 ++++ .../sonar/javascript/checks/CheckList.java | 1 + .../javascript/checks/NoThisInSfcCheck.java | 36 ++++++++++++++++++ .../javascript/rules/javascript/S6757.html | 38 +++++++++++++++++++ .../javascript/rules/javascript/S6757.json | 29 ++++++++++++++ .../rules/javascript/Sonar_way_profile.json | 3 +- 13 files changed, 157 insertions(+), 1 deletion(-) create mode 100644 its/ruling/src/test/expected/js/file-for-rules/javascript-S6757.json create mode 100644 its/ruling/src/test/expected/js/javascript-test-sources/javascript-S6757.json create mode 100644 its/ruling/src/test/expected/js/react-cloud-music/javascript-S6757.json create mode 100644 its/sources/file-for-rules/S6757.js create mode 100644 sonar-plugin/javascript-checks/src/main/java/org/sonar/javascript/checks/NoThisInSfcCheck.java create mode 100644 sonar-plugin/javascript-checks/src/main/resources/org/sonar/l10n/javascript/rules/javascript/S6757.html create mode 100644 sonar-plugin/javascript-checks/src/main/resources/org/sonar/l10n/javascript/rules/javascript/S6757.json diff --git a/its/ruling/src/test/expected/js/file-for-rules/javascript-S1172.json b/its/ruling/src/test/expected/js/file-for-rules/javascript-S1172.json index 464cc015e6f..e1474707a72 100644 --- a/its/ruling/src/test/expected/js/file-for-rules/javascript-S1172.json +++ b/its/ruling/src/test/expected/js/file-for-rules/javascript-S1172.json @@ -18,5 +18,8 @@ ], "file-for-rules:S6304.js": [ 5 +], +"file-for-rules:S6757.js": [ +2 ] } diff --git a/its/ruling/src/test/expected/js/file-for-rules/javascript-S139.json b/its/ruling/src/test/expected/js/file-for-rules/javascript-S139.json index 8b23aa9f382..2f3e09a6222 100644 --- a/its/ruling/src/test/expected/js/file-for-rules/javascript-S139.json +++ b/its/ruling/src/test/expected/js/file-for-rules/javascript-S139.json @@ -61,5 +61,8 @@ "file-for-rules:S6321.js": [ 65, 100 +], +"file-for-rules:S6757.js": [ +3 ] } diff --git a/its/ruling/src/test/expected/js/file-for-rules/javascript-S1451.json b/its/ruling/src/test/expected/js/file-for-rules/javascript-S1451.json index e619946bacf..6be4d54f9ba 100644 --- a/its/ruling/src/test/expected/js/file-for-rules/javascript-S1451.json +++ b/its/ruling/src/test/expected/js/file-for-rules/javascript-S1451.json @@ -170,6 +170,9 @@ "file-for-rules:S6746.js": [ 0 ], +"file-for-rules:S6757.js": [ +0 +], "file-for-rules:boundOrAssignedEvalOrArguments.js": [ 0 ] diff --git a/its/ruling/src/test/expected/js/file-for-rules/javascript-S3798.json b/its/ruling/src/test/expected/js/file-for-rules/javascript-S3798.json index 3b95a487693..af88de7886b 100644 --- a/its/ruling/src/test/expected/js/file-for-rules/javascript-S3798.json +++ b/its/ruling/src/test/expected/js/file-for-rules/javascript-S3798.json @@ -47,6 +47,9 @@ "file-for-rules:S6442.js": [ 3 ], +"file-for-rules:S6757.js": [ +2 +], "file-for-rules:boundOrAssignedEvalOrArguments.js": [ 2, 8 diff --git a/its/ruling/src/test/expected/js/file-for-rules/javascript-S6757.json b/its/ruling/src/test/expected/js/file-for-rules/javascript-S6757.json new file mode 100644 index 00000000000..3c1146daace --- /dev/null +++ b/its/ruling/src/test/expected/js/file-for-rules/javascript-S6757.json @@ -0,0 +1,5 @@ +{ +"file-for-rules:S6757.js": [ +3 +] +} diff --git a/its/ruling/src/test/expected/js/javascript-test-sources/javascript-S6757.json b/its/ruling/src/test/expected/js/javascript-test-sources/javascript-S6757.json new file mode 100644 index 00000000000..ff35a18b5f4 --- /dev/null +++ b/its/ruling/src/test/expected/js/javascript-test-sources/javascript-S6757.json @@ -0,0 +1,19 @@ +{ +"javascript-test-sources:src/ace/src/edit_session/bracket_match.js": [ +114, +171 +], +"javascript-test-sources:src/ace/src/editor.js": [ +2518, +2519, +2521 +], +"javascript-test-sources:src/ace/src/layer/font_metrics.js": [ +103, +111 +], +"javascript-test-sources:src/ace/src/mode/folding/mixed.js": [ +18, +20 +] +} diff --git a/its/ruling/src/test/expected/js/react-cloud-music/javascript-S6757.json b/its/ruling/src/test/expected/js/react-cloud-music/javascript-S6757.json new file mode 100644 index 00000000000..770da23a969 --- /dev/null +++ b/its/ruling/src/test/expected/js/react-cloud-music/javascript-S6757.json @@ -0,0 +1,8 @@ +{ +"react-cloud-music:src/baseUI/music-note/index.jsx": [ +47, +48, +49, +51 +] +} diff --git a/its/sources/file-for-rules/S6757.js b/its/sources/file-for-rules/S6757.js new file mode 100644 index 00000000000..490ade0155d --- /dev/null +++ b/its/sources/file-for-rules/S6757.js @@ -0,0 +1,7 @@ +import React from 'react'; +function MyComponent(props){ + const foo = this.props.bar; // Noncompliant: remove 'this' + return ( +
Referring to this
in React functional component would be an error because the components are just regular JavaScript functions and do
+not have an object assotiated with them. The functional components receive its props as a first argument to the component function, so you can access
+then directly, and it is a common style to destructure them right away.
+function UserProfile({firstName, lastName}){ + return ( + <div className="user">{firstName} {lastName}</div> + ); +} ++
React also supports legacy class-based components, where this
keyword refers to the component instance object, but this style of
+writing components is no longer recommended, and mixing it with functional components will lead to errors.
+function MyComponent(props){ + const foo = this.props.bar; // Noncompliant: remove 'this' + return ( + <div>{foo}</div> + ); +} ++
To fix the issue remove this
from your functional component code (are you mixing functional and class-based component styles?)
+function MyComponent(props){ + const foo = props.bar; + return ( + <div>{foo}</div> + ); +} ++