前提
确保本地安装了maven
以一个模块工程为例,内部包含了许多maven项目
生命周期
这是全部的生命周期
其中,常用的生命周期的各个功能为:
(clean生命周期)mvn clean
清理target
(default生命周期①)mvn validate
验证项目为maven项目,正确并且所有信息可用
(default生命周期②)mvn compile
编译源代码为.class
文件(java)
(default生命周期③)mvn test
对管理的模块项目进行test目录下的(JUnit)单元测试
(default生命周期④)mvn package
打包.class
文件成为JAR(或其它格式文件)
(default生命周期⑤)mvn verify
集成测试,运行任意的检查测试来验证项目达到标准
(default生命周期⑥)mvn install
安装包到本地maven仓库(自己取的结构名下可以找到),可供他人使用
(default生命周期⑦)mvn depoly
远程部署,需要在maven本地仓库的setting里面写用户名密码,以及连上服务器上的(nexus)私有仓库
(site生命周期)mvn site
覆盖率测试和PMD测试,生成报告,生成站点
自定义拓展插件
可用自定义插件,需要在POM中写入(这里展示生成源码jar包插件
)
写入区域为<project>
内,格式:
<build>
<plugins>
<plugin>
<!--GAV坐标-->
<groupId>org. apache.maven.plugins</groupId>
<artifactId>maven-source-plugin</artifactId>
<version>2.2.1</version>
<!--执行内容-->
<executions>
<execution>
<!--执行目标-->
<goals>
<!--jar:对源码打包,test-jar:对测试代码打包-->
<goal>jar</goal>
</goals>
<!--执行阶段,可在前面图片内查看过程-->
<phase>generate-test-resources</phase>
</execution>
</executions>
</plugin>
</plugins>
</build>
写完后,点击install,即可发现有2个jar包,一个是发布的jar包,一个是源码jar包
当我们在这写入2个目标时,就会生成测试jar包和源码jar包了
分模块开发与设计思想
通常在中大型项目中需要解耦,因此将原有的单模块(dao,service,controller层统一由一个pom进行管理)全部拆分成独立的模块,方便团队协作开发
项目的大模块又称聚合模块
父模块pom编写
父模块作为所有项目的模块的祖宗模块,它需要统一管理版本
因此,pom中必须有版本管理配置
其中,<dependencyManagement>
中的 ${XXX.version}
对应的是上面<properties>
内的版本
请注意,<dependencyManagement>
是不会自动加载依赖的(懒加载),只有你在继承它的子模块中加入了相应的依赖,并且不填写版本,maven才会加载。
当然,如果你在子模块中写入了版本,maven则会以就近原则来选取子模块的版本
子模块可用加入父模块没有的依赖,作为自己需要的依赖
<properties>
<java.version>1.8</java.version>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
<project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>
<!--spring-->
<spring-boot.version>2.3.7.RELEASE</spring-boot.version>
<spring-cloud.version>Hoxton.SR9</spring-cloud.version>
<spring-boot.version>...</spring-boot.version>
</properties>
<dependencyManagement>
<dependencies>
<!--SpringCloud-->
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-dependencies</artifactId>
<version>${spring-cloud.version}</version>
<type>pom</type>
<scope>import</scope>
</dependency>
<!--SpringBoot-->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-dependencies</artifactId>
<version>${spring-boot.version}</version>
<type>pom</type>
<scope>import</scope>
</dependency>
<dependency>
GAV...
</dependency>
</dependencyManagement>
</dependencies>
子模块pom编写
所有的子模块都需要继承父模块parent进行统一的版本管理,格式为:
<parent>
<groupId>组织地址</groupId>
<artifactId>父模块名称</artifactId>
<version>0.0.1-SNAPSHOT</version>
<relativePath>../父模块名称</relativePath>
</parent>
聚合模块pom编写
聚合模块指定了内部的子模块,同时也是继承了父模块parent(也是parent的子模块),格式为
<parent>
<groupId>组织地址</groupId>
<artifactId>父模块名称</artifactId>
<version>0.0.1-SNAPSHOT</version>
<relativePath>../父模块名称</relativePath>
</parent>
<modules>
<module>控制层子模块名称</module>
<module>业务层子模块名称</module>
<module>模型层子模块名称</module>
</modules>
同时,需要加上<packaging>pom</packaging>
,因为这样使得maven辨别此为聚合模块,而不是一个把子模块全部混淆的jar包父模块pom与jar详解
聚合模块的子模块pom编写
聚合模块的子模块可以是各层拆分后得到的模块(dao,service,ctrler等)
因此,它需要指定父模块为聚合模块,路径不需要填写(填写正确也没啥事)
<parent>
<groupId>cn.emscc</groupId>
<artifactId>emscc-content</artifactId>
<version>0.0.1-SNAPSHOT</version>
<relativePath>../../emscc-content</relativePath>
</parent>
由于我们已经写好了一个base模块,供别的模块调用依赖,因此,我们调用一下base模块即可,然后再调用自己相调用的依赖
<!--emscc-base-->
<dependency>
<groupId>cn.emscc</groupId>
<artifactId>emscc-base</artifactId>
<version>0.0.1-SNAPSHOT</version>
</dependency>
版本冲突
如:A依赖了B的1.0,C依赖了B的2.0,导致B有2个版本
解决办法:
①使用<exclusions>
排除依赖
只使用B的1.0版本,那么在依赖C时排除对B的依赖
②使用<dependencyManagement>
锁定版本号
循环依赖
A模块要去依赖B模块的部分功能,B模块也要去依赖A模块的部分功能;
从而导致maven在打包时不知道先去打包哪个(由于maven打包是自下而上的打包方式)
解决办法:
①设置service与service impl包,将各个不同模块的互相引用分离开来,其它模块引用自己的接口,而自己的模块也引用其它模块的接口即可
②添加一个中间模块,让大家都去引用中间模块