开发本身的maven插件

1,建立一个maven plugin项目 html

mvn archetype:generate \
  -DgroupId=sample.plugin \
  -DartifactId=hello-maven-plugin \
  -DarchetypeGroupId=org.apache.maven.archetypes \
  -DarchetypeArtifactId=maven-archetype-plugin

其中 archetypeGroupId 是固定的,其余的 groupId .... 你本身配置 java

2,配置你的plugin的快捷方式 apache

能够看到1中生成的maven plugin 项目 也算是个标准的maven项目,找到pom.xml中的下方所示,配置 maven

<build>
    <plugins>
      <plugin>
        <groupId>org.apache.maven.plugins</groupId>
        <artifactId>maven-plugin-plugin</artifactId>
        <version>3.2</version>
        <configuration>
          <goalPrefix>sun</goalPrefix>
          <skipErrorNoDescriptorsFound>true</skipErrorNoDescriptorsFound>
        </configuration> ide

goalPrefix这一项,这个是调用插件的快捷方式,若是不配置这个你调用某个plugin就是 ui

mvn groupId:artifactId:version:goal

而若是像我这里设置的则是(sun就是个人调用前缀了) url

mvn sun:goal


3,Mojo 类的配置。涉及2中屡次出现的goal,goal就是某个具体执行目标了,通常来讲一个插件通常能够执行多个功能。 spa

package sample.plugin;


import org.apache.maven.plugin.AbstractMojo;
import org.apache.maven.plugin.MojoExecutionException;
import org.apache.maven.plugins.annotations.Mojo;


@Mojo( name = "sayhi",requiresProject=true,requiresDependencyResolution=ResolutionScope.RUNTIME)
@Execute(phase = LifecyclePhase.COMPILE)
public class GreetingMojo extends AbstractMojo{   
    @Parameter(defaultValue = "8080",property ="port",required = false)
    private int port;  
 
    public void execute() throws MojoExecutionException
    {
        getLog().info( "Hello, world." );
    }
}

@Parameter注解是给 成员变量注入 配置值,对应的在项目中要引入使用此plugin时配置以下 插件

<plugin>
                <groupId>xxx</groupId>
                <artifactId>xxx</artifactId>
                <configuration>
                    <port>9090</port>
                </configuration>
</plugin>
这样配置信息就注入了Mojo对象内了。
code

这个注解 @Mojo(name="sayhi"),sayhi就是一个goal。这样的类能够有多个,固然是不一样的goal。

那么若是我 

mvn sun:sayhi
则 该类的execute方法就会被执行。maven plugin的工做原理就是如此了。你能够动手开始你的第一个maven plugin的开发了。下面讲一些其中可能会遇到的坑。


4,plugin classLoader

颇有可能你的插件是要做用于引用这个插件的那个maven项目的。可是plugin是被叫作plugin classLoader加载的,而这个load是没有引用方project的classPath的,也就是说在plugin代码中没法加载引用方project的类和对象。

参考:http://maven.apache.org/guides/mini/guide-maven-classloading.html

可是这样也不是说彻底没有办法,咱们能够经过给Mojo对象添加一个成员变量MavenProject,该对象能够获取 注解@Mojo(requiresDependencyResolution=ResolutionScope.RUNTIME)中指定的classPath路径,经过建立本身的classLoader来加载目标class就好了。

@Parameter(defaultValue = "${project}",required = true)
private MavenProject project;
private ClassLoader projectLoader;
private ClassLoader getClassLoader() throws MojoExecutionException{
        if(projectLoader==null){
            try{
                List<String> classpathElements = project.getCompileClasspathElements();
                System.out.println(classpathElements);
                classpathElements.add(project.getBuild().getOutputDirectory() );
                System.out.println(project.getBuild().getOutputDirectory());
                classpathElements.add(project.getBuild().getTestOutputDirectory() );
                System.out.println(classpathElements);
                URL urls[] = new URL[classpathElements.size()];


                for ( int i = 0; i < classpathElements.size(); ++i )
                {
                    urls[i] = new File( (String) classpathElements.get( i ) ).toURI().toURL();
                }
                projectLoader=new URLClassLoader(urls, getClass().getClassLoader() );
            }
            catch (Exception e){
                throw new MojoExecutionException("Couldn't create a project classloader.", e);
            }
        }
        return projectLoader;
} 

接下来你要执行 目标 maven plugin goal时仍然会发现找不到classPath那是由于项目尚未编译,而你但愿你的plugin是自动执行某个maven生命周期后执行,好比在编译后执行,那么就须要 @Execute(phase = LifecyclePhase.COMPILE)

5 ,上传你的插件到本身的私服后,在设置maven的仓库为本身私服后,就能够下载使用本身插件了

相关文章
相关标签/搜索