SpringBoot2.x的依赖管理

主要梳理一下SpringBoot2.x的依赖关系和依赖的版本管理,依赖版本管理是开发和管理一个SpringBoot项目的前提。web

SpringBoot实际上是经过starter的形式,对spring-framework进行装箱,消除了(可是兼容和保留)原来的XML配置,目的是更加便捷地集成其余框架,打造一个完整高效的开发生态。redis

SpringBoot依赖关系

由于我的不太喜欢Gradle,因此下文都以Maven举例。spring

SpringCloud的版本(SpringCloud的正式版是用伦敦地铁站或者说伦敦某地名的英文名称做为版本号,例如比较经常使用的F版本Finchley就是位于伦敦北部芬奇利)管理不一样,SpringBoot的依赖组件发布版本格式是:X.Y.Z.RELEASE。由于SpringBoot组件通常会装箱为starter,因此组件的依赖GAV通常为:org.springframework.boot:spring-boot-starter-${组件名}:X.Y.Z.RELEASE,其中X是主版本,不一样的主版本意味着能够放弃兼容性,也就是SpringBoot1.xSpringBoot2.x不保证兼容性,而组件名通常是表明一类中间件或者一类功能,如data-redisspring-boot-starter-data-redis,提供Redis访问功能)、jdbcspring-boot-starter-jdbc,提供基于JDBC驱动访问数据库功能)等等。以SpringBoot当前最新的发布版本2.3.1.RELEASEorg.springframework.boot:spring-boot-starter:jar:2.3.1.RELEASE为例,用mvn dependency:tree分析它的依赖关系以下:数据库

 

img

 

这个依赖树也印证了starter是基于Spring项目装箱和扩展的。框架

SpringBoot依赖管理

若是使用Spring Initializr建立一个SpringBoot项目的话,那么会发现项目的POM文件中会加入了一个parent元素:elasticsearch

<parent>
     <groupId>org.springframework.boot</groupId>
     <artifactId>spring-boot-starter-parent</artifactId>
     <version>2.3.1.RELEASE</version>
     <relativePath/> <!-- lookup parent from repository -->
 </parent>

 

其实spring-boot-starter-parent至关于做为了当前项目的父模块,在父模块里面管理了当前指定的SpringBoot版本2.3.1.RELEASE全部依赖的第三方库的统一版本管理,经过spring-boot-starter-parent上溯到最顶层的项目,会找到一个properties元素,里面统一管理Spring框架和全部依赖到的第三方组件的统一版本号,这样就能确保对于一个肯定的SpringBoot版本,它引入的其余starter再也不须要指定版本,同时全部的第三方依赖的版本也是固定的。如项目的POM文件以下:ide

<!-- 暂时省略其余的配置属性 -->
 <parent>
     <groupId>org.springframework.boot</groupId>
     <artifactId>spring-boot-starter-parent</artifactId>
     <version>2.3.1.RELEASE</version>
     <relativePath/> <!-- lookup parent from repository -->
 </parent>
 <groupId>com.example</groupId>
 <artifactId>demo</artifactId>
 <version>0.0.1-SNAPSHOT</version>
 <name>demo</name>
 <dependencies>
     <dependency>
         <groupId>org.springframework.boot</groupId>
         <artifactId>spring-boot-starter</artifactId>
     </dependency>
     <dependency>
         <groupId>org.springframework.boot</groupId>
         <artifactId>spring-boot-starter-test</artifactId>
         <scope>test</scope>
         <exclusions>
             <exclusion>
                 <groupId>org.junit.vintage</groupId>
                 <artifactId>junit-vintage-engine</artifactId>
             </exclusion>
         </exclusions>
     </dependency>
 </dependencies>

 

这样只须要修改parent元素中的版本号,就能全局更变全部starter的版本号。这种作法其实本质上是把当前项目做为spring-boot-starter-parent的子项目,其实在必定程度上并不灵活。这里推荐使用另外一种方式:经过dependencyManagement元素全局管理SpringBoot版本,适用于单模块或者多模块的Maven项目。项目的(父)POM文件以下:spring-boot

 
<!-- spring-boot-guide 父POM -->
 <properties>
     <spring.boot.version>2.3.1.RELEASE</spring.boot.version>
 </properties>
 <dependencyManagement>
     <dependencies>
         <dependency>
             <groupId>org.springframework.boot</groupId>
             <artifactId>spring-boot-dependencies</artifactId>
             <version>${spring.boot.version}</version>
             <scope>import</scope>
             <type>pom</type>
         </dependency>
     </dependencies>
 </dependencyManagement>

 

而后须要用到其余starter的时候,只须要在dependencies直接引入便可,再也不须要指定版本号,版本号由dependencyManagement中定义的版本号统一管理。测试

<!-- spring-boot-guide/ch0-dependency 子POM -->
 <dependencies>
     <dependency>
         <groupId>org.springframework.boot</groupId>
         <artifactId>spring-boot-starter</artifactId>
     </dependency>
 </dependencies>

 

SpringBoot依赖覆盖

有些特殊的状况,可能项目中大部分的starter使用的是相对低的版本,可是因为部分新的功能须要使用到更高版本的个别starter,则须要强制引入该高版本的starter。这里举一个例子,项目用到的SpringBoot组件的版本是2.1.5.RELEASE,使用的中间件服务Elasticsearch的版本是7.x,而spring-boot-starter-data-elasticsearch支持的版本以下:ui

 

 

 

理论上能够一会儿升级SpringBoot2.3.1.RELEASE,其实也能够直接指定spring-boot-starter-data-elasticsearch的版本覆盖掉全局的SpringBoot组件版本,这里应用了Maven依赖调解原则

<!-- 父POM或者全局POM -->
 <properties>
     <spring.boot.version>2.1.5.RELEASE</spring.boot.version>
 </properties>
 <dependencyManagement>
     <dependencies>
         <dependency>
             <groupId>org.springframework.boot</groupId>
             <artifactId>spring-boot-dependencies</artifactId>
             <version>${spring.boot.version}</version>
             <scope>import</scope>
             <type>pom</type>
         </dependency>
     </dependencies>
 </dependencyManagement><dependencies>
     <dependency>
         <groupId>org.springframework.boot</groupId>
         <artifactId>spring-boot-starter-web</artifactId>
     </dependency>
     <dependency>
         <groupId>org.springframework.boot</groupId>
         <artifactId>spring-boot-starter-data-elasticsearch</artifactId>
         <version>2.3.1.RELEASE</version>
     </dependency>
 </dependencies>

 

这样就能单独提高spring-boot-starter-data-elasticsearch的版本为2.3.1.RELEASE,其余组件的版本依然保持为2.1.5.RELEASE

小结

目前有两种经常使用的方式管理SpringBoot组件的版本(两种方式二选一):

  1. 配置parent元素,经过项目继承的方式指定SpringBoot组件的版本号,这是Spring Initializr生成的项目中默认的配置方式。

  2. 配置dependencyManagement元素(推荐此方式),经过(父)POM文件统一指定SpringBoot组件的版本号。

另外,SpringBoot1.x2.x之间有兼容性问题(最明显的一点是2.x中删除了1.x中大量的内建类,若是用到了这些SpringBoot中的内建类,容易出现ClassNotFoundException),降级或者升级都有比较大的风险。通常状况下,建议使用同一个大版本进行项目开发,若是肯定须要进行大版本切换,请务必作完毕的功能测试。

相关文章
相关标签/搜索