Come creare un plugin Maven

1. Introduzione

Maven offre una grande varietà di plugin per aiutarci con la costruzione del nostro progetto. Tuttavia, potremmo trovare casi in cui questi plugin non sono sufficienti e dobbiamo svilupparne uno nostro.

Fortunatamente, Maven fornisce alcuni strumenti utili per aiutarci in questo processo.

In questo tutorial, saremo abbastanza pratici e mostreremo passo dopo passo come creare un plugin Maven da zero.

Mostreremo anche come usarlo nei nostri progetti e come creare documentazione per esso.

2. Creazione di un plugin

Durante questo tutorial, svilupperemo un plugin chiamato counter-maven-plugin che conterà il numero di dipendenze contenute in un progetto. È molto importante seguire la convenzione di denominazione dei plug-in che Maven consiglia quando scegliamo il nome per il nostro plug-in.

Ora che sappiamo cosa svilupperemo, la prossima cosa che dobbiamo fare è creare un progetto Maven. Nel pom.xml definiremo groupId , artifactId e versione del nostro plugin:

 4.0.0 com.baeldung counter-maven-plugin maven-plugin 0.0.1-SNAPSHOT counter-maven-plugin Maven Mojo //maven.apache.org  1.8 1.8  

Si noti che abbiamo impostato la confezione su maven-plugin .

In questo caso, abbiamo creato il progetto manualmente, ma potremmo anche farlo usando il maven-archetype-mojo :

mvn archetype:generate -DgroupId=com.baeldung -DartifactId=counter-maven-plugin -Dversion=0.0.1-SNAPSHOT -DarchetypeGroupId=org.apache.maven.archetypes -DarchetypeArtifactId=maven-archetype-mojo

Quando si esegue questa operazione, è necessario aggiornare le versioni predefinite delle dipendenze per utilizzare quelle più recenti.

3. Creazione di un Mojo

Ora è il momento di creare il nostro primo mojo. Mojo è una classe Java che rappresenta un obiettivo che il nostro plugin eseguirà . Un plugin contiene uno o più mojo.

Il nostro mojo sarà responsabile del conteggio del numero di dipendenze di un progetto.

3.1. Aggiunta di dipendenze

Prima di creare il mojo, dobbiamo aggiungere alcune dipendenze al nostro pom.xml :

  org.apache.maven maven-plugin-api 3.6.3   org.apache.maven.plugin-tools maven-plugin-annotations 3.6.0 provided   org.apache.maven maven-project 2.2.1  

La dipendenza maven-plugin-api è richiesta e contiene le classi e le interfacce necessarie per creare il nostro mojo . La dipendenza maven-plugin-annotations è utile per usare le annotazioni nelle nostre classi. La dipendenza maven-project ci consente di accedere alle informazioni sul progetto in cui includiamo il plugin.

3.2. Creazione della classe Mojo

Ora siamo pronti per creare il nostro mojo!

Un mojo deve implementare l' interfaccia Mojo . Nel nostro caso, estenderemo da AbstractMojo quindi dovremo solo implementare il metodo di esecuzione :

