一.继承
1.目的:不同模块中经常需要用到同一个依赖,这样要在每个pom.xml中都引入对应的坐标,继承可以用来解决依赖引入重复的问题。
2.实现:我们可以在创建一个父工程,然后将多个模块来继承这个父工程。然后再将各个模块中都共有的依赖都提取到父工程中进行配置,只要子工程继承了父工程,依赖它也会继承下来,这样就无需在各个子工程中进行配置了。(其实就像aop,和注解提取一样,就是一种提取的思想,将子类共有的依赖提取到父类)
3.案例与具体操作:
【1】案例:有三个模块tlias-pojo,tlias-utils,tlias-web-mangement,他们都有一个相同的依赖--lombok,我们要将这个依赖提取到tlias-parent.
但是因为这是一个springboot项目,而所有的springboot项目都有一个统一的父工程,就是spring-boot-starter-parent。与java一样,Maven不支持多继承。那么怎么解决呢。
不支持多继承,但我们可以多重继承啊。
【2】具体操作
1.创建maven模块tlias-parent,该工程为父工程,在其pom.xml的packaging标签中设置打包方式为pom.
[注:Maven打包方式:
jar:普通模块打包,springboot项目基本都是jar包(内嵌tomcat运行)
war:普通web程序打包,需要部署在外部的tomcat服务器中运行
pom:父工程或聚合工程,该模块不写代码,仅进行依赖管理]
2.在子工程的pom.xml文件中,配置继承关系。例:
以 tlias-utils 为例,指定其父工程。其他的模块,都是相同的配置方式。
<parent>
<groupId>com.itheima</groupId>
<artifactId>tlias-parent</artifactId>
<version>1.0-SNAPSHOT</version>
<relativePath>../tlias-parent/pom.xml</relativePath>
</parent>
<artifactId>tlias-utils</artifactId>
<version>1.0-SNAPSHOT</version>
注意:(1)在子工程中,配置了继承关系后,groupId是可以省略的,因为会自动继承父工程。
(2)relativePath指定父工程的pom文件的相对位置,如果不指定,将从本地仓库/远程仓库查找该工程。
../代表的上一级目录。
【3】在父工程中配置各个工程共有依赖(子工程会自动继承一拉),然后我们就可以将子工程中的依赖配置和依赖文件删除了。
注:
*我们当前的目录结构:
*实际项目是先设计好模块之后在开始创建模块,开发项目,所以实际中的项目结构更加清晰:
二.版本锁定
1.场景
在开发中,还有一部分依赖,并不是各个模块都共有的,可能只有其中的一小部分模块中使用到了这个依赖。所以说还是有一部分依赖没有被提取,就是分散的。
如果依赖每次更换版本,我们都得找到这个项目中涉及到这个依赖的每一个模块,一个一个的更改,很容易出问题和遗漏。
这时我们就使用Maven的版本锁定功能来统一管理各个依赖的版本。
2.实现
可以在父工程的pom文件中通过<dependencyManagement>来统一管理依赖版本。
父工程:
<!--统一管理依赖版本-->
<dependencyManagement>
<dependencies>
<!--JWT令牌-->
<dependency>
<groupId>io.jsonwebtoken</groupId>
<artifactId>jjwt</artifactId>
<version>0.9.1</version>
</dependency>
</dependencies>
</dependencyManagement>
子工程:
<dependencies>
<!--JWT令牌-->
<dependency>
<groupId>io.jsonwebtoken</groupId>
<artifactId>jjwt</artifactId>
</dependency>
</dependencies>
面试题:<dependencyManagement> 与 <dependencies> 的区别是什么?
<dependencies> 是直接依赖,在父工程配置了依赖,子工程会直接继承下来。
<dependencyManagement> 是统一管理依赖版本,不会直接依赖,还是需要在子工程中引入所需依赖,
只是此时就无需指定<version>版本号了。
3.我们之所以之前在springboot项目中很多时候引入依赖坐标不需要写<version>,是因为在springboot自己继承的父工程spring-boot-starter-parent中已经通过<dependencyManagement>对依赖的版本进行统一管理。
4.我们也可以通过自定义属性及属性引用的形式,在父工程中将依赖的版本号进行进一步统一管理。
例1:
//自定义属性
<properties>
<lombok.version>1.18.24</lombok.version>
</properties>
//引用属性
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
<version>${lombok.version}</version>
</dependency>
例2:
<properties>
<maven.compiler.source>11</maven.compiler.source>
<maven.compiler.target>11</maven.compiler.target>
<lombok.version>1.18.24</lombok.version>
<jjwt.version>0.9.1</jjwt.version>
<aliyun.oss.version>3.15.1</aliyun.oss.version>
<jaxb.version>2.3.1</jaxb.version>
<activation.version>1.1.1</activation.version>
<jaxb.runtime.version>2.3.3</jaxb.runtime.version>
</properties>
<dependencies>
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
<version>${lombok.version}</version>
</dependency>
</dependencies>
<!--统一管理依赖版本-->
<dependencyManagement>
<dependencies>
<!--JWT令牌-->
<dependency>
<groupId>io.jsonwebtoken</groupId>
<artifactId>jjwt</artifactId>
<version>${jjwt.version}</version>
</dependency>
<!--阿里云OSS-->
<dependency>
<groupId>com.aliyun.oss</groupId>
<artifactId>aliyun-sdk-oss</artifactId>
<version>${aliyun.oss.version}</version>
</dependency>
<dependency>
<groupId>javax.xml.bind</groupId>
<artifactId>jaxb-api</artifactId>
<version>${jaxb.version}</version>
</dependency>
<dependency>
<groupId>javax.activation</groupId>
<artifactId>activation</artifactId>
<version>${activation.version}</version>
</dependency>
<!-- no more than 2.3.3-->
<dependency>
<groupId>org.glassfish.jaxb</groupId>
<artifactId>jaxb-runtime</artifactId>
<version>${jaxb.runtime.version}</version>
</dependency>
</dependencies>
</dependencyManagement>
这样就可以将版本号进一步移动到父工程的properties中。