Skip to content

Commit 66c0ee6

Browse files
committed
[PR 128-ecocode] replace EC34 by EC35 : update Python implem
1 parent 14e5e7d commit 66c0ee6

File tree

5 files changed

+90
-49
lines changed

5 files changed

+90
-49
lines changed

src/main/java/fr/greencodeinitiative/python/PythonRuleRepository.java

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -59,7 +59,7 @@ public List<Class> checkClasses() {
5959
AvoidGettersAndSetters.class,
6060
AvoidGlobalVariableInFunctionCheck.class,
6161
AvoidSQLRequestInLoop.class,
62-
AvoidTryCatchFinallyCheck.class,
62+
AvoidTryCatchFileOpenCheck.class,
6363
AvoidUnoptimizedVectorImagesCheck.class,
6464
NoFunctionCallWhenDeclaringForLoop.class,
6565
AvoidFullSQLRequest.class,
Lines changed: 85 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,85 @@
1+
/*
2+
* ecoCode - Python language - Provides rules to reduce the environmental footprint of your Python programs
3+
* Copyright © 2023 Green Code Initiative (https://www.ecocode.io)
4+
*
5+
* This program is free software: you can redistribute it and/or modify
6+
* it under the terms of the GNU General Public License as published by
7+
* the Free Software Foundation, either version 3 of the License, or
8+
* (at your option) any later version.
9+
*
10+
* This program is distributed in the hope that it will be useful,
11+
* but WITHOUT ANY WARRANTY; without even the implied warranty of
12+
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13+
* GNU General Public License for more details.
14+
*
15+
* You should have received a copy of the GNU General Public License
16+
* along with this program. If not, see <http://www.gnu.org/licenses/>.
17+
*/
18+
package fr.greencodeinitiative.python.checks;
19+
20+
import org.sonar.check.Rule;
21+
import org.sonar.plugins.python.api.PythonSubscriptionCheck;
22+
import org.sonar.plugins.python.api.SubscriptionContext;
23+
import org.sonar.plugins.python.api.symbols.Symbol;
24+
import org.sonar.plugins.python.api.tree.*;
25+
import org.sonarsource.analyzer.commons.annotations.DeprecatedRuleKey;
26+
27+
import java.util.List;
28+
import java.util.Objects;
29+
30+
import static org.sonar.plugins.python.api.tree.Tree.Kind.CALL_EXPR;
31+
import static org.sonar.plugins.python.api.tree.Tree.Kind.LIST_COMPREHENSION;
32+
33+
@Rule(key = "EC35")
34+
@DeprecatedRuleKey(repositoryKey = "gci-python", ruleKey = "S34")
35+
@DeprecatedRuleKey(repositoryKey = "gci-python", ruleKey = "EC34")
36+
public class AvoidTryCatchFileOpenCheck extends PythonSubscriptionCheck {
37+
38+
public static final String DESCRIPTION = "Avoid the use of try-catch with a file open in try block";
39+
40+
@Override
41+
public void initialize(Context context) {
42+
context.registerSyntaxNodeConsumer(Tree.Kind.TRY_STMT, this::visitNode);
43+
}
44+
45+
private void visitNode(SubscriptionContext context) {
46+
TryStatement tryStatement = (TryStatement) context.syntaxNode();
47+
48+
for (Statement stmt : tryStatement.body().statements()){
49+
if (stmt.is(CALL_EXPR)) {
50+
CallExpression callExpression = (CallExpression) stmt;
51+
visitCallExpression(context, callExpression);
52+
} else {
53+
checkCallExpressionInChildren(context, stmt);
54+
}
55+
}
56+
57+
}
58+
59+
private void checkCallExpressionInChildren(SubscriptionContext context, Tree stmt) {
60+
stmt.children().forEach(tree -> {
61+
if (tree.is(CALL_EXPR)) {
62+
CallExpression callExpression = (CallExpression) tree;
63+
visitCallExpression(context, callExpression);
64+
} else {
65+
checkCallExpressionInChildren(context, tree);
66+
}
67+
});
68+
}
69+
70+
private void visitCallExpression(SubscriptionContext context, CallExpression callExpression){
71+
switch (getFunctionNameFromCallExpression(callExpression)) {
72+
case "open":
73+
context.addIssue(callExpression.firstToken(), DESCRIPTION);
74+
break;
75+
default:
76+
break;
77+
}
78+
}
79+
80+
private String getFunctionNameFromCallExpression(CallExpression callExpression) {
81+
Symbol symbol = callExpression.calleeSymbol();
82+
return symbol != null && symbol.name() != null ? symbol.name() : "";
83+
}
84+
85+
}

src/main/java/fr/greencodeinitiative/python/checks/AvoidTryCatchFinallyCheck.java

Lines changed: 0 additions & 44 deletions
This file was deleted.

src/test/java/fr/greencodeinitiative/python/checks/AvoidTryCatchFinallyCheckTest.java

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,6 @@
2424
public class AvoidTryCatchFinallyCheckTest {
2525
@Test
2626
public void test() {
27-
PythonCheckVerifier.verify("src/test/resources/checks/avoidTryCatchFinallyCheck.py", new AvoidTryCatchFinallyCheck());
27+
PythonCheckVerifier.verify("src/test/resources/checks/avoidTryCatchWithFileOpenCheck.py", new AvoidTryCatchFileOpenCheck());
2828
}
2929
}

src/test/resources/checks/avoidTryCatchFinallyCheck.py renamed to src/test/resources/checks/avoidTryCatchWithFileOpenCheck.py

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -6,16 +6,16 @@
66
def my_function():
77
x=0
88

9-
try: # Noncompliant {{Avoid the use of try-catch}}
9+
try:
1010
print(x)
1111
except:
1212
print("Something went wrong")
1313
finally:
1414
print("The 'try except' is finished")
1515

1616
def foo():
17-
try: # Noncompliant {{Avoid the use of try-catch}}
18-
f = open(path)
17+
try:
18+
f = open(path) # Noncompliant {{Avoid the use of try-catch with a file open in try block}}
1919
print(f.read())
2020
except:
2121
print('No such file '+path)

0 commit comments

Comments
 (0)