Maven是一个项目管理和构建自动化工具,主要服务于基于Java的项目。它使用一个名为POM(Project Object Model)的XML文件来描述项目的构建过程、依赖、插件等信息。
肖哥弹架构 跟大家“弹弹” 高并发锁, 关注公号回复 'mvcc' 获得手写数据库事务代码
欢迎 点赞,关注,评论。
关注公号Solomon肖哥弹架构获取更多精彩内容
历史热点文章
- 解锁大语言模型参数:零基础掌握大型语言模型参数奥秘与实践指南
- 高性能连接池之HikariCP框架分析:高性能逐条分解(架构师篇)
- 缓存雪崩/穿透/击穿/失效原理图/14种缓存数据特征+10种数据一致性方案
- Java 8函数式编程全攻略:43种函数式业务代码实战案例解析(收藏版)
- 一个项目代码讲清楚DO/PO/BO/AO/E/DTO/DAO/ POJO/VO
- 17个Mybatis Plugs注解:Mybatis Plugs插件架构设计与注解案例(必须收藏)
0、本节范围
1、maven POM 结构设计
POM 结构说明
- 项目对象模型 (POM) : Maven 项目的核心配置文件。
- 模型基础信息 : 包含模型版本、组 ID、构件 ID、版本和打包方式。
- 模型版本: POM 模型的版本。
- 组 ID: 项目组的唯一标识符。
- 构件 ID: 项目的唯一基础名称。
- 版本: 项目的当前版本。
- 打包方式: 项目的打包方式,如 jar、war、pom 等。
- 模型基础信息 : 包含模型版本、组 ID、构件 ID、版本和打包方式。
- 父项目 : 定义项目的父项目信息,包括父组 ID、父构件 ID、父版本和父相对路径。
- 资源(jar/project)依赖 : 项目依赖的列表,包括 jar 和 project 依赖。
- 构建配置 : 定义项目的构建过程,包括插件配置。
- 插件 : 构建过程中使用的插件列表。
- 配置文件 : 定义项目的不同环境配置文件。
- 配置文件项 : 单个配置文件项。
- 配置文件 ID: 配置文件的唯一标识。
- 激活条件: 定义配置文件的激活条件。
- 仓库 : 配置文件特有的仓库列表。
- 插件仓库 : 配置文件特有的插件仓库列表。
- 配置文件项 : 单个配置文件项。
2、maven POM 案例说明
以下是一个包含详细注释的 Maven pom.xml
案例,这个 pom.xml
文件定义了一个 Maven 项目的完整结构,包括模型版本、项目坐标、依赖管理、构建配置、插件和配置文件等。
3、maven 配置文件激活策略
在 Maven 的 pom.xml
文件中定义了 <profile>
后,你可以通过多种方式激活该配置文件(profile)。配置文件 dev
的激活可以通过以下方式进行:
3.1. 命令行激活
在执行 Maven 命令时,可以通过 -P
参数指定要激活的配置文件的 ID。例如,要激活 ID 为 dev
的配置文件,可以使用:
这告诉 Maven 在构建时使用 dev
配置文件中定义的设置。
3.2. 在 settings.xml
中激活
在用户或全局的 settings.xml
文件中,可以使用 <activeProfiles>
标签激活配置文件。这通常位于 ~/.m2/settings.xml
(用户设置)或 /etc/maven/settings.xml
(全局设置)。
在这个例子中,每次 Maven 运行时都会自动激活 dev
配置文件。
3.3. 自动激活
在 pom.xml
中定义的配置文件可以包含激活条件,如果这些条件满足,配置文件将自动激活。例如:
在这个例子中,如果运行 Maven 的环境符合指定的 JDK 版本和操作系统条件,dev
配置文件将自动激活。
3.4. 通过环境变量激活
可以在 activation
标签内使用环境变量来控制配置文件的激活:
然后,可以在命令行中设置环境变量来激活配置文件:
或者在 Windows 命令行中:
或者 通过 Maven 命令行参数激活,在 Maven 命令中直接设置属性 env
:
这些方法提供了灵活的配置文件激活方式,可以根据不同的构建环境和需求进行选择。
4、maven 依赖管理
Maven 使用一个中央仓库来管理项目的依赖。每个依赖都由一组坐标定义,Maven 可以根据这些坐标自动下载和安装依赖。
4.1 依赖坐标
每个依赖都由一组坐标定义,这些坐标是:
- GroupId: 项目组的唯一标识符,通常是一个反向域名。
- ArtifactId: 项目的唯一基础名称。
- Version: 项目当前的版本。 这些坐标一起构成了 Maven 依赖的全局唯一标识符。
4.2 依赖范围
依赖范围定义了依赖在哪些构建阶段被包含,常见的依赖范围有:
- compile: 编译范围,这是默认值。依赖在编译、测试、运行时都可用。
- test: 测试范围,依赖仅在测试编译和执行阶段可用。
- provided: 提供范围,依赖在编译和测试时可用,但在运行时需要由运行环境提供。
- runtime: 运行时范围,依赖在测试和运行时可用,但不在编译时。
- system: 系统范围,与 provided 类似,但不推荐使用,因为它要求开发者在本地机器上手动安装指定的依赖。
依赖范围定义了依赖在哪些构建阶段被包含:
4.3 依赖调解
依赖调解(Dependency Mediation)是 Maven 解决依赖冲突的过程。当项目中引入的多个依赖指定了同一个依赖的不同版本时,Maven 会根据版本号选择一个版本:
- Maven 会遵循“最近版本”原则,选择最新的版本作为最终版本。
- 如果依赖有明确的版本号,Maven 会使用指定的版本。
- 如果依赖使用了动态版本号(如
${property.name}
),Maven 会使用 POM 中定义的属性值。
依赖调解是 Maven 解决依赖冲突的过程:
5.4 传递性依赖
传递性依赖是指一个依赖除了它自己还包含了其他依赖。Maven 会解析所有传递性依赖,并尝试确保依赖树的一致性和最小化:
- Maven 会构建项目的依赖树,展示每个依赖的来源。
- Maven 会尝试解决任何版本冲突,选择一个合适的版本。
- Maven 提供了依赖排除功能,允许用户从依赖中排除特定的传递性依赖。
传递性依赖是指一个依赖除了它自己还包含了其他依赖:
在这个例子中,A
依赖 B
,B
又依赖 C
,但 C
被 B
依赖项中的 <exclusions>
标签排除了
5. 构建生命周期
Maven 的构建生命周期是一系列阶段,每个阶段执行一组特定的任务。主要的生命周期包括:
- clean: 清理项目。
- default (编译、测试、打包、部署等): 包括 compile、test、package、install、deploy。
- site: 生成项目报告文档。
每个生命周期阶段都可以由一系列插件来实现,这些插件定义了该阶段的具体行为。
Maven 生命周期图说明
- Clean 生命周期: 负责清理项目,例如删除生成的文件。
pre-clean
: 清理前的操作。clean
: 执行清理操作。post-clean
: 清理后的操作。
- Default 生命周期: 构建项目的主要生命周期。
validate
: 验证项目信息。compile
: 编译源代码。test
: 运行测试。package
: 将代码打包。integration-test
: 集成测试。verify
: 验证构建。install
: 安装到本地仓库。deploy
: 部署到远程仓库。
- Site 生命周期: 生成项目报告文档。
pre-site
: 准备生成项目文档。site
: 生成项目文档。post-site
: 生成项目文档后的操作。site-deploy
: 部署项目文档。
插件
- JGit: Maven 使用 JGit 插件处理 Git 相关任务。
- maven-compiler-plugin: Maven 使用编译插件编译 Java 代码。
- maven-surefire-plugin: Maven 使用 Surefire 插件运行单元测试。
- maven-jar-plugin: Maven 使用 JAR 插件打包应用为 JAR 文件。
- maven-war-plugin: Maven 使用 WAR 插件打包应用为 WAR 文件。
- maven-deploy-plugin: Maven 使用部署插件部署项目。
- maven-site-plugin: Maven 使用 Site 插件生成项目报告文档。
5.1 默认构建生命周期时序图
Maven 默认构建生命周期时序图说明
- Maven: 表示 Maven 构建工具本身,负责驱动整个构建过程。
- Plugins: 表示 Maven 插件,它们实现了各个构建阶段的具体任务。
各个阶段说明:
- validate: 验证项目可以被构建。
- initialize: 初始化构建。
- generate-sources: 生成源代码。
- process-sources: 处理源代码。
- generate-resources: 生成资源文件。
- process-resources: 复制并处理资源文件到目标目录。
- compile: 编译项目的源代码。
- process-classes: 处理编译生成的类文件。
- generate-test-sources: 生成测试源代码。
- process-test-sources: 处理测试源代码。
- generate-test-resources: 生成测试资源。
- process-test-resources: 复制并处理测试资源文件到目标目录。
- test-compile: 编译测试源代码。
- process-test-classes: 处理测试编译生成的类文件。
- test: 运行测试。
- prepare-package: 准备打包。
- package: 将编译的代码打包成 JAR、WAR 或其他格式。
- pre-integration-test: 在集成测试执行之前准备。
- integration-test: 执行集成测试。
- post-integration-test: 集成测试执行之后的工作。
- verify: 验证包是否符合质量标准。
- install: 将包安装到本地仓库,供其他项目使用。
- deploy: 将最终的包部署到远程仓库。
5.2 构建生命周操作命令
5.2.1 执行整个生命周期
执行以下命令将处理整个构建生命周期,默认从 validate
阶段开始直到 install
阶段:
如果你想跳过测试,可以使用 -DskipTests
参数:
5.2.2 执行特定阶段
你可以通过在命令中指定阶段来执行特定阶段或一系列阶段。例如:
- 编译源代码:
或者使用 package
阶段作为开始点:
- 运行测试:
如果你想要运行特定的测试,可以使用 it.test
参数:
- 打包项目:
- 安装项目到本地仓库:
- 部署项目到远程仓库:
在执行部署之前,你可能需要配置 pom.xml
中的部署信息和服务器信息。
5.2.3 使用生命周期辅助命令
Maven 也提供了一些辅助命令来帮助你执行常见的任务:
- 清理项目 (Clean Lifecycle):
这将执行 clean
阶段,通常删除 target
目录中的所有生成物。
- 更新项目依赖 (Default Lifecycle):
这将更新项目的依赖,但不构建项目。
- 生成项目报告 (Site Lifecycle):
这将生成项目报告,包括 JavaDoc、测试结果等。
5.2.4 执行特定插件的特定目标
你还可以执行特定插件的特定目标(goal)。例如,使用 Javadoc 插件生成 JavaDoc:
请注意,javadoc:javadoc
是 maven-javadoc-plugin
的 javadoc
目标。
5.2.5 组合命令
你可以组合 Maven 命令来执行多个阶段或任务。例如,要清理项目并安装:
这将执行从 clean
阶段到 install
阶段的所有任务。
6. 插件和目标
Maven 插件是实现 Maven 生命周期阶段的代码。插件可以被绑定到生命周期的特定阶段,或者直接由用户在命令行中调用。
- 插件: 一个 Maven 插件可以包含多个目标(goals),每个目标执行一个特定的任务。
- 目标: 插件中的一个可执行单元,例如
maven-compiler-plugin
有一个compile
目标,用于编译源代码。
6.1 插件与目标关系图
Maven 插件与目标图说明
- 插件 (Plugin) : Maven 插件是 Maven 构建过程中的一个扩展点,可以执行多种任务。
- 目标 1, 2, 3 (Goal) : 表示插件中定义的不同的可执行目标。
插件实例:maven-compiler-plugin
- maven-compiler-plugin:
- compile: 编译项目的主源代码。
- testCompile: 编译测试源代码。
执行插件目标
你可以通过命令行执行特定的 Maven 目标:
例如,要执行 maven-compiler-plugin 的 compile 目标:
这将编译项目的源代码。
6.2 插件与目标类设计图
Maven 类图说明
- Goal (目标) :
goalName
: 目标的名称。description
: 目标的描述。configurations
: 目标的配置参数。phase
: 目标绑定的构建生命周期阶段。
- Plugin (插件) :
groupId
: 插件的组唯一标识符。artifactId
: 插件的唯一基础名称。version
: 插件的版本。goals
: 插件包含的目标列表。
- Execution (执行) :
id
: 执行的唯一标识符。phase
: 执行的构建生命周期阶段。goals
: 执行指定的目标列表。
- Project (项目) :
groupId
: 项目的组唯一标识符。artifactId
: 项目的唯一基础名称。version
: 项目当前版本。plugins
: 项目使用的插件列表。executions
: 项目配置的执行列表。
6.3 插件与目标执行流程图
Maven 插件工作流程说明
- 开始: 构建过程启动。
- 项目构建触发: Maven 根据命令行输入或 IDE 触发构建。
- 插件是否被调用: 检查当前构建阶段是否需要执行插件。
- 插件初始化: 插件载入并初始化。
- 目标列表载入: 插件中定义的所有目标被载入。
- 配置参数处理: 处理插件的配置参数。
- 执行具体目标: 执行具体的构建任务。
- 所有目标是否完成: 检查插件中的所有目标是否执行完成。
- 插件后处理: 执行完成后的清理和资源回收。
- 构建继续或结束: 根据构建流程,决定是继续执行下一个插件还是结束构建。
6.4 插件定义XML案例
6.4.1. maven-compiler-plugin 插件配置示例
这个配置指定了用于编译项目的 Maven 编译插件,设定了 Java 源代码和目标编译版本为 1.8。
多目标定义
这个配置案例展示了如何在 Maven 项目的 pom.xml
文件中配置 maven-compiler-plugin
插件,并将其绑定到特定的构建阶段和目标。这样,当 Maven 构建到达 compile
和 test-compile
阶段时,它将分别执行 compile
和 testCompile
目标。
6.4.2. maven-surefire-plugin 插件配置示例
这个配置用于运行单元测试的 Maven Surefire 插件,设置为不跳过测试。
6.4.3. maven-jar-plugin 插件配置示例
这个配置用于创建可执行 JAR 文件的 Maven JAR 插件,指定了程序的主类。
6.4.4. maven-war-plugin 插件配置示例
这个配置用于创建 Web 应用的 WAR 文件的 Maven WAR 插件,指定了 Web 应用资源的目录。
6.4.5. maven-deploy-plugin 插件配置示例
这个配置用于将项目部署到远程仓库的 Maven Deploy 插件。
6.4.6. maven-site-plugin 插件配置示例
这个配置用于生成项目报告的 Maven Site 插件。 用户可以通过配置 POM 来自定义插件的行为,或者通过命令行参数来传递参数给插件。
其他内容在第二篇文章《高效开发Maven架构设计图解/掌握项目工程自动化技巧(精通篇二)》中。。。