diff --git a/src/main/java/fr/greencodeinitiative/java/JavaCheckRegistrar.java b/src/main/java/fr/greencodeinitiative/java/JavaCheckRegistrar.java
index f4ef343..54a69b3 100644
--- a/src/main/java/fr/greencodeinitiative/java/JavaCheckRegistrar.java
+++ b/src/main/java/fr/greencodeinitiative/java/JavaCheckRegistrar.java
@@ -20,21 +20,7 @@
import java.util.Collections;
import java.util.List;
-import fr.greencodeinitiative.java.checks.ArrayCopyCheck;
-import fr.greencodeinitiative.java.checks.AvoidFullSQLRequest;
-import fr.greencodeinitiative.java.checks.AvoidGettingSizeCollectionInLoop;
-import fr.greencodeinitiative.java.checks.AvoidMultipleIfElseStatement;
-import fr.greencodeinitiative.java.checks.AvoidRegexPatternNotStatic;
-import fr.greencodeinitiative.java.checks.AvoidSQLRequestInLoop;
-import fr.greencodeinitiative.java.checks.AvoidSetConstantInBatchUpdate;
-import fr.greencodeinitiative.java.checks.AvoidSpringRepositoryCallInLoopOrStreamCheck;
-import fr.greencodeinitiative.java.checks.AvoidStatementForDMLQueries;
-import fr.greencodeinitiative.java.checks.AvoidUsageOfStaticCollections;
-import fr.greencodeinitiative.java.checks.FreeResourcesOfAutoCloseableInterface;
-import fr.greencodeinitiative.java.checks.IncrementCheck;
-import fr.greencodeinitiative.java.checks.InitializeBufferWithAppropriateSize;
-import fr.greencodeinitiative.java.checks.NoFunctionCallWhenDeclaringForLoop;
-import fr.greencodeinitiative.java.checks.OptimizeReadFileExceptions;
+import fr.greencodeinitiative.java.checks.*;
import org.sonar.plugins.java.api.CheckRegistrar;
import org.sonar.plugins.java.api.JavaCheck;
import org.sonarsource.api.sonarlint.SonarLintSide;
@@ -62,7 +48,8 @@ public class JavaCheckRegistrar implements CheckRegistrar {
InitializeBufferWithAppropriateSize.class,
AvoidSetConstantInBatchUpdate.class,
FreeResourcesOfAutoCloseableInterface.class,
- AvoidMultipleIfElseStatement.class
+ AvoidMultipleIfElseStatement.class,
+ UseFetchTypeLazyRule.class
);
/**
diff --git a/src/main/java/fr/greencodeinitiative/java/checks/UseFetchTypeLazyRule.java b/src/main/java/fr/greencodeinitiative/java/checks/UseFetchTypeLazyRule.java
new file mode 100644
index 0000000..122cb3d
--- /dev/null
+++ b/src/main/java/fr/greencodeinitiative/java/checks/UseFetchTypeLazyRule.java
@@ -0,0 +1,74 @@
+/*
+ * ecoCode - Java language - Provides rules to reduce the environmental footprint of your Java programs
+ * Copyright © 2023 Green Code Initiative (https://www.ecocode.io)
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program. If not, see .
+ */
+package fr.greencodeinitiative.java.checks;
+
+import org.sonar.check.Rule;
+import org.sonar.plugins.java.api.JavaFileScanner;
+import org.sonar.plugins.java.api.JavaFileScannerContext;
+import org.sonar.plugins.java.api.tree.*;
+
+@Rule(key = "EC205")
+public class UseFetchTypeLazyRule extends BaseTreeVisitor implements JavaFileScanner {
+ protected static final String ONE_TO_MANY = "OneToMany";
+ protected static final String MESSAGE_RULE = "Avoid Using FetchType.EAGER instead of FetchType.LAZY on collections in JPA Entity";
+ protected static final String JPA_ANNOTATION_WITHOUT_FETCH_TYPE_DETECTED = "JPA annotation without FetchType detected";
+ protected static final String LAZY = "LAZY";
+ protected static final String MANY_TO_MANY = "ManyToMany";
+ private JavaFileScannerContext context;
+
+ @Override
+ public void scanFile(JavaFileScannerContext javaFileScannerContext) {
+ this.context = javaFileScannerContext;
+ // The call to the scan method on the root of the tree triggers the visit of the AST by this visitor
+ scan(context.getTree());
+ }
+
+ @Override
+ public void visitAnnotation(AnnotationTree annotationTree) {
+ String annotationName = ((IdentifierTree) annotationTree.annotationType()).name();
+ if (ONE_TO_MANY.equals(annotationName)
+ || MANY_TO_MANY.equals(annotationName)) {
+ boolean fetchExist = false;
+ ExpressionTree fetchTypeArg = null;
+
+ for (ExpressionTree argument : annotationTree.arguments()) {
+ if (argument.is(Tree.Kind.ASSIGNMENT)) {
+ AssignmentExpressionTree assignmentInvocation = (AssignmentExpressionTree) argument;
+ if (assignmentInvocation.variable().toString().equals("fetch")) {
+ fetchExist = true;
+ fetchTypeArg = assignmentInvocation.expression();
+ }
+ }
+ }
+
+ this.reportFetchTypeIssue(fetchExist,fetchTypeArg,annotationTree);
+ }
+ super.visitAnnotation(annotationTree);
+ }
+
+ private void reportFetchTypeIssue(boolean fetchExist, ExpressionTree fetchTypeArg, AnnotationTree annotationTree){
+ if (!fetchExist) {
+ context.reportIssue(this, annotationTree, JPA_ANNOTATION_WITHOUT_FETCH_TYPE_DETECTED);
+ } else if (fetchTypeArg != null) {
+ String fetchType = ((MemberSelectExpressionTree) fetchTypeArg).identifier().name();
+ if (!LAZY.equals(fetchType.strip())) {
+ context.reportIssue(this, annotationTree, MESSAGE_RULE);
+ }
+ }
+ }
+}
diff --git a/src/test/files/UseFetchTypeLazyRule.java b/src/test/files/UseFetchTypeLazyRule.java
new file mode 100644
index 0000000..65db55c
--- /dev/null
+++ b/src/test/files/UseFetchTypeLazyRule.java
@@ -0,0 +1,50 @@
+/*
+ * ecoCode - Java language - Provides rules to reduce the environmental footprint of your Java programs
+ * Copyright © 2023 Green Code Initiative (https://www.ecocode.io)
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program. If not, see .
+ */
+package fr.greencodeinitiative.java.checks;
+
+import javax.persistence.OneToMany;
+import javax.persistence.ManyToOne;
+import java.util.Collections;
+
+public class UseFetchTypeLazyRuleTest {
+
+ @OneToMany(mappedBy = "firstEntity") // Noncompliant
+ private Collection firstEntities;
+
+ @ManyToMany(mappedBy = "firstEntity1") // Noncompliant
+ private Collection firstEntities1;
+
+ @OneToMany // Noncompliant
+ private Collection secondEntities1;
+
+ @ManyToMany // Noncompliant
+ private Collection secondEntities2;
+
+ @OneToMany(mappedBy = "thirdEntity1", fetch= FetchType.EAGER) // Noncompliant
+ private Collection thirdEntities1;
+
+ @ManyToMany(mappedBy = "thirdEntity1", fetch= FetchType.EAGER) // Noncompliant
+ private Collection thirdEntities2;
+
+ @OneToMany(fetch = FetchType.LAZY) // Compliant
+ private Collection fourthEntities1;
+
+ @ManyToMany(fetch = FetchType.LAZY) // Compliant
+ private Collection fourthEntities2;
+
+}
diff --git a/src/test/java/fr/greencodeinitiative/java/JavaCheckRegistrarTest.java b/src/test/java/fr/greencodeinitiative/java/JavaCheckRegistrarTest.java
index 02270ca..552d683 100644
--- a/src/test/java/fr/greencodeinitiative/java/JavaCheckRegistrarTest.java
+++ b/src/test/java/fr/greencodeinitiative/java/JavaCheckRegistrarTest.java
@@ -31,9 +31,8 @@ void checkNumberRules() {
final JavaCheckRegistrar registrar = new JavaCheckRegistrar();
registrar.register(context);
- assertThat(context.checkClasses()).hasSize(15);
+ assertThat(context.checkClasses()).hasSize(16);
assertThat(context.testCheckClasses()).isEmpty();
}
-
}
diff --git a/src/test/java/fr/greencodeinitiative/java/checks/UseFetchTypeLazyRuleTest.java b/src/test/java/fr/greencodeinitiative/java/checks/UseFetchTypeLazyRuleTest.java
new file mode 100644
index 0000000..97e16f0
--- /dev/null
+++ b/src/test/java/fr/greencodeinitiative/java/checks/UseFetchTypeLazyRuleTest.java
@@ -0,0 +1,32 @@
+/*
+ * ecoCode - Java language - Provides rules to reduce the environmental footprint of your Java programs
+ * Copyright © 2023 Green Code Initiative (https://www.ecocode.io)
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program. If not, see .
+ */
+package fr.greencodeinitiative.java.checks;
+
+import org.junit.jupiter.api.Test;
+import org.sonar.java.checks.verifier.CheckVerifier;
+
+class UseFetchTypeLazyRuleTest {
+
+ @Test
+ void test() {
+ CheckVerifier.newVerifier()
+ .onFile("src/test/files/UseFetchTypeLazyRule.java")
+ .withCheck(new UseFetchTypeLazyRule())
+ .verifyIssues();
+ }
+}