@Mojo(name = "dependency-counter", defaultPhase = LifecyclePhase.COMPILE) public class DependencyCounterMojo extends AbstractMojo { // ... }

Come possiamo vedere, il contatore delle dipendenze è il nome dell'obiettivo. D'altra parte, l'abbiamo allegato alla fase di compilazione per impostazione predefinita, quindi non dovremo necessariamente specificare una fase quando si utilizza questo obiettivo.

Per avere accesso alle informazioni sul progetto, dobbiamo aggiungere un MavenProject come parametro:

@Parameter(defaultValue = "${project}", required = true, readonly = true) MavenProject project;

Questo oggetto verrà iniettato da Maven quando viene creato il contesto.

A questo punto, siamo in grado di implementare il metodo di esecuzione e contare il numero di dipendenze del progetto:

public void execute() throws MojoExecutionException, MojoFailureException { List dependencies = project.getDependencies(); long numDependencies = dependencies.stream().count(); getLog().info("Number of dependencies: " + numDependencies); }

Il metodo getLog () fornisce l'accesso al registro di Maven. L'AbstractMojo gestisce già il suo ciclo di vita.

3.3. Aggiunta di parametri

Il parametro che abbiamo aggiunto prima è di sola lettura e non può essere configurato dall'utente. Inoltre, è stato iniettato da Maven, quindi potremmo dire che è un po 'speciale.

In questa sezione, aggiungeremo un parametro in cui gli utenti possono specificare l'ambito delle dipendenze che vogliamo contare.

Quindi, creiamo un parametro di ambito nel nostro mojo:

@Parameter(property = "scope") String scope;

Abbiamo solo impostato l' attributo di proprietà . Ci consente di impostare questa proprietà tramite la riga di comando o una proprietà pom . Per il resto degli attributi, stiamo bene con i valori predefiniti.

Ora modificheremo il nostro metodo di esecuzione per utilizzare questo parametro e filtrare le dipendenze durante il conteggio:

public void execute() throws MojoExecutionException, MojoFailureException  List dependencies = project.getDependencies(); long numDependencies = dependencies.stream() .filter(d -> (scope == null 

Tipi di parametri più avanzati sono spiegati nella documentazione ufficiale.

4. Testare il plugin

Abbiamo finito con lo sviluppo del plugin. Proviamolo per vedere se funziona!

Prima di tutto, dobbiamo installare il plugin nel nostro repository locale:

mvn clean install

Nelle prossime sezioni, vedremo prima come eseguire il nostro plugin dalla riga di comando. Quindi, vedremo anche come usarlo in un progetto Maven.

4.1. Esecuzione del nostro plugin

Possiamo eseguire l'obiettivo di un plugin nella riga di comando specificando il suo nome completo:

mvn groupId:artifactId:version:goal

Nel nostro caso, assomiglia a questo:

mvn com.baeldung:counter-maven-plugin:0.0.1-SNAPSHOT:dependency-counter

Tuttavia, se abbiamo seguito la convenzione di denominazione del plug-in che abbiamo menzionato all'inizio di questo tutorial, Maven risolverà il prefisso del nostro plug-in e possiamo abbreviare il comando:

mvn counter:dependency-counter

Notice that this command is using the latest version of the plugin. Also, keep in mind that we have to add our groupId to the pluginGroups of our settings.xml so Maven also searches in this group:

 com.baeldung 

If we check the output of the command, we can see that the plugin counted the number of dependencies in the pom.xml of our plugin:

[INFO] Scanning for projects... [INFO] [INFO] ----------------------------------- [INFO] Building counter-maven-plugin Maven Mojo 0.0.1-SNAPSHOT [INFO] ----------------------------[ maven-plugin ]---------------------------- [INFO] [INFO] --- counter-maven-plugin:0.0.1-SNAPSHOT:dependency-counter (default-cli) @ counter-maven-plugin --- [INFO] Number of dependencies: 3 [INFO] ------------------------------------------------------------------------ [INFO] BUILD SUCCESS [INFO] ------------------------------------------------------------------------ [INFO] Total time: 0.529 s [INFO] Finished at: 2019-11-30T20:43:41+01:00 [INFO] ------------------------------------------------------------------------

We can also set the scope parameter via command line properties:

mvn counter:dependency-counter -Dscope=test

Notice that the scope name is the one that we defined in the property attribute of our parameter in the mojo.

4.2. Using Our Plugin in a Project

Let's test now our plugin by using it in a project!

We're going to create a very simple Maven project with some dependencies that our plugin will count:

 4.0.0 com.baeldung example pom 0.0.1-SNAPSHOT   org.apache.commons commons-lang3 3.9   junit junit 4.12 test   

The last thing is to add our plugin to the build. We have to explicitly set that we want to run the dependency-counter goal:

   com.baeldung counter-maven-plugin 0.0.1-SNAPSHOT    dependency-counter     test    

Notice that we've specified the scope parameter in the configuration node. Also, we haven't specified any phase because our mojo is attached to the compile phase by default.

Now, we just need to run the compile phase to execute our plugin:

mvn clean compile

And our plugin will print the number of test dependencies:

[INFO] Scanning for projects... [INFO] [INFO] ------------------------------------------------ [INFO] Building example 0.0.1-SNAPSHOT [INFO] --------------------------------[ pom ]--------------------------------- [INFO] [INFO] --- maven-clean-plugin:2.5:clean (default-clean) @ example --- [INFO] [INFO] --- counter-maven-plugin:0.0.1-SNAPSHOT:dependency-counter (default) @ example --- [INFO] Number of dependencies: 1 [INFO] ------------------------------------------------------------------------ [INFO] BUILD SUCCESS [INFO] ------------------------------------------------------------------------ [INFO] Total time: 0.627 s [INFO] Finished at: 2019-11-25T18:57:22+01:00 [INFO] ------------------------------------------------------------------------

In this tutorial, we're not covering how to write unit or integration tests for our plugin but Maven provides some mechanisms to do it.

5. Adding Documentation

When we create a Maven plugin, it's important to generate documentation to make it easy for other people to use it.

We'll briefly cover how to generate this documentation with maven-plugin-plugin.

maven-plugin-plugin is already included in the project, but we're gonna update it to use the latest version.

Also, we'll do the same for maven-site-plugin:

    org.apache.maven.plugins maven-plugin-plugin 3.6.0   org.apache.maven.plugins maven-site-plugin 3.8.2    

Then, we have to make sure that we've added javadoc to our Mojo and also add some metadata in the pom.xml of the plugin:

 Baeldung //www.baeldung.com/ 

After that, we need to add a reporting section in our pom.xml:

   org.apache.maven.plugins maven-plugin-plugin    report      

Finally, we'll generate the documentation with the maven site command:

mvn site

Inside the target folder, we can find a site directory with all the HTML files generated. The plugin-info.html is the one containing the plugin documentation:

More options to add to our documentation can be found on the Maven plugin documentation guide.

6. Conclusion

In this tutorial, we've shown how to create a Maven plugin. We first implemented a simple plugin, which helped us see a typical Maven plugin project structure. Then, we covered some of the tools that Maven provides to help us develop plugins.

We've kept it simple to make things clearer, but at the same time, we've provided some useful links with the necessary information on how to create a more powerful plugin.

Come sempre, il codice sorgente completo per gli esempi è disponibile su GitHub.