我们接着上篇文章,来继续介绍Maven中几个核心的概念:
POM (Project Object Model)
Maven 插件
Maven 生命周期
Maven 依赖管理
Maven 库
我们首先来看一下,上篇文章做演示的时候生成的pom.xml文件:
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd"> <modelVersion>4.0.0</modelVersion> <groupId>com.test.helloworld</groupId> <artifactId>helloworld</artifactId> <version>1.0-SNAPSHOT</version> <packaging>jar</packaging> <name>helloworld</name> <url>http://maven.apache.org</url> <properties> <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding> </properties> <dependencies> <dependency> <groupId>junit</groupId> <artifactId>junit</artifactId> <version>3.8.1</version> <scope>test</scope> </dependency> </dependencies> </project>
在该配置文件中有三个必须写的字段,groupId,artifactId,version。groupId代表组织或者创建团队的名字,通常用域名全称倒过来,比如说Apache maven 官方就是org.apache.maven。artifactId表示项目的唯一名称。version标识项目开发的版本,snapshot通常表示一个项目处于开发阶段。
所有的项目都继承super POM文件,除非有额外的特殊设置。
Maven 生命周期
项目构建和分发的过程就是一个项目的生命周期。系统内置有三种构建生命周期:default, clean 和 site。default生命周期处理项目部署的问题,clean处理项目的清理问题,site处理项目的站点文档问题。不一一说明了,详细可以参考官方文档中的说明 http://maven.apache.org/guides/introduction/introduction-to-the-lifecycle.html
clean 生命周期中常用的操作:
mvn pre-clean 执行实际项目清理前所需要的流程
mvn clean 用来清理构建阶段产生的文件(删除生成的target目录)
mvn post-clean 执行完成项目清理所需要的流程
default 生命周期常用的操作:
mvn validate 验证项目配置项或者必要的信息是否正确
mvn initialize 初始化构建状态,比如设置属性或者是创建目录
mvn compile 将项目文件进行编译
mvn test 对项目进行单元测试,这个过程不要求项目代码被打包或者是部署(如果代码没有被编译,那么将首先执行compile的过程)
mvn package 将已经编译好的代码打包为分发的格式,比如jar,或者war等
mvn verify 对集成结果进行检查,测试是否满足预期要求
mvn install 将项目安装到自己本地仓库,用作本地其他项目依赖项
mvn deploy 在继承环境或者版本环境中完成,将最终包复制到远程仓库
site 生命周期常用的操作:
mvn pre-site 执行项目生成之前所需要的流程
mvn site 生成项目文档
mvn post-site 执行完成网站所需要的流程,为站点部署做准备
mvn site-deploy 将生成的项目文档上传至指定服务器
Maven 插件
Maven通过插件实现其功能,整个Maven都是插件的集合。简单来说,插件可以帮助我们创建jar文件,创建war文件,编译文件,进行单元测试等。任何项目中你能够想到的功能都是通过插件来实现的。
Maven依赖管理
Maven通过pom.xml文件dependency标签来配置整个项目的依赖包,然后所有的dependency标签被放在它的父标签dependencies中组成一个依赖库的集合。比如,
<dependencies> <dependency> <groupId>junit</groupId> <artifactId>junit</artifactId> <version>3.8.1</version> <scope>test</scope> </dependency> </dependencies>
这里dependency节点中,goupId依旧是组织或者创建团队的名字,artifactId为该插件的名字,version为该插件的版本号。scope为该插件的作用范围。依赖范围用于限制依赖关系传递性,并会影响到各类构建 任务的类文件路径。默认如果配置了该选项,插件将会从http://repo.maven.apache.org/maven2/进行下载。在首次安装的时候我们可以看到download from xxx。
scope有6种可用的配置项:
compile 这是默认的配置选项,编译的依赖关系在所有项目类路径都可用。而且,这些依赖关系被传递到依赖项目。
provided 这个和compile选项很类似,表示在JDK或容器运行时提供依赖关系。 例如,在为Java Enterprise Edition构建Web应用程序时,可以将Servlet API和相关的Java EE API的依赖项设置为范围,因为Web容器提供了这些类。 此作用域仅在编译和测试类路径中可用,不可传递。
runtime 顾名思义,这个配置项是在项目运行时调用依赖插件,而不是编译的时候。
test 这个主要用于测试阶段,对于项目并不是必须不可的。不可传递。
system 与provided类似,除非明确指定包含它的jar文件。
import (Maven 2.0.9+) 只支持在<dependencyManagement>部分的类型pom依赖。 它指示依赖项将被替换为指定POM的<dependencyManagement>部分中的依赖关系的有效列表。 由于它们被替换,因此具有导入范围的依赖关系实际上并不参与限制依赖关系的传递性。
如果有多个子项目有公共的依赖库文件,那么我们可以在其父pom文件中指定,这样子pom直接做继承就好了。详细情况可以参考官方文档:
https://maven.apache.org/guides/introduction/introduction-to-dependency-mechanism.html
这里需要注意的是,如果子类依赖包的类型不一样,那么需要在继承之后特别设置type字段。因为依赖寻找的顺序是{groupId, artifactId, type, classifier},在很多情况下我们仅仅需要指定{groupId, artifactId},因为默认情况下type的类型为jar。
Maven 库
Maven库被分为本地库和远程库,本地库可以看做是安装时远程库的一个副本,还包括本地项目构建时的临时构建工作。远程库指除了本地库以外的其他库,可以通过比如file:// 或者 http:// 协议对文件进行访问下载的。比如一些第三方库,repo.maven.apache.org和uk.maven.org maven的中心库等。另外一些比如公司内部搭建的库,用于内部分享相对隐私的数据。我们可以通过maven安装目录下,conf目录中的settings.xml来对远程仓库的地址进行配置。具体的配置说明可以参考官方的文档,或者settings.xml的注释部分。这里就不多讲了。
本地仓库的位置在用户家目录下一个.m2的隐藏文件夹,然后里边有个repository的目录,比如我这里:
比如web container插件jetty:
我们可以在自己的项目编译好之后将其部署到我们本地的库中,我们在我们的项目目录中(pom.xml)所在的目录执行 mvn install。
如果有远成仓库的上传权限,我们也可以将做好的项目上传至远程仓库。