maven 配置文件
配置文件的加载顺序 ~/.m2/setting.xml --> conf/settings.xml
../conf/settings.xml 中配置本地仓库地址 <localRepository>../local/repo</localRepository>
pom 文件
dependencyManagement 标签
在 Maven 中 dependencyManagement 的作用其实相当于一个对所依赖 jar 包进行版本管理的管理器。
pom.xml 文件中,jar 的版本判断的两种途径:
1.如果 dependencies 里的 dependency 自己没有声明 version 元素,那么 maven 就会到 dependencyManagement 里面去找有没有对该 artifactId 和 groupId 进行过版本声明,如果有,就继承它,如果没有就会报错,告诉你必须为 dependency 声明一个 version。
2.如果 dependencies 中的 dependency 声明了 version,那么无论 dependencyManagement 中有无对该 jar 的 version 声明,都以 dependency 里的 version 为准。
1. 为方便管理,建议只出现在父 pom 。子 pom 一般是 dependencies 。
2. 统一版本号 <version> 标签。
3. 声明作用 (子 pom 里用到再引),不会被实际引用,子 pom 的引用必须在父 pom 存在。
Dependency 的子标签
Type 标签
依赖的类型,默认方式 jar 。
scope 标签
在POM 4 中,<dependency>中还引入了<scope>,它主要管理依赖的部署,可以优化 pom,什么时候用和需不需要打到包中。目前<scope>可以使用5个值:
* compile,缺省值,适用于所有阶段(编译、测试、运行),会打到 jar 或 war 包中。
* provided,适用于编译和测试阶段,不会打到 jar 包或 war 包。表示期望 JDK、容器或使用者会提供这个依赖。如 servlet.jar。
* runtime,在测试和运行阶段使用,会打到 jar 或 war 包中。如 JDBC 驱动,适用运行和测试阶段。
* test,只在测试阶段使用。不会打到 jar 包或 war 包。
* system,类似 provided,需要显式提供包含依赖的 jar,Maven 不会在 Repository 中查找它。
依赖范围控制哪些依赖在哪些 classpath 中可用,哪些依赖包含在一个应用中。让我们详细看一下每一种范围:
compile (编译范围)
compile 是默认的范围;如果没有提供一个范围,那该依赖的范围就是编译范围。编译范围依赖在所有的 classpath 中可用,同时它们也会被打包。
provided (已提供范围)
provided 依赖只有在当 JDK 或者一个容器已提供该依赖之后才使用。例如, 如果你开发了一个 web 应用,你可能在编译 classpath 中需要可用的 Servlet API 来编译一个 servlet,但是你不会想要在打包好的 WAR 中包含这个 Servlet API;这个 Servlet API JAR 由你的应用服务器或者 servlet 容器提供。已提供范围的依赖在编译 classpath (不是运行时)可用。它们不是传递性的,也不会被打包。
runtime (运行时范围)
runtime 依赖在运行和测试系统的时候需要,但在编译的时候不需要。比如,你可能在编译的时候只需要 JDBC API JAR,而只有在运行的时候才需要 JDBC 驱动实现。
test (测试范围)
test 范围依赖 在一般的编译和运行时都不需要,它们只有在测试编译和测试运行阶段可用。
system (系统范围)
system 范围依赖与 provided 类似,但是你必须显式的提供一个本地系统中 JAR 文件的路径。这么做是为了允许基于本地对象编译,而这些对象是系统类库的一部分。这样的构件应该是一直可用的,Maven 也不会在仓库中去寻找它。如果你将一个依赖范围设置成系统范围,你必须同时提供一个 systemPath 元素。注意该范围是不推荐使用的(你应该一直尽量去从公共或定制的 Maven 仓库中引用依赖)。
依赖的传递性
第一列表示直接依赖(A->B)的 scope,第一行表示间接依赖(B->C)的 scope,中间值表示 A 项目对 C jar 的依赖关系(A->C)。例如,作用域是 test 的包不会传递到引用这个项目的其它项目。- 表示不传递依赖。
compile | test | provided | runtime | |
compile | compile | - | - | runtime |
test | test | - | - | test |
provided | provided | - | provided | provided |
runtime | runtime | - | - | runtime |
依赖调节
最短路径原则
加载先后原则
exclusions 标签
exclusions 排除包,spring 的框架中自带的 log 依赖一般不用,予以排除。
<dependency> <groupId>org.springframework</groupId> <artifactId>spring-context</artifactId> <verison>${org.springframework-version}</verison> <exclusions> <exclusion> <groupId>commons-logging</groupId> <artifactId>commons-logging</artifactId> </exclusion> </exclusions> </dependency>
mvn 依赖查找技巧
把 mvn 依赖树输出到文本文件中。命令窗口中 进入到该 model 的 pom 所在的文件夹路径,再执行命令 mvn dependency:tree > d.txt
版本管理
a) 1.0-SNAPSHOT 更新时,可以原号推到私服上去。
i. 删除本地的 repository 库。
ii. mvn clean package -U (不管本地有没有 jar 包,强制到远程拉一次)
b) 主版本号.次版本号.增量版本号-<里程碑版本>
1.0.0-RELAESE/Final
多模块打包
多模块项目打包后,其他 module 作为一个 jar 放在 web 的 war 的 lib 中。他们的 spring 配置文件,需要在 web.xml 中进行如下配置,才能找到。
<context-param>
<param-name>contextConfiglocation</param-name>
<param-value>classpath*:applicationContext*.xml</param-value>
</context-param>
就能找到以 applicationContext 开头的 xml。
classpath 和 classpath* 区别:
classpath:只会到你指定的 class 路径中查找找文件;
classpath*:不仅包含 class 路径,还包括 jar 文件中(class路径)进行查找。
项目生命周期
Maven 有三套相互独立的生命周期(lifecycle),分别是:clean、default、site。clean 主要是清理项目、default 是 Maven 最核心的构建项目、site 是生成项目站点。每一个大的生命周期又分为很多个阶段(phase)。后面的阶段依赖于前面的阶段。阶段又由 goal 组成。A Build Lifecycle is Made Up of Phases. A Build Phase is Made Up of Plugin Goals. phase 可以认为是一个虚拟的名字,实际上的 maven 是由许多的 goal 组成。phase 标签可以指定该插件的作用阶段(phase)。插件要在某个 phase 之前运行,phase 就定义为前一个 phase。在 pom.xml 中的标签形式为:
<plugin> ... <executions> <execution> <phase>packge</phase> <goals> <goal></goal> </goals> </exection> </executions> </plugin>
生命周期本身相互独立,用户可以仅仅调用生命周期的某一个阶段,也就是说用户调用了 default 周期的任何阶段,并不会触发 clean 周期以及 site 周期的任何事情。三大生命周的阶段,如下图:
(1)clean周期:
pre-clean:准备清理
clean:真正的清理工作
post-clean:执行清理后的一些后续工作
(2)default周期:
validate:验证
initialize:初始化配置
generate-sources:生成源代码编译目录
process-sources:处理项目主资源文件,复制资源文件到outputclasspath
generate-resources:生成资源目录
process-resources:处理资源文件
complie:编译源代码
process-classes:处理编译后文件
generate-test-sources:生成测试目录
process-test-sources:处理项目测试资源文件,复制测试资源文件到outputclasspath
generate-test-resources:生成测试资源文件
process-test-resources:处理测试资源文件
test-compile:编译测试代码
process-test-classes:处理测试代码
test:单元测试运行测试代码
prepare-package:打包前的准备
package:将编译好的代码打包成为jar或者war或者ear等等
pre-integration-test:准备整体测试
integration-test:整体测试
post-integration-test:为整体测试收尾
verify:验证
install:安装到本地Maven库
deploy:将最终包部署到远程Maven仓库
(3)site周期:
pre-site:准备生成站点
site:生成站点及文档
post-site:站点收尾
site-deploy:将生成的站点发布到服务器上
mvn 常用命令
compile
clean 删除 target/
test 运行test case,包括 junit 和 testNG
package
install 将java工程打成jar、war
maven 执行 install 的存放位置是本地的 repository 仓库。mvn clean install -Dmaven.test.skip=true
deploy 发本地jar发布到remote
插件
常用网站
jar 包坐标查询 https://mvnrepository.com/
maven 插件查询 tomcat7-maven-plugin:https://maven.apache.org/plugins/ tomcat-maven-plugin:http://www.mojohaus.org/plugins.html
常用插件
<build> <finalName>${project.artifactId}</finalName> <plugins> <!-- 资源文件拷贝插件 --> <plugin> <groupId>org.apache.maven.plugins</groupId> <artifactId>maven-resources-plugin</artifactId> <version>2.7</version> <configuration> <encoding>UTF-8</encoding> </configuration> </plugin> <!-- java编译插件 --> <plugin> <groupId>org.apache.maven.plugins</groupId> <artifactId>maven-compiler-plugin</artifactId> <version>3.2</version> <configuration> <source>1.7</source> <target>1.7</target> <encoding>UTF-8</encoding> </configuration> </plugin> </plugins> <pluginManagement> <plugins> <!-- 配置Tomcat插件 --> <plugin> <groupId>org.apache.tomcat.maven</groupId> <artifactId>tomcat7-maven-plugin</artifactId> <version>2.2</version> <configuration> <port>80</port> <path>/SSM</path> <uriEncoding>UTF-8</uriEncoding> <server>tomcat7</server> <!-- 指定tomcat名称 --> </configuration> </plugin> </plugins> </pluginManagement> </build>
findbugs 静态代码检查。 针对于字节码操作的,需要先生成字节码。 命令 mvn findbugs:findbugs 执行完后,点击该插件的 gui goal 查看结果。
source 打包源代码。phase 标签设置为 install。不使用在对外的工作中。
assembly 打可执行 jar 包等
<plugin> <artifactId>maven-assembly-plugin</artifactId> <version>3.0.0</version> <configuration> <descriptorRefs> <descriptorRef>jar-with-dependencies</descriptorRef> <!-- 把依赖也打到jar中 --> </descriptorRefs> <archive> <manifest> <mainClass>com.test.Test</mainClass> <!-- 主方法类 --> </manifest> </archive> </configuration> <executions> <execution> <id>make-assembly</id> <phase>package</phase> <goals> <goal>single</goal> </goals> </execution> </executions> </plugin>
配置了一个 manifest 标签来配置 Main 函数的入口。执行命令 mvn assembly:assembly 即能生成可执行jar。 生成可执行 jar 的3种方式。
versions 项目版本修改同步
maven 修改 主 pom 中项目的版本号,要想子 module 中 parent 标签下的 version 标签的值同步改变,可使用 version 插件,不然得手动修改;插件坐标为:
<build> <plugins> <plugin> <groupId>org.codehaus.mojo</groupId> <artifactId>version-maven-plugin</artifactId> <version>2.3</version> <plugin> <plugins> <build>
在引用里插件的情况下,于命令窗口的项目路径下运行 mvn 命令 mvn versions:set -DnewVersion=1.1.20180101-SNAPSHOT 即可。
tomcat7
model 单独使用的插件在子 pom 单独定义。
如果对 web 的 model 单独使用的插件,就单独定义在 web 的 pom 中,例如:
<plugin> <groupId>org.apache.tomcat.maven</groupId> <artifactId>tomcat7-maven-plugin</artifactId> <version>2.2</version> <configuration> <port>8080</port> <path>/<path> </configuration> <plugin>
如果在 pom.xml 中配置了 Tomcat 插件,在 idea 右边的 Maven Project 中会出现对应的插件。此时只需要右击,就可以以 run 模式或者 debug 模式启动项目。或者:点击 Run-->Edit Configurations 后搜索 maven
自定义插件
guide:https://maven.apache.org/guides/plugin/guide-java-plugin-development.html
步骤:
1、创建项目 修改项目的 pom,添加一个 <packaging>maven-plugin</packaging> 标签项。
2、创建一个继承 AbstractMojo 的类。
3、编码。@Mojo(name = "sayHello") 中的 name 定义的就是插件的 goal 的名称。
import org.apache.maven.plugin.AbstractMojo; import org.apache.maven.plugin.MojoExecutionException; import org.apache.maven.plugin.MojoFailureException; import org.apache.maven.plugin.annotations.LifecyclePhase; import org.apache.maven.plugin.annotations.Mojo; @Mojo(name = "sayHello", defaultPhase = LifecyclePhase.PACKGE) public class BoomMojo extends AbstractMojo { @Parameter private String msg; @Parameter private List<String> options; public void execute() throws MojoException, MojoFailureException { System.out.println(boom's sayHello ! + msg); System.out.println(boom's sayHello ! + options); } }
4、执行 mvn clean install 生成 jar 包。
5、在其他项目的 pom 中,进行引用参数传递。 若要在 mvn 执行命令中添加 -Dgxx=sd 参数,需要定义 @Parameter(property = "gxx")。也可用这个 -D 配置 maven 自带的属性值project.xxx和setting.xxx。maven 的自带属性在 pom 中的引用 ${project.artifactId}
<plugin> <groupId>com.boom</groupId> <artifactId>boom-plugin</artifactId> <version>1.0.0-SNAPSHOT</version> <configuration> <msg>booooom</msg> <options> <option>11</option> </options> </configuration> <executions> <execution> <phase>package</phase> <goals> <goal>sayHello</goal> <goals> </execution> </executions> </plugin>
静态资源链接添加版本号
场景:防止用户端浏览器缓存旧版的静态资源文件。可以通过 maven plugin 插件,实现对 js、css 等文件的缓存问题处理。
页面 js 操作的添加方式:https://blog.csdn.net/qq_36171431/article/details/77840268
插件实现的两种方式:
https://github.com/StruggleBird/asset-cache-control
https://github.com/byzy/jcv-maven-plugin
Profile
1、使用场景,分环境打包。dev/test/pro
project.src.main.resources.conf 包下有 dev、pro、test 等目录包。
<!-- 定义的profile变量 --> <profiles> <profile> <id>dev</id> <properties> <profies.active>dev</profies.active> </properties> <activation> <activeByDefault>true</activeByDefault> <!-- 默认方式 --> </activation> </profile> <profile> <id>test</id> <properties> <profies.active>test</profies.active> </properties> </profile> <profile> <id>pro</id> <properties> <profies.active>pro</profies.active> </properties> </profile> </profiles> <!-- 使用profile变量 --> <build> <resources> <resource> <directory>${basedir}/src/main/resources</directory> <excludes> <exclude>conf/**</exclude> <excludes> </resource> <resource> <directory>${basedir}/src/main/resources/${profile.actve}</directory> </resource> </resources> </build>
输入命令 mvn install -P test 打完的包里 conf 目录下就只有 test 包。
2、在 maven 的 setting.xml 中定义两个 profile 来切换仓库地址。用 <activeProfile> 标签值指定的 profile 的 id,完成切换。
archetype 模板化
生成一个 archetype
命令 mvn archetype:create-from-project
进入目标文件夹 cd /target/generated-sources/archetype
执行 mvn install 或 mvn deploy 生成模板。
可以把模板添加到 idea 的 maven 骨架列表。Add Archetype... 不推荐,会下载远端的 xml 配置,易失败。
从 archetype 创建项目 mvn archetype:generate -DarchetypeCatalog=local 。
常用镜像
<mirror> <id>alimaven</id> <name>aliyun maven</name> <url>http://maven.aliyun.com/nexus/content/groups/public/</url> <mirrorOf>central</mirrorOf> </mirror> <mirror> <id>ui</id> <mirrorOf>central</mirrorOf> <name>Human Readable Name for this Mirror.</name> <url>http://uk.maven.org/maven2/</url> </mirror> <mirror> <id>osc</id> <mirrorOf>central</mirrorOf> <url>http://maven.oschina.net/content/groups/public/</url> </mirror> <mirror> <id>osc_thirdparty</id> <mirrorOf>thirdparty</mirrorOf> <url>http://maven.oschina.net/content/repositories/thirdparty/</url> </mirror>