Repository: jhipster/jhipster-lite
Pull request #9792 (2024-05-12 20:14:01)

feat(maven): replace existing plugin rather than adding a duplicated one


Patch:
diff --git a/src/main/java/tech/jhipster/lite/module/infrastructure/secondary/javadependency/maven/MavenCommandHandler.java b/src/main/java/tech/jhipster/lite/module/infrastructure/secondary/javadependency/maven/MavenCommandHandler.java
index e5a600059..802a9c18f 100644
--- a/src/main/java/tech/jhipster/lite/module/infrastructure/secondary/javadependency/maven/MavenCommandHandler.java
+++ b/src/main/java/tech/jhipster/lite/module/infrastructure/secondary/javadependency/maven/MavenCommandHandler.java
@@ -14,18 +14,13 @@ import org.codehaus.plexus.util.xml.Xpp3Dom;
 import org.codehaus.plexus.util.xml.Xpp3DomBuilder;
 import org.codehaus.plexus.util.xml.pull.XmlPullParserException;
 import tech.jhipster.lite.module.domain.Indentation;
-import tech.jhipster.lite.module.domain.buildproperties.BuildProperty;
-import tech.jhipster.lite.module.domain.buildproperties.PropertyKey;
-import tech.jhipster.lite.module.domain.buildproperties.PropertyValue;
+import tech.jhipster.lite.module.domain.buildproperties.*;
 import tech.jhipster.lite.module.domain.javabuild.MavenBuildExtension;
 import tech.jhipster.lite.module.domain.javabuild.VersionSlug;
 import tech.jhipster.lite.module.domain.javabuild.command.*;
 import tech.jhipster.lite.module.domain.javabuildprofile.BuildProfileActivation;
 import tech.jhipster.lite.module.domain.javabuildprofile.BuildProfileId;
-import tech.jhipster.lite.module.domain.javadependency.DependencyId;
-import tech.jhipster.lite.module.domain.javadependency.JavaDependency;
-import tech.jhipster.lite.module.domain.javadependency.JavaDependencyClassifier;
-import tech.jhipster.lite.module.domain.javadependency.JavaDependencyScope;
+import tech.jhipster.lite.module.domain.javadependency.*;
 import tech.jhipster.lite.module.domain.mavenplugin.*;
 import tech.jhipster.lite.module.infrastructure.secondary.javadependency.JavaDependenciesCommandHandler;
 import tech.jhipster.lite.shared.enumeration.domain.Enums;
@@ -285,7 +280,7 @@ public class MavenCommandHandler implements JavaDependenciesCommandHandler {
       .map(this::findProfile)
       .map(this::pluginManagement)
       .orElse(pluginManagement());
-    pluginManagement.addPlugin(toMavenPlugin(command));
+    replaceOrAddPlugin(pluginManagement.getPlugins(), toMavenPlugin(command));
 
     writePom();
   }
@@ -311,12 +306,23 @@ public class MavenCommandHandler implements JavaDependenciesCommandHandler {
     command.pluginVersion().ifPresent(version -> handle(new SetVersion(version)));
     command.dependenciesVersions().forEach(version -> handle(new SetVersion(version)));
 
-    BuildBase projectBuild = command.buildProfile().map(this::findProfile).map(this::profileBuild).orElse(projectBuild());
-    projectBuild.addPlugin(toMavenPlugin(command));
+    BuildBase build = command.buildProfile().map(this::findProfile).map(this::profileBuild).orElse(projectBuild());
+    replaceOrAddPlugin(build.getPlugins(), toMavenPlugin(command));
 
     writePom();
   }
 
