Maven基础教程之插件

3次阅读

共计 3608 个字符,预计需要花费 10 分钟才能阅读完成。

这又是一个系列,一个要把 Maven 讲透的系列,希望能够对大家有帮助!

前言

上一篇《Maven 基础教程之生命周期》中也讲到了,Maven 中通过模板方法这样的设计模式,生命周期只“立牌坊”,而实际上是插件在背后默默的奉献着。也就是说,在 Maven 中,真正的完成生命周期中那些阶段该干的活,都是由插件来做的。所以,从上面的描述,大家也能感受到 Maven 中插件的重要性了;插件非常重要,所以它的知识点肯定也少不了,对吧;然而,我的这篇关于插件的文章,我并不打算长篇大论的铺开来将 Maven 中的插件,因为我觉的有些东西,并不是那样的重要,所以,这篇关于插件的文章,点到为止,意会即可!

插件目标?

在继续下面的总结之前,我们需要先来理解“插件目标”这个概念。根据我们的开发经验,在开发一个软件时,这个软件肯定会包含很多的功能,并不会一个功能搞一个软件;同理,Maven 中的插件也是这样的,比如下图所示:

而这里的每一个功能就对应一个插件目标。比如 maven-dependency-plugin 插件有十多个目标,每个目标对应一个功能。在《Maven 基础教程之依赖》中讲到的 dependency:listdependency:treedependency:analyze这些都是插件目标,这是一种通用的写法,冒号前面是插件前缀,冒号后面是该插件的目标。

插件绑定

说完了插件目标,那这个插件目标到底如何使用呢?上一篇说了生命周期,这个生命周期和插件是相互独立存在的,如果需要插件完成生命周期对应阶段的任何,那就需要将生命周期与插件相互绑定,也就是说需要将生命周期的阶段与插件的目标相互绑定,这样才能完成某个具体的构建任务。

就如上图所示,default 生命周期的 compile 阶段与 maven-compiler-plugin 插件的 compile 插件目标,到时候,就由 compile 插件目标完成 default 生命周期的 compile 阶段对应的实际操作。

关于插件绑定,主要分为内置绑定和自定义绑定两大类。

  • 内置绑定
    我们都知道,为了让 Maven 开箱即用,Maven 开发了很多默认的插件来完成每个生命周期对于阶段的一些工作,同时,也将这些生命周期的一些主要的阶段和这些默认插件的插件目标进行了绑定,这就是内置绑定。对于内置绑定,我们知道有这么一回事,知道 Maven 的实现原理即可,至于哪个插件的插件目标和那个生命周期的阶段进行内置绑定,有了问题再查也 OK 的。
  • 自定义绑定
    为了能补充内置绑定的不足,完成更多个性化的任务,Maven 社区的大牛开发了很多的插件,当然了,我们自己也可以开发,后面会讲到的。那这些插件如何和 Maven 的生命周期的阶段进行绑定呢,这就是我们要说的自定义绑定。下面我们通过一个例子来说明自定义绑定:

    <build>
        <plugins>
          <plugin>
            <groupId>org.apache.maven.plugins</groupId>
            <artifactId>maven-shade-plugin</artifactId>
            <version>3.2.1</version>
            <executions>
              <execution>
                <phase>package</phase>
                <goals>
                  <goal>shade</goal>
                </goals>
                <configuration>
                  <transformers>
                    <transformer implementation="org.apache.maven.plugins.shade.resource.ManifestResourceTransformer">
                      <mainClass>com.jellythink.HelloWorld.App</mainClass>
                    </transformer>
                  </transformers>
                </configuration>
              </execution>
            </executions>
          </plugin>
        </plugins>
    </build>

    在 POM 的 build 元素下的 plugins 子元素中声明插件的使用,插件在 Maven 中同其它包一样,也是作为独立的构建存在,所以也需要通过指定 groupIdartifactIdversion这三个坐标元素去仓库中定位插件。除了基本的插件坐标声明外,还有插件执行配置,executions下每个 execution 子元素可以用来配置执行一个任务。上述例子中通过 phase 配置,将其绑定到 package 生命周期阶段上,再通过 goals 配置指定要执行的插件目标,这样自定义插件绑定就完成了。

    执行 mvn clean install 命令,我们就可以看到这样的输出:

    [INFO] --- maven-shade-plugin:3.2.1:shade (default) @ hello-world ---
    [INFO] Replacing original artifact with shaded artifact.
    [INFO] Replacing E:\Code\Spring\helloworld\target\hello-world-1.0-SNAPSHOT.jar with E:\Code\Spring\helloworld\target\hello-world-1.0-SNAPSHOT-shaded.jar

    可以看到执行了 maven-shade-plugin 插件的 shade 插件目标。

    有的时候,你会看到有的插件不通过 phase 元素配置生命周期阶段,插件目标也能够绑定到生命周期中去。这个时候也不要惊讶,这主要是很多插件的目标在编写时已经定义了默认绑定阶段,我们可以通过 maven-help-plugin 查看插件的详细信息,了解插件目标的默认绑定阶段。执行 mvn help:describe -Dplugin=org.apache.maven.plugins:maven-shade-plugin:3.2.1 -Ddetail 就可以看到插件的完整信息,比如这个插件有几个插件目标,有哪些参数,默认绑定阶段等,通过查找Bound to phase: package,我们就可以看到默认绑定到哪个阶段。

