一、Maven概述
Maven 是什么?
Maven 是一个项目管理和整合工具。Maven 为开发者提供了一套完整的构建生命周期框架。开发团队几乎不用花多少时间就能够自动完成工程的基础构建配置,因为 Maven 使用了一个标准的目录结构和一个默认的构建生命周期。
在有多个开发团队环境的情况下,Maven 能够在很短的时间内使得每项工作都按照标准进行。因为大部分的工程配置操作都非常简单并且可复用,在创建报告、检查、构建和测试自动配置时,Maven 可以让开发者的工作变得更简单。
Maven 能够帮助开发者完成以下工作:
- 构建
- 文档生成
- 报告
- 依赖
- SCMs
- 发布
- 分发
- 邮件列表
Maven 的目标
Maven 的主要目的是为开发者提供
- 一个可复用、可维护、更易理解的工程综合模型
- 与这个模型交互的插件或者工具
Maven 工程结构和内容被定义在一个 xml 文件中 - pom.xml,是 Project Object Model (POM) 的简称,此文件是整个 Maven 系统的基础组件。
约定优于配置
开发者不需要再关心每一个配置细节,比如说,代码存放在哪里,打包的class在哪里,等等。Maven 为工程提供了合理的默认行为。当创建 Maven 工程时,Maven 会创建默认的工程结构。开发者只需要合理的放置文件
举例说明,下面的表格展示了工程源码文件、资源文件的默认配置,和其他一些配置。假定 ${basedir} 表示工程目录:
配置项 | 默认值 |
---|---|
source code | ${basedir}/src/main/java |
resources | ${basedir}/src/main/resources |
Tests | ${basedir}/src/test |
Complied byte code | ${basedir}/target |
distributable JAR | ${basedir}/target/classes |
为了构建工程,Maven 为开发者提供了选项来配置生命周期目标和工程依赖(依赖于 Maven 的插件扩展功能和默认的约定)。大部分的工程管理和构建任务是由 Maven 插件完成的。
开发人员不需要了解每个插件是如何工作的,就能够构建任何Maven 工程。使用插件只需要进行简单的配置,就可以使用
二、POM
POM 它放在工程根目录下,包含了关于工程和各种配置细节的信息,Maven 使用这些信息构建工程。
POM 也包含了目标和插件。当执行一个任务或者目标时,Maven 会查找当前目录下的 POM,从其中读取所需要的配置信息,然后执行目标。
POM 常用的配置,下面会进行详细介绍。
POM必须的字段
每个工程应该只有一个 POM 文件。
所有的 POM 文件需要 project 元素和三个必须的字段:groupId, artifactId,version。表达当前工程的信息
- 在仓库中的工程标识为 groupId:artifactId:version
节点 | 描述 |
---|---|
groupId | 这是工程组的标识。它在一个组织或者项目中通常是唯一的。例如,一个银行组织 com.company.bank 拥有所有的和银行相关的项目。 |
artifactId | 这是工程的标识。它通常是工程的名称。例如,消费者银行。groupId 和 artifactId 一起定义了 artifact 在仓库中的位置。 |
version | 这是工程的版本号。在 artifact 的仓库中,它用来区分不同的版本。例如:com.company.bank:consumer-banking:1.0 com.company.bank:consumer-banking:1.1. |
Super POM
所有的 POM 都继承自一个父 POM(无论是否显式定义了这个父 POM)。父 POM 也被称作 Super POM,它包含了一些可以被继承的默认设置。
Maven 使用 effective pom(Super pom 加上工程自己的配置)来执行相关的目标,它帮助开发者在 pom.xml 中做尽可能少的配置,当然这些配置可以被方便的重写。
三、Maven - 构建生命周期
要了解构建生命周期,需要认识这三个字段 :
- lifecycle 生命周期
- phase 阶段
- goal 目标
lifecycle 中包含phase ,phase 中包含goal 。
mvn命令后面可以跟随phase 或goal。执行命令时,其实就是执行的phase 中的goal 。goal 也可以单独执行。
例如mvn clean
命令后面的clean,是一个phase ,它执行的就是clean lifecycle中的 clean phase中的clean goal 。
下面对这三个字段进行详细的介绍:
3.1、lifecycle
每个lifecycle 中都包含一个或多个phase 。
通过 Maven 命令调用lifecycle中的phase时,该lifecycle中phase之前以及包括该phase在内的所有phase会被执行。
Maven 有以下三个默认的生命周期:
- clean
- default(or build)
- site
下面介绍这三个生命周期
3.1.1、Clean 生命周期
Maven 调用 clean 生命周期,它包含以下phase 。
- pre-clean
- clean
- post-clean
Maven 的 clean goal (clean:clean)绑定到了 clean lifecycle的 clean phase 。它的 clean:clean 目标通过删除构建目录删除了构建输出。所以当 mvn clean 命令执行时,Maven 删除了构建目录。
3.1.2、Default (or Build) 生命周期
Maven 的主要生命周期,被用于构建应用。包括下面的 23 个阶段。
phase | 描述 |
---|---|
validate | 检查工程配置是否正确,完成构建过程的所有必要信息是否能够获取到。 |
initialize | 初始化构建状态,例如设置属性。 |
generate-sources | 生成编译阶段需要包含的任何源码文件。 |
process-sources | 处理源代码,例如,过滤任何值(filter any value)。 |
generate-resources | 生成工程包中需要包含的资源文件。 |
process-resources | 拷贝和处理资源文件到目的目录中,为打包阶段做准备。 |
compile | 编译工程源码。 |
process-classes | 处理编译生成的文件,例如 Java Class 字节码的加强和优化。 |
generate-test-sources | 生成编译阶段需要包含的任何测试源代码。 |
process-test-sources | 处理测试源代码,例如,过滤任何值(filter any values)。 |
test-compile | 编译测试源代码到测试目的目录。 |
process-test-classes | 处理测试代码文件编译后生成的文件。 |
test | 使用适当的单元测试框架(例如JUnit)运行测试。 |
prepare-package | 在真正打包之前,为准备打包执行任何必要的操作。 |
package | 获取编译后的代码,并按照可发布的格式进行打包,例如 JAR、WAR 或者 EAR 文件。 |
pre-integration-test | 在集成测试执行之前,执行所需的操作。例如,设置所需的环境变量。 |
integration-test | 处理和部署必须的工程包到集成测试能够运行的环境中。 |
post-integration-test | 在集成测试被执行后执行必要的操作。例如,清理环境。 |
verify | 运行检查操作来验证工程包是有效的,并满足质量要求。 |
install | 安装工程包到本地仓库中,该仓库可以作为本地其他工程的依赖。 |
deploy | 拷贝最终的工程包到远程仓库中,以共享给其他开发人员和工程。 |
通过 Maven 命令调用phase时,例如 mvn compile,该phase之前以及包括该phase在内的所有phase会被执行。
3.1.3、Site 生命周期
Maven Site 插件一般用来创建新的报告文档、部署站点等。
这个生命周期包括的阶段:
- pre-site
- site
- post-site
- site-deploy
3.2、phase
执行phase实际执行的是goal。如果一个phase没有绑定goal,这个phase就不会被执行。
每个phase定义了一个或多个goals ,其中的goals是顺序执行。
一些phase默认已经绑定了一些goal。对于default lifecycle来说, 这些被绑定的goal并不完全相同,而是和packaging value相关。
所谓的packaging value就是< packaging>jar< / packaging>,对于不同的包类型,打包的过程不尽相同,因此需要执行的goal也不同。
3.3.goal
最终被执行的就是goal
goal与goal之间是独立的。因此单独执行一个goal不会导致其他goal被执行。
3.4、举个例子
mvn clean dependency:copy-dependencies package
clean是phase。
dependency:copy-dependencies是plugin-in dependency 中的 copy-dependencies 目标。(这里涉及到插件,后面会讲到)
package也是一个phase。
maven会顺序执行这3个对象中包含的所有goal。
四、Maven - 仓库
在 Maven 的术语中,仓库是一个位置(place),就是项目中依赖的第三方库,这个库所在的位置叫做仓库。
Maven 仓库有三种类型:
- 本地(local)
- 中央(central)
- 远程(remote)
4.1、本地仓库
Maven 本地仓库是机器上的一个文件夹。它在你第一次运行任何 maven 命令的时候创建。
Maven 本地仓库保存你的工程的所有依赖(library jar、plugin jar 等)。当你运行一次 Maven 构建,Maven 会自动从中央库或远程库下载所有依赖的 jar 文件到本地仓库中。它避免了每次构建时都引用存放在远程机器上的依赖文件。
Maven 本地仓库默认被创建在 %USER_HOME% 目录下。要修改默认位置,在 %M2_HOME%\conf 目录中的 Maven 的 settings.xml 文件中定义另一个路径。
<settings xmlns="http://maven.apache.org/SETTINGS/1.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/SETTINGS/1.0.0
http://maven.apache.org/xsd/settings-1.0.0.xsd">
<localRepository>C:/MyLocalRepository</localRepository>
</settings>
当你运行 Maven 命令,Maven 将下载依赖的文件到你指定的路径中。
4.2、中央仓库
Maven 中央仓库是由 Maven 社区提供的仓库&