+  private static void replaceOrAddPlugin(List<Plugin> plugins, Plugin newPlugin) {
+    for (int i = 0; i < plugins.size(); i++) {
+      Plugin existingPlugin = plugins.get(i);
+      if (existingPlugin.getGroupId().equals(newPlugin.getGroupId()) && existingPlugin.getArtifactId().equals(newPlugin.getArtifactId())) {
+        plugins.set(i, newPlugin);
+        return;
+      }
+    }
+    plugins.add(newPlugin);
+  }
+
   private BuildBase profileBuild(Profile mavenProfile) {
     if (mavenProfile.getBuild() == null) {
       mavenProfile.setBuild(new Build());


Test patch:
diff --git a/src/test/java/tech/jhipster/lite/module/infrastructure/secondary/javadependency/maven/MavenCommandHandlerTest.java b/src/test/java/tech/jhipster/lite/module/infrastructure/secondary/javadependency/maven/MavenCommandHandlerTest.java
index 3431dd177..4371ca615 100644
--- a/src/test/java/tech/jhipster/lite/module/infrastructure/secondary/javadependency/maven/MavenCommandHandlerTest.java
+++ b/src/test/java/tech/jhipster/lite/module/infrastructure/secondary/javadependency/maven/MavenCommandHandlerTest.java
@@ -828,6 +828,88 @@ class MavenCommandHandlerTest {
         assertThat(contentNormalizingNewLines(pom)).contains(pluginManagement());
       }
 
+      @Test
+      void shouldReplaceExistingMavenPlugin() {
+        Path pom = projectWithPom("src/test/resources/projects/empty-maven/pom.xml");
+        MavenCommandHandler mavenCommandHandler = new MavenCommandHandler(Indentation.DEFAULT, pom);
+        mavenCommandHandler.handle(AddMavenPluginManagement.builder().plugin(mavenEnforcerPlugin()).build());
+
+        mavenCommandHandler.handle(
+          AddMavenPluginManagement.builder()
+            .plugin(
+              mavenPlugin()
+                .groupId("org.apache.maven.plugins")
+                .artifactId("maven-enforcer-plugin")
+                .versionSlug("maven-enforcer-plugin")
+                .build()
+            )
+            .build()
+        );
+
+        assertThat(contentNormalizingNewLines(pom))
+          .doesNotContain(
+            // language=xml
+            """
+                    <plugin>
+                      <artifactId>maven-enforcer-plugin</artifactId>
+                    </plugin>\
+            """
+          )
+          .containsOnlyOnce(
+            // language=xml
+            """
+                    <plugin>
+                      <artifactId>maven-enforcer-plugin</artifactId>
+                      <version>${maven-enforcer-plugin.version}</version>
+                    </plugin>\
+            """
+          );
+      }
+
+      @Test
+      void shouldReplaceExistingThirdPartyPlugin() {
+        Path pom = projectWithPom("src/test/resources/projects/empty-maven/pom.xml");
+        MavenCommandHandler mavenCommandHandler = new MavenCommandHandler(Indentation.DEFAULT, pom);
+        mavenCommandHandler.handle(AddMavenPluginManagement.builder().plugin(asciidoctorPlugin()).build());
+        mavenCommandHandler.handle(AddMavenPluginManagement.builder().plugin(mavenEnforcerPlugin()).build());
+
+        mavenCommandHandler.handle(
+          AddMavenPluginManagement.builder()
+            .plugin(mavenPlugin().groupId("org.asciidoctor").artifactId("asciidoctor-maven-plugin").build())
+            .build()
+        );
+
+        assertThat(contentNormalizingNewLines(pom))
+          .doesNotContain(
+            // language=xml
+            """
+                    <plugin>
+                      <groupId>org.asciidoctor</groupId>
+                      <artifactId>asciidoctor-maven-plugin</artifactId>
+                      <dependencies>
+                        <dependency>
+                          <groupId>org.asciidoctor</groupId>
+                          <artifactId>asciidoctorj-screenshot</artifactId>
+                        </dependency>
+                        <dependency>
+                          <groupId>org.asciidoctor</groupId>
+                          <artifactId>asciidoctorj-diagram</artifactId>
+                        </dependency>
+                      </dependencies>
+                    </plugin>\
+            """
+          )
+          .containsOnlyOnce(
+            // language=xml
+            """
+                    <plugin>
+                      <groupId>org.asciidoctor</groupId>
+                      <artifactId>asciidoctor-maven-plugin</artifactId>
+                    </plugin>\
+            """
+          );
+      }
+
       private void addMavenEnforcerPlugin(Path pom) {
         AddMavenPluginManagement command = AddMavenPluginManagement.builder().plugin(mavenEnforcerPluginManagement()).build();
         new MavenCommandHandler(Indentation.DEFAULT, pom).handle(command);
@@ -1086,6 +1168,88 @@ class MavenCommandHandlerTest {
           );
       }
 
+      @Test
+      void shouldReplaceExistingMavenPlugin() {
+        Path pom = projectWithPom("src/test/resources/projects/empty-maven/pom.xml");
+        MavenCommandHandler mavenCommandHandler = new MavenCommandHandler(Indentation.DEFAULT, pom);
+        mavenCommandHandler.handle(AddDirectMavenPlugin.builder().plugin(mavenEnforcerPlugin()).build());
+        mavenCommandHandler.handle(AddDirectMavenPlugin.builder().plugin(asciidoctorPlugin()).build());
+
+        mavenCommandHandler.handle(
+          AddDirectMavenPlugin.builder()
+            .plugin(
+              mavenPlugin()
+                .groupId("org.apache.maven.plugins")
+                .artifactId("maven-enforcer-plugin")
+                .versionSlug("maven-enforcer-plugin")
+                .build()
+            )
+            .build()
+        );
+
+        assertThat(contentNormalizingNewLines(pom))
+          .doesNotContain(
+            // language=xml
+            """
+                  <plugin>
+                    <artifactId>maven-enforcer-plugin</artifactId>
+                  </plugin>\
+            """
+          )
+          .containsOnlyOnce(
+            // language=xml
+            """
+                  <plugin>
+                    <artifactId>maven-enforcer-plugin</artifactId>
+                    <version>${maven-enforcer-plugin.version}</version>
+                  </plugin>\
+            """
+          );
+      }
+
+      @Test
+      void shouldReplaceExistingThirdPartyPlugin() {
+        Path pom = projectWithPom("src/test/resources/projects/empty-maven/pom.xml");
+        MavenCommandHandler mavenCommandHandler = new MavenCommandHandler(Indentation.DEFAULT, pom);
+        mavenCommandHandler.handle(AddDirectMavenPlugin.builder().plugin(asciidoctorPlugin()).build());
+
+        mavenCommandHandler.handle(
+          AddDirectMavenPlugin.builder()
+            .plugin(mavenPlugin().groupId("org.asciidoctor").artifactId("asciidoctor-maven-plugin").build())
+            .build()
+        );
+
+        assertThat(contentNormalizingNewLines(pom))
+          .doesNotContain(
+            // language=xml
+            """
+                  <plugin>
+                    <groupId>org.asciidoctor</groupId>
+                    <artifactId>asciidoctor-maven-plugin</artifactId>
+                    <dependencies>
+                      <dependency>
+                        <groupId>org.asciidoctor</groupId>
+                        <artifactId>asciidoctorj-screenshot</artifactId>
+                      </dependency>
+                      <dependency>
+                        <groupId>org.asciidoctor</groupId>
+                        <artifactId>asciidoctorj-diagram</artifactId>
+                      </dependency>
+                    </dependencies>
+                  </plugin>\
+            """
+          )
+          .containsOnlyOnce(
+            // language=xml
+            """
+                  <plugin>
+                    <groupId>org.asciidoctor</groupId>
+                    <artifactId>asciidoctor-maven-plugin</artifactId>
+                  </plugin>\
+            """
+          );
+      }
+
       private void addMavenEnforcerPlugin(Path pom) {
         new MavenCommandHandler(Indentation.DEFAULT, pom).handle(
           AddDirectMavenPlugin.builder().plugin(mavenEnforcerPluginManagement()).build()