插件配置

我们在实现一个功能时,也会想着通过传递参数来实现更强大的功能。Maven 插件也是这样的,我们可以配置插件目标的参数,满足我们对插件更加个性化的要求。对于插件的参数配置,有以下两种常用方式:

  • 通过命令行进行插件配置
    我们经常看到以下这个命令:

    mvn clean install -Dmaven.test.skip=true

    这个就是典型的通过命令行进行插件配置,maven.test.skip是 maven-surefire-plugin 提供的一个参数,我们通过命令行传入一个 true 参数,表示跳过执行测试。

    参数 -D 是 Java 自带的,其功能是通过命令行设置一个 Java 系统属性。Maven 简单的重用了该参数。

  • 通过 POM 文件进行插件全局配置
    比如有些参数配置,从项目创建到项目发布都不会改变,或者基本上很少改变。对于这种场景,就更适合通过 POM 文件进行插件配置。比如以下的配置我们经常在一些项目中看到:

    <build>
        <plugins>
            <plugin>
                <groupId>org.apache.maven.plugins</groupId>
                <artifactId>maven-compiler-plugin</artifactId>
                <version>3.1</version>
                <configuration>
                    <source>1.7</source>
                    <target>1.7</target>
                </configuration>
            </plugin>
        </plugins>
    </build>

    这样就是一个全局的配置,也就是说,所有使用该插件目标的任务,都会使用这些配置。再回头看看上面插件绑定中自定义绑定里的那个例子,那个参数就是插件特有的参数,我们就可以通过参数实现一个不一样的功能。

总结

Maven 中最后一个核心概念终于总结完了。集齐了 Maven 中坐标、仓库、依赖、生命周期和插件这五大核心概念,应该就对 Maven 有一个比较全面的理解和认识了。这篇对 Maven 中的插件进行了比较全面的理解,当然了还有一些用的很少的知识点,或者我认为即使你不知道这些知识点也不会影响你对 Maven 插件的理解,在这里没有进行总结,如果你感兴趣,也可以自己阅读以下《Maven 实战》这本书,你也许会有不同的收获。Maven 的插件总结就到此完毕,接下来的文章将偏重于 Maven 的使用实战,感谢大家的一路支持,我们下一篇再见~ 祝好!

果冻想,玩代码,玩技术!

2019 年 4 月 17 日,于内蒙古呼和浩特。


正文完
 0