From c25c65bc2c2c67891637bf1b1db93d0a5f4dbdb6 Mon Sep 17 00:00:00 2001 From: steve-aom-elliott Date: Tue, 6 May 2025 16:23:49 -0400 Subject: [PATCH 1/3] Reordering annotations (aphabetically only for now) on method declarations. --- .../staticanalysis/ReorderAnnotations.java | 58 +++++++++++++++ .../ReorderAnnotationsTest.java | 74 +++++++++++++++++++ 2 files changed, 132 insertions(+) create mode 100644 src/main/java/org/openrewrite/staticanalysis/ReorderAnnotations.java create mode 100644 src/test/java/org/openrewrite/staticanalysis/ReorderAnnotationsTest.java diff --git a/src/main/java/org/openrewrite/staticanalysis/ReorderAnnotations.java b/src/main/java/org/openrewrite/staticanalysis/ReorderAnnotations.java new file mode 100644 index 000000000..80fddcdcf --- /dev/null +++ b/src/main/java/org/openrewrite/staticanalysis/ReorderAnnotations.java @@ -0,0 +1,58 @@ +package org.openrewrite.staticanalysis; + +import lombok.EqualsAndHashCode; +import lombok.Value; +import org.openrewrite.ExecutionContext; +import org.openrewrite.Recipe; +import org.openrewrite.java.JavaIsoVisitor; +import org.openrewrite.java.tree.J; + +import java.util.ArrayList; +import java.util.Comparator; +import java.util.List; + +@Value +@EqualsAndHashCode(callSuper = false) +public class ReorderAnnotations extends Recipe { + private static final Comparator defaultComparator = Comparator.comparing(J.Annotation::getSimpleName); + // TODO: Take in optional Comparator, defaulted to alphabetical + @Override + public String getDisplayName() { + return "Reorder annotations in a consistent order"; + } + + @Override + public String getDescription() { + return "Reorder annotations based on a provided Comparator class."; + } + + @Value + @EqualsAndHashCode(callSuper = false) + public static class ReorderAnnotationVisitor extends JavaIsoVisitor { + Comparator comparator; + + @Override + public J.MethodDeclaration visitMethodDeclaration(J.MethodDeclaration method, ExecutionContext ctx) { + J.MethodDeclaration m = super.visitMethodDeclaration(method, ctx); + List annotations = m.getLeadingAnnotations(); + if (annotations.isEmpty()) { + return m; + } + List sortedAnnotations = new ArrayList<>(annotations); + sortedAnnotations.sort(comparator); + if (sortedAnnotations.equals(annotations)) { + return m; + } + for (int i = 0; i < annotations.size(); i++) { + sortedAnnotations.set(i, sortedAnnotations.get(i).withPrefix(annotations.get(i).getPrefix())); + } + + return m.withLeadingAnnotations(sortedAnnotations); + } + } + + @Override + public JavaIsoVisitor getVisitor() { + return new ReorderAnnotationVisitor(defaultComparator); + } +} diff --git a/src/test/java/org/openrewrite/staticanalysis/ReorderAnnotationsTest.java b/src/test/java/org/openrewrite/staticanalysis/ReorderAnnotationsTest.java new file mode 100644 index 000000000..51f3ac4c9 --- /dev/null +++ b/src/test/java/org/openrewrite/staticanalysis/ReorderAnnotationsTest.java @@ -0,0 +1,74 @@ +package org.openrewrite.staticanalysis; + +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; +import org.openrewrite.DocumentExample; +import org.openrewrite.test.RewriteTest; + +import static org.openrewrite.java.Assertions.java; + +public class ReorderAnnotationsTest implements RewriteTest { + @Nested + class ParameterlessConstructor { + @Test + @DocumentExample + void doesNotReorderAnnotationsIfNotNeeded() { + rewriteRun( + spec -> spec.recipe(new ReorderAnnotations()), + //language=java + java( + """ + import org.junit.jupiter.api.Test; + import org.junitpioneer.jupiter.ExpectedToFail; + import org.junitpioneer.jupiter.Issue; + + class A { + @ExpectedToFail + @Issue("https://github.com/openrewrite/rewrite/issues/2973") + @Test + void explicitImplementationClassInApi() { + } + } + """ + ) + ); + } + + @Test + @DocumentExample + void reordersMethodAnnotations() { + rewriteRun( + spec -> spec.recipe(new ReorderAnnotations()), + //language=java + java( + """ + import org.junit.jupiter.api.Test; + import org.junitpioneer.jupiter.ExpectedToFail; + import org.junitpioneer.jupiter.Issue; + + class A { + @Issue("https://github.com/openrewrite/rewrite/issues/2973") + @Test + @ExpectedToFail + void explicitImplementationClassInApi() { + } + } + """, + """ + import org.junit.jupiter.api.Test; + import org.junitpioneer.jupiter.ExpectedToFail; + import org.junitpioneer.jupiter.Issue; + + class A { + @ExpectedToFail + @Issue("https://github.com/openrewrite/rewrite/issues/2973") + @Test + void explicitImplementationClassInApi() { + } + } + """ + ) + ); + } + } +} From 528ad1b69d400b738f01fb9d391390c3ff46028b Mon Sep 17 00:00:00 2001 From: Tim te Beek Date: Tue, 6 May 2025 22:43:28 +0200 Subject: [PATCH 2/3] Apply suggestions from code review Co-authored-by: github-actions[bot] <41898282+github-actions[bot]@users.noreply.github.com> --- .../staticanalysis/ReorderAnnotations.java | 15 +++++++++++++++ .../staticanalysis/ReorderAnnotationsTest.java | 17 ++++++++++++++++- 2 files changed, 31 insertions(+), 1 deletion(-) diff --git a/src/main/java/org/openrewrite/staticanalysis/ReorderAnnotations.java b/src/main/java/org/openrewrite/staticanalysis/ReorderAnnotations.java index 80fddcdcf..2a194cf4f 100644 --- a/src/main/java/org/openrewrite/staticanalysis/ReorderAnnotations.java +++ b/src/main/java/org/openrewrite/staticanalysis/ReorderAnnotations.java @@ -1,3 +1,18 @@ +/* + * Copyright 2025 the original author or authors. + *

+ * Licensed under the Moderne Source Available License (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + *

+ * https://docs.moderne.io/licensing/moderne-source-available-license + *

+ * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ package org.openrewrite.staticanalysis; import lombok.EqualsAndHashCode; diff --git a/src/test/java/org/openrewrite/staticanalysis/ReorderAnnotationsTest.java b/src/test/java/org/openrewrite/staticanalysis/ReorderAnnotationsTest.java index 51f3ac4c9..050cc3901 100644 --- a/src/test/java/org/openrewrite/staticanalysis/ReorderAnnotationsTest.java +++ b/src/test/java/org/openrewrite/staticanalysis/ReorderAnnotationsTest.java @@ -1,3 +1,18 @@ +/* + * Copyright 2025 the original author or authors. + *

+ * Licensed under the Moderne Source Available License (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + *

+ * https://docs.moderne.io/licensing/moderne-source-available-license + *

+ * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ package org.openrewrite.staticanalysis; import org.junit.jupiter.api.Nested; @@ -7,7 +22,7 @@ import static org.openrewrite.java.Assertions.java; -public class ReorderAnnotationsTest implements RewriteTest { +class ReorderAnnotationsTest implements RewriteTest { @Nested class ParameterlessConstructor { @Test From cecd8ef3b565ff1f0e4036e81261b540fc8779ac Mon Sep 17 00:00:00 2001 From: steve-aom-elliott Date: Wed, 7 May 2025 09:41:43 -0400 Subject: [PATCH 3/3] Suggested formatting changes --- .../ReorderAnnotationsTest.java | 63 +++++++++---------- 1 file changed, 30 insertions(+), 33 deletions(-) diff --git a/src/test/java/org/openrewrite/staticanalysis/ReorderAnnotationsTest.java b/src/test/java/org/openrewrite/staticanalysis/ReorderAnnotationsTest.java index 050cc3901..cea3d809e 100644 --- a/src/test/java/org/openrewrite/staticanalysis/ReorderAnnotationsTest.java +++ b/src/test/java/org/openrewrite/staticanalysis/ReorderAnnotationsTest.java @@ -33,17 +33,16 @@ void doesNotReorderAnnotationsIfNotNeeded() { //language=java java( """ - import org.junit.jupiter.api.Test; - import org.junitpioneer.jupiter.ExpectedToFail; - import org.junitpioneer.jupiter.Issue; - - class A { - @ExpectedToFail - @Issue("https://github.com/openrewrite/rewrite/issues/2973") - @Test - void explicitImplementationClassInApi() { - } - } + import org.junit.jupiter.api.Test; + import org.junitpioneer.jupiter.ExpectedToFail; + import org.junitpioneer.jupiter.Issue; + class A { + @ExpectedToFail + @Issue("https://github.com/openrewrite/rewrite/issues/2973") + @Test + void explicitImplementationClassInApi() { + } + } """ ) ); @@ -57,30 +56,28 @@ void reordersMethodAnnotations() { //language=java java( """ - import org.junit.jupiter.api.Test; - import org.junitpioneer.jupiter.ExpectedToFail; - import org.junitpioneer.jupiter.Issue; - - class A { - @Issue("https://github.com/openrewrite/rewrite/issues/2973") - @Test - @ExpectedToFail - void explicitImplementationClassInApi() { - } - } + import org.junit.jupiter.api.Test; + import org.junitpioneer.jupiter.ExpectedToFail; + import org.junitpioneer.jupiter.Issue; + class A { + @Issue("https://github.com/openrewrite/rewrite/issues/2973") + @Test + @ExpectedToFail + void explicitImplementationClassInApi() { + } + } """, """ - import org.junit.jupiter.api.Test; - import org.junitpioneer.jupiter.ExpectedToFail; - import org.junitpioneer.jupiter.Issue; - - class A { - @ExpectedToFail - @Issue("https://github.com/openrewrite/rewrite/issues/2973") - @Test - void explicitImplementationClassInApi() { - } - } + import org.junit.jupiter.api.Test; + import org.junitpioneer.jupiter.ExpectedToFail; + import org.junitpioneer.jupiter.Issue; + class A { + @ExpectedToFail + @Issue("https://github.com/openrewrite/rewrite/issues/2973") + @Test + void explicitImplementationClassInApi() { + } + } """ ) );