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),降級或者升級都有比較大的風險。通常狀況下,建議使用同一個大版本進行項目開發,若是肯定須要進行大版本切換,請務必作完畢的功能測試。

相關文章
相關標籤/搜索