Skip to content

Commit 49380b5

Browse files
authored
Provide a non empty profile (#30)
* Prepare a non empty built-in profile
1 parent 1fa6261 commit 49380b5

File tree

32 files changed

+635
-34
lines changed

32 files changed

+635
-34
lines changed

rust-checks/pom.xml

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -28,6 +28,10 @@
2828
<groupId>commons-io</groupId>
2929
<artifactId>commons-io</artifactId>
3030
</dependency>
31+
<dependency>
32+
<groupId>org.sonarsource.analyzer-commons</groupId>
33+
<artifactId>sonar-analyzer-test-commons</artifactId>
34+
</dependency>
3135

3236
<!-- test dependencies -->
3337
<dependency>

rust-checks/src/main/java/org/elegoff/rust/checks/CheckList.java

Lines changed: 11 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -17,20 +17,24 @@
1717
* along with this program; if not, write to the Free Software Foundation,
1818
* Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
1919
*/
20-
2120
package org.elegoff.rust.checks;
2221

2322
import java.util.*;
2423

2524
public class CheckList {
26-
public static final String REPOSITORY_KEY = "rust";
25+
public static final String REPOSITORY_KEY = "community-rust";
2726

28-
private CheckList() { }
27+
private CheckList() {
28+
}
2929

30-
public static List<Class<? extends RustCheck>> getRustChecks() {
31-
//empty array so far, until a first rule is defined
32-
return new ArrayList<>();
30+
public static List<Class<?>> getRustChecks() {
31+
return Arrays.asList(
32+
LineLengthCheck.class,
33+
FunctionParametersCountCheck.class,
34+
EmptyEnumCheck.class
35+
);
3336
}
37+
}
38+
3439

3540

36-
}
Lines changed: 52 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,52 @@
1+
/**
2+
* Sonar Rust Plugin (Community)
3+
* Copyright (C) 2021 Eric Le Goff
4+
* http://github.com/elegoff/sonar-rust
5+
*
6+
* This program is free software; you can redistribute it and/or
7+
* modify it under the terms of the GNU Lesser General Public
8+
* License as published by the Free Software Foundation; either
9+
* version 3 of the License, or (at your option) any later version.
10+
*
11+
* This program is distributed in the hope that it will be useful,
12+
* but WITHOUT ANY WARRANTY; without even the implied warranty of
13+
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14+
* Lesser General Public License for more details.
15+
*
16+
* You should have received a copy of the GNU Lesser General Public License
17+
* along with this program; if not, write to the Free Software Foundation,
18+
* Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
19+
*/
20+
package org.elegoff.rust.checks;
21+
22+
import com.sonar.sslr.api.AstNode;
23+
import com.sonar.sslr.api.AstNodeType;
24+
import org.sonar.check.Rule;
25+
import org.sonar.rust.RustGrammar;
26+
27+
import java.util.Collections;
28+
import java.util.Set;
29+
30+
@Rule(key = "EmptyEnum")
31+
public class EmptyEnumCheck extends RustCheck {
32+
@Override
33+
public Set<AstNodeType> subscribedKinds() {
34+
return Collections.singleton(RustGrammar.ENUMERATION);
35+
}
36+
37+
@Override
38+
public void visitNode(AstNode node) {
39+
AstNode enumItems = node.getFirstChild(RustGrammar.ENUM_ITEMS);
40+
41+
if (enumItems == null) {
42+
raiseIssue(node);
43+
}
44+
}
45+
46+
private void raiseIssue(AstNode node) {
47+
addIssue("Either remove or fill this empty enumeration.", node);
48+
}
49+
50+
}
51+
52+
Lines changed: 64 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,64 @@
1+
/**
2+
* Sonar Rust Plugin (Community)
3+
* Copyright (C) 2021 Eric Le Goff
4+
* http://github.com/elegoff/sonar-rust
5+
*
6+
* This program is free software; you can redistribute it and/or
7+
* modify it under the terms of the GNU Lesser General Public
8+
* License as published by the Free Software Foundation; either
9+
* version 3 of the License, or (at your option) any later version.
10+
*
11+
* This program is distributed in the hope that it will be useful,
12+
* but WITHOUT ANY WARRANTY; without even the implied warranty of
13+
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14+
* Lesser General Public License for more details.
15+
*
16+
* You should have received a copy of the GNU Lesser General Public License
17+
* along with this program; if not, write to the Free Software Foundation,
18+
* Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
19+
*/
20+
package org.elegoff.rust.checks;
21+
22+
import com.sonar.sslr.api.AstNode;
23+
import com.sonar.sslr.api.AstNodeType;
24+
import org.sonar.check.Rule;
25+
import org.sonar.check.RuleProperty;
26+
import org.sonar.rust.RustGrammar;
27+
28+
import java.util.Collections;
29+
import java.util.Set;
30+
31+
@Rule(key = "FunctionParametersCount")
32+
public class FunctionParametersCountCheck extends RustCheck {
33+
34+
private static final int DEFAULT_MAXIMUM_PARAMETER_COUNT = 8;
35+
36+
@RuleProperty(
37+
key = "maximumParameterCount",
38+
description = " Maximum authorized number of parameters",
39+
defaultValue = "" + DEFAULT_MAXIMUM_PARAMETER_COUNT)
40+
public int maximumParameterCount = DEFAULT_MAXIMUM_PARAMETER_COUNT;
41+
42+
@Override
43+
public Set<AstNodeType> subscribedKinds() {
44+
return Collections.singleton(RustGrammar.FUNCTION);
45+
}
46+
47+
@Override
48+
public void visitNode(AstNode node) {
49+
int numberOfParameters = getNumberOfParameters(node);
50+
51+
if (numberOfParameters > maximumParameterCount) {
52+
addIssue(
53+
"Reduce the number of parameters that this function takes from " + numberOfParameters + " to at most " + maximumParameterCount + ".",
54+
node);
55+
}
56+
}
57+
58+
private static int getNumberOfParameters(AstNode node) {
59+
AstNode parameterNameList = node.getFirstChild(RustGrammar.FUNCTION_PARAMETERS);
60+
61+
return parameterNameList == null ? 0 : parameterNameList.getChildren(RustGrammar.FUNCTION_PARAM).size();
62+
}
63+
64+
}
Lines changed: 50 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,50 @@
1+
/**
2+
* Sonar Rust Plugin (Community)
3+
* Copyright (C) 2021 Eric Le Goff
4+
* http://github.com/elegoff/sonar-rust
5+
*
6+
* This program is free software; you can redistribute it and/or
7+
* modify it under the terms of the GNU Lesser General Public
8+
* License as published by the Free Software Foundation; either
9+
* version 3 of the License, or (at your option) any later version.
10+
*
11+
* This program is distributed in the hope that it will be useful,
12+
* but WITHOUT ANY WARRANTY; without even the implied warranty of
13+
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14+
* Lesser General Public License for more details.
15+
*
16+
* You should have received a copy of the GNU Lesser General Public License
17+
* along with this program; if not, write to the Free Software Foundation,
18+
* Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
19+
*/
20+
package org.elegoff.rust.checks;
21+
22+
import com.sonar.sslr.api.AstNode;
23+
import org.sonar.check.Rule;
24+
import org.sonar.check.RuleProperty;
25+
26+
@Rule(key = "LineLength")
27+
public class LineLengthCheck extends RustCheck {
28+
29+
private static final int DEFAULT_MAXIMUM_LINE_LENHGTH = 120;
30+
31+
@RuleProperty(
32+
key = "maximumLineLength",
33+
description = "The maximum authorized line length.",
34+
defaultValue = "" + DEFAULT_MAXIMUM_LINE_LENHGTH)
35+
public int maximumLineLength = DEFAULT_MAXIMUM_LINE_LENHGTH;
36+
37+
@Override
38+
public void visitFile(AstNode astNode) {
39+
String[] lines = getContext().file().content().split("\\r?\\n");
40+
for (int i = 0; i < lines.length; i++) {
41+
int length = lines[i].length();
42+
if (length > maximumLineLength) {
43+
addLineIssue(
44+
"Split this " + length + " characters long line (which is greater than " + maximumLineLength + " authorized).",
45+
i + 1);
46+
}
47+
}
48+
}
49+
50+
}

rust-checks/src/main/java/org/elegoff/rust/checks/RustCheck.java

Lines changed: 3 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -21,11 +21,11 @@
2121

2222
import com.sonar.sslr.api.AstNode;
2323
import com.sonar.sslr.api.Token;
24-
import org.sonar.api.internal.google.common.collect.ImmutableList;
2524
import org.sonar.rust.RustVisitor;
2625
import org.sonar.rust.RustVisitorContext;
2726

2827
import java.util.ArrayList;
28+
import java.util.Collections;
2929
import java.util.List;
3030

3131
public class RustCheck extends RustVisitor {
@@ -34,17 +34,15 @@ public class RustCheck extends RustVisitor {
3434
public List<Issue> scanFileForIssues(RustVisitorContext context) {
3535
issues.clear();
3636
scanFile(context);
37-
return ImmutableList.copyOf(issues);
37+
return Collections.unmodifiableList(new ArrayList<>(issues));
3838
}
3939

4040
public void addIssue(String message, AstNode node) {
4141
addIssue(message, node.getToken());
4242
}
4343

4444
public void addIssue(String message, Token token) {
45-
if (token.getURI().equals(getContext().file().uri())) {
46-
addLineIssue(message, token.getLine());
47-
}
45+
addLineIssue(message, token.getLine());
4846
}
4947

5048
public void addLineIssue(String message, int line) {
Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,11 @@
1+
<p>Empty enums should be avoided. Use a never_type instead.</p>
2+
<h2>Noncompliant Code Example</h2>
3+
<pre>
4+
enum Foo {}
5+
</pre>
6+
<h2>Compliant Code Example</h2>
7+
<pre>
8+
#![feature(never_type)]
9+
10+
struct Foo(!);
11+
</pre>
Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,16 @@
1+
2+
{
3+
"title": "Enum should not be left empty",
4+
"type": "CODE_SMELL",
5+
"status": "ready",
6+
"remediation": {
7+
"func": "Constant\/Issue",
8+
"constantCost": "5min"
9+
},
10+
"tags": [
11+
"suspicious"
12+
],
13+
"defaultSeverity": "Major",
14+
"sqKey": "EmptyEnum",
15+
"scope": "All"
16+
}
Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,16 @@
1+
<p>Functions with excessive parameters are difficult to use, as one needs to figure out what each parameter is.</p>
2+
<p>In many cases, the procedure can either be split into several smaller ones, or a better data structure can be found.</p>
3+
<p>This rule verifies that each function has at most the given number of parameters.</p>
4+
<h2>Noncompliant Code Example</h2>
5+
<pre>
6+
fn nine_params_sum(p1 : i32, p2 : i32,p3 : i32,p4 : i32,p5 : i32,p6 : i32,p7 : i32,p8 : i32,p9 : i32) -> i32 {/* Non-Compliant - too many parameters */
7+
return p1 + p2 + p3 + p4 +p5 + p6 + p7 + p8 +p9;
8+
}
9+
</pre>
10+
<h2>Compliant Solution</h2>
11+
<pre>
12+
fn single_params_sum(a : &[i32] )-> i32{
13+
a.iter().sum()
14+
}
15+
</pre>
16+
Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,14 @@
1+
{
2+
"title": "Functions should not have too many parameters",
3+
"type": "CODE_SMELL",
4+
"status": "ready",
5+
"remediation": {
6+
"func": "Constant\/Issue",
7+
"constantCost": "20min"
8+
},
9+
"tags": [
10+
"brain-overload"
11+
],
12+
"defaultSeverity": "Major",
13+
"scope": "All"
14+
}

0 commit comments

Comments
 (0)