建企業(yè)版網(wǎng)站多久白山seo
目錄
一、?配置優(yōu)先級
?編輯
二、Bean管理
???????2.1:獲取Bean
?編輯
???????2.2:Bean作用域
??????????????2.3:第三方Bean
三、Springboot底層原理
3.1:起步依賴
3.1.1:maven的依賴傳遞:
3.2:自動配置(重點(diǎn)):
3.2.1?概述:
3.2.2:常見方案
3.2.2.1:???????概述
3.2.2.2:??????????????方案一
???????3.2.2.3:方案二
3.2.3:原理分析
3.2.4:自動配置源碼小結(jié)
前言:
在當(dāng)今快節(jié)奏的開發(fā)時代,Spring Boot 作為一款極具影響力的框架,徹底改變了 Java 應(yīng)用的構(gòu)建方式。它憑借簡潔的配置、強(qiáng)大的功能,為開發(fā)者節(jié)省大量精力。然而,多數(shù)人忙于使用,對其底層原理卻一知半解。此刻,讓我們停下匆忙的腳步,一同深入這篇博客,去探究 Spring Boot 是如何施展魔法,從啟動初始化到運(yùn)行時的精妙管控,層層剖析,挖掘那些隱藏在便捷背后的技術(shù)奧秘。
1. 配置優(yōu)先級:Springboot項目當(dāng)中屬性配置的常見方式以及配置的優(yōu)先級
2. Bean的管理
3. 剖析Springboot的底層原理
一、?配置優(yōu)先級
在我們前面的課程當(dāng)中,我們已經(jīng)講解了SpringBoot項目當(dāng)中支持的三類配置文件:
application.properties
application.yml
application.yaml
? ? ? ?在SpringBoot項目當(dāng)中,我們要想配置一個屬性,可以通過這三種方式當(dāng)中的任意一種來配置都可以,那么如果項目中同時存在這三種配置文件,且都配置了同一個屬性,如:Tomcat端口號,到底哪一份配置文件生效呢?
server.port=8081
server:
port: 8082
server:port: 8082
我們啟動SpringBoot程序,測試下三個配置文件中哪個Tomcat端口號生效:
properties、yaml、yml三種配置文件,優(yōu)先級最高的是properties
配置文件優(yōu)先級排名(從高到低):
1. properties配置文件
2. yml配置文件
3. yaml配置文件
注意事項:雖然springboot支持多種格式配置文件,但是在項目開發(fā)時,推薦統(tǒng)一使用一種格式的配置。(yml是主流)
在SpringBoot項目當(dāng)中除了以上3種配置文件外,SpringBoot為了增強(qiáng)程序的擴(kuò)展性,除了支持配置
文件的配置方式以外,還支持另外兩種常見的配置方式:
1. Java系統(tǒng)屬性配置 (格式: -Dkey=value)
2. 命令行參數(shù) (格式:--key=value)
那在idea當(dāng)中運(yùn)行程序時,如何來指定Java系統(tǒng)屬性和命令行參數(shù)呢?
編輯啟動程序的配置信息
優(yōu)先級: 命令行參數(shù) > 系統(tǒng)屬性參數(shù) > properties參數(shù) > yml參數(shù) > yaml參數(shù)
思考:如果項目已經(jīng)打包上線了,這個時候我們又如何來設(shè)置Java系統(tǒng)屬性和命令行參數(shù)呢?
1 java -Dserver.port=9000 -jar XXXXX.jar --server.port=10010
下面我們來演示下打包程序運(yùn)行時指定Java系統(tǒng)屬性和命令行參數(shù):
- 執(zhí)行maven打包指令package,把項目打成jar文件
- 使用命令:java?-jar?方式運(yùn)行jar文件程序
運(yùn)行jar程序:
同時設(shè)置Java系統(tǒng)屬性和命令行參數(shù)
僅設(shè)置Java系統(tǒng)屬性
Springboot項目進(jìn)行打包時,需要引入插件 spring-boot-maven-plugin?(基于官網(wǎng)骨架創(chuàng)建項目,會自動添加該插件)
在SpringBoot項目當(dāng)中,常見的屬性配置方式有5種,??3種配置文件,加上2種外部屬性的配置(Java
系統(tǒng)屬性、命令行參數(shù))。通過以上的測試,我們也得出了優(yōu)先級(從低到高):
?application.yaml(忽略)?
?application.yml
?application.properties
?java系統(tǒng)屬性(-Dxxx=xxx)?
?命令行參數(shù)(--xxx=xxx)
二、Bean管理
? ? ? 在前面的課程當(dāng)中,我們已經(jīng)講過了我們可以通過Spring當(dāng)中提供的注解@Component以及它的三個衍生注解(@Controller、@Service、@Repository)來聲明IOC容器中的bean對象,同時我們也學(xué)習(xí)了如何為應(yīng)用程序注入運(yùn)行時所需要依賴的bean對象,也就是依賴注入DI。
我們今天主要學(xué)習(xí)IOC容器中Bean的其他使用細(xì)節(jié),主要學(xué)習(xí)以下三方面:
- 如何從IOC容器中手動的獲取到bean對象
- bean的作用域配置
- 管理第三方的bean對象
接下來我們先來學(xué)習(xí)第一方面,從IOC容器中獲取bean對象。
???????2.1:獲取Bean
默認(rèn)情況下,SpringBoot項目在啟動的時候會自動的創(chuàng)建IOC容器(也稱為Spring容器),并且在啟動的過程當(dāng)中會自動的將bean對象都創(chuàng)建好,存放在IOC容器當(dāng)中。應(yīng)用程序在運(yùn)行時需要依賴什么bean對象,就直接進(jìn)行依賴注入就可以了。
而在Spring容器中提供了一些方法,可以主動從IOC容器中獲取到bean對象,下面介紹3種常用方式:
? ?1、根據(jù)name獲取bean???????
1 Object?getBean(String?name)
- 根據(jù)類型獲取bean
1 <T> T getBean(Class<T> requiredType)
???????根據(jù)name獲取bean(帶類型轉(zhuǎn)換)
1 <T> T getBean(String name, Class<T> requiredType)
思考:要從IOC容器當(dāng)中來獲取到bean對象,需要先拿到IOC容器對象,怎么樣才能拿到IOC容器呢?
?想獲取到IOC容器,直接將IOC容器對象注入進(jìn)來就可以了
控制器:DeptController
業(yè)務(wù)實(shí)現(xiàn)類:DeptServiceImpl
Mapper接口:
測試類
???????2.2:Bean作用域
在前面我們提到的IOC容器當(dāng)中,默認(rèn)bean對象是單例模式(只有一個實(shí)例對象)。那么如何設(shè)置bean對象為非單例呢?需要設(shè)置bean的作用域。
在Spring中支持五種作用域,后三種在web環(huán)境才生效:
??????????????2.3:第三方Bean
學(xué)習(xí)完bean的獲取、bean的作用域之后,接下來我們再來學(xué)習(xí)第三方bean的配置。
之前我們所配置的bean,像controller、service,dao三層體系下編寫的類,這些類都是我們在項目當(dāng)中自己定義的類(自定義類)。當(dāng)我們要聲明這些bean,也非常簡單,我們只需要在類上加上 @Component以及它的這三個衍生注解(@Controller、@Service、@Repository),就可以來聲明這個bean對象了。
但是在我們項目開發(fā)當(dāng)中,還有一種情況就是這個類它不是我們自己編寫的,而是我們引入的第三方依賴當(dāng)中提供的。
在pom.xml文件中,引入dom4j:
三、Springboot底層原理
3.1:起步依賴

spring-webmvc依賴:這是Spring框架進(jìn)行web程序開發(fā)所需要的依賴
servlet-api依賴:Servlet基礎(chǔ)依賴
jackson-databind依賴:JSON處理工具包
如果要使用AOP,還需要引入aop依賴、aspect依賴
項目中所引入的這些依賴,還需要保證版本匹配,否則就可能會出現(xiàn)版本沖突問題。
如果我們使用了SpringBoot,就不需要像上面這么繁瑣的引入依賴了。我們只需要引入一個依賴就可以了,那就是web開發(fā)的起步依賴:springboot-starter-web。
3.1.1:maven的依賴傳遞:
假設(shè)a依賴了b,b依賴了c,c依賴了d,只需要引入a依賴,b,c,d依賴就都引入進(jìn)來了
為什么我們只需要引入一個web開發(fā)的起步依賴,web開發(fā)所需要的所有的依賴都有了呢?
因為Maven的依賴傳遞。
在SpringBoot給我們提供的這些起步依賴當(dāng)中,已提供了當(dāng)前程序開發(fā)所需要的所有的常
見依賴(官網(wǎng)地址:https://docs.spring.io/spring-boot/docs/2.7.7/referen
ce/htmlsingle/#using.build-systems.starters )。
比如:springboot-starter-web,這是web開發(fā)的起步依賴,在web開發(fā)的起步依賴當(dāng)
中,就集成了web開發(fā)中常見的依賴:json、web、webmvc、tomcat等。我們只需要引入
這一個起步依賴,其他的依賴都會自動的通過Maven的依賴傳遞進(jìn)來。
結(jié)論:起步依賴的原理就是Maven的依賴傳遞。
3.2:自動配置(重點(diǎn)):
springboot原理就是自動配置的原理
3.2.1?概述:
SpringBoot的自動配置就是當(dāng)Spring容器啟動后,一些配置類、bean對象就自動存入到了IOC容器
中,不需要我們手動去聲明,從而簡化了開發(fā),省去了繁瑣的配置操作。
比如:我們要進(jìn)行事務(wù)管理、要進(jìn)行AOP 程序的開發(fā),此時就不需要我們再去手動的聲明這些bean對象了,我們直接使用就可以從而大大的簡化程序的開發(fā),省去了繁瑣的配置操作。
下面我們打開idea,一起來看下自動配置的效果:
運(yùn)行SpringBoot啟動類:

我們會發(fā)現(xiàn),出現(xiàn)了很多沒有見過的bean對象,也被加載進(jìn)來了,這些就是springboot的自動配置的bean對象。
? ? ??大家會看到有兩個CommonConfig,在第一個CommonConfig類中定義了一個bean對象,bean對象的名字叫reader。
? ? ? 在第二個CommonConfig中它的bean名字叫commonConfig,為什么還會有這樣一個bean對象呢?原因是在CommonConfig配置類上添加了一個注解@Configuration,而@Configuration底層就是@Component
所以配置類最終也是SpringIOC容器當(dāng)中的一個bean對象
在IOC容器中除了我們自己定義的bean以外,還有很多配置類,這些配置類都是SpringBoot在啟動的時候加載進(jìn)來的配置類。這些配置類加載進(jìn)來之后,它也會生成很多的bean對象。
比如:配置類GsonAutoConfiguration里面有一個bean,bean的名字叫gson,它的類型是
Gson。
com.google.gson.Gson是谷歌包中提供的用來處理JSON格式數(shù)據(jù)的
?
3.2.2:常見方案
3.2.2.1:???????概述
? ? ? ?我們知道了什么是自動配置之后,接下來我們就要來剖析自動配置的原理。解析自動配置的原理就是分析在???SpringBoot項目當(dāng)中,我們引入對應(yīng)的依賴之后,是如何將依賴jar包當(dāng)中所提供的bean以及配置類直接加載到當(dāng)前項目的SpringIOC容器當(dāng)中的。
接下來,我們就直接通過代碼來分析自動配置原理。
???????準(zhǔn)備工作:在Idea中導(dǎo)入"資料\03.??自動配置原理"下的itheima-utils工程
1、在SpringBoot項目 ?spring-boot-web-config2?工程中,通過坐標(biāo)引入itheima-utils依賴

2、在測試類中,添加測試方法
3、執(zhí)行測試方法
異常信息描述: ?沒有com.example.TokenParse類型的bean
說明:在Spring容器中沒有找到com.example.TokenParse類型的bean對象
思考:引入進(jìn)來的第三方依賴當(dāng)中的bean以及配置類為什么沒有生效?
原因在我們之前講解IOC的時候有提到過,在類上添加@Component注解來聲明bean對象時,還需要保證@Component注解能被Spring的組件掃描到。
SpringBoot項目中的@SpringBootApplication注解,具有包掃描的作用,但是它只會掃描啟動類所在的當(dāng)前包以及子包。
??當(dāng)前包:com.itheima,?第三方依賴中提供的包:com.example(掃描不到)
那么如何解決以上問題的呢?
方案1:@ComponentScan?組件掃描
方案2:@Import?導(dǎo)入(使用@Import導(dǎo)入的類會被Spring加載到IOC容器中)
3.2.2.2:??????????????方案一
@ComponentScan組件掃描
重新執(zhí)行測試方法,控制臺日志輸出:

???????3.2.2.3:方案二
@Import導(dǎo)入
?導(dǎo)入形式主要有以下幾種:
- 導(dǎo)入普通類
- 導(dǎo)入ImportSelector接口實(shí)現(xiàn)類
- 導(dǎo)入配置類?
? 1、導(dǎo)入普通類???????
2、使用@Import導(dǎo)入配置類:
配置類
3、使用@Import導(dǎo)入ImportSelector接口實(shí)現(xiàn)類:
ImportSelector接口實(shí)現(xiàn)類
我們使用@Import注解通過這三種方式都可以導(dǎo)入第三方依賴中所提供的bean或者是配置類。
思考:如果基于以上方式完成自動配置,當(dāng)要引入一個第三方依賴時,是不是還要知道第三方依賴中有哪些配置類和哪些Bean對象?
??答案:是的。?(對程序員來講,很不友好,而且比較繁瑣)
思考:當(dāng)我們要使用第三方依賴,依賴中到底有哪些bean和配置類,誰最清楚?
答案:第三方依賴自身最清楚。
怎么讓第三方依賴自己指定bean對象和配置類?
??比較常見的方案就是第三方依賴給我們提供一個注解,這個注解一般都以@EnableXxxx開頭的注解,注解中封裝的就是@Import注解
使用第三方依賴提供的 ?@EnableXxxxx注解
第三方依賴中提供的注解
在使用時只需在啟動類上加上@EnableXxxxx注解即可
以上四種方式都可以完成導(dǎo)入操作,但是第4種方式會更方便更優(yōu)雅,而這種方式也是SpringBoot當(dāng)中所采用的方式。
3.2.3:原理分析
源碼跟蹤
? ? ? 前面我們講解了在項目當(dāng)中引入第三方依賴之后,如何加載第三方依賴中定義好的bean對象以及配置類,從而完成自動配置操作。那下面我們通過源碼跟蹤的形式來剖析下SpringBoot底層到底是如何完成自動配置的。
源碼跟蹤技巧:
在跟蹤框架源碼的時候,一定要抓住關(guān)鍵點(diǎn),找到核心流程。一定不要從頭到尾一行代碼去看,一個方法的去研究,一定要找到關(guān)鍵流程,抓住關(guān)鍵點(diǎn),先在宏觀上對整個流程或者整個原理有一個認(rèn)識,有精力再去研究其中的細(xì)節(jié)。
要搞清楚SpringBoot的自動配置原理,要從SpringBoot啟動類上使用的核心注解
@SpringBootApplication開始分析:
ConpoentScan 翻譯:組件掃描
Configuration:配置
在@SpringBootApplication注解中包含了:
?元注解(不再解釋)
?@SpringBootConfiguration?
?@EnableAutoConfiguration?
?@ComponentScan
我們先來看第一個注解:@SpringBootConfiguration
@SpringBootConfiguration注解上使用了@Configuration,表明SpringBoot啟動類就是一個配置類。
@Indexed注解,是用來加速應(yīng)用啟動的(不用關(guān)心)。
?接下來再先看@ComponentScan注解:
@ComponentScan注解是用來進(jìn)行組件掃描的,掃描啟動類所在的包及其子包下所有被?@Component及其衍生注解聲明的類。
SpringBoot啟動類,之所以具備掃描包功能,就是因為包含了@ComponentScan注解。
?最后我們來看看@EnableAutoConfiguration注解(自動配置核心注解):
使用@Import注解,導(dǎo)入了實(shí)現(xiàn)ImportSelector接口的實(shí)現(xiàn)類。
AutoConfigurationImportSelector類是ImportSelector接口的實(shí)現(xiàn)類。
AutoConfigurationImportSelector類中重寫了ImportSelector接口的selectImports()方法:
selectImports()方法底層調(diào)用getAutoConfigurationEntry()方法,獲取可自動配置的配置類信息集合?
getAutoConfigurationEntry()方法通過調(diào)用 getCandidateConfigurations(annotationMetadata,?attributes)方法獲取在配置文件中配置的所有自動配置類的集合
getCandidateConfigurations方法的功能:
獲取所有基于META- INF/spring/org.springframework.boot.autoconfigure.AutoConfiguration.imp?orts文件、META-INF/spring.factories文件中配置類的集合
META-
INF/spring/org.springframework.boot.autoconfigure.AutoConfiguration.imports
文件和META-INF/spring.factories文件這兩個文件在哪里呢?
?通常在引入的起步依賴中,都有包含以上兩個文件
在前面在給大家演示自動配置的時候,我們直接在測試類當(dāng)中注入了一個叫gson的bean對象,進(jìn)行 JSON格式轉(zhuǎn)換。雖然我們沒有配置bean對象,但是我們是可以直接注入使用的。原因就是因為在自動配置類當(dāng)中做了自動配置。到底是在哪個自動配置類當(dāng)中做的自動配置呢?我們通過搜索來查詢一下。
在META-
INF/spring/org.springframework.boot.autoconfigure.AutoConfiguration.imports
配置文件中指定了第三方依賴Gson的配置類:GsonAutoConfiguration
第三方依賴中提供的GsonAutoConfiguration類:
在GsonAutoConfiguration類上,添加了注解@AutoConfiguration,通過查看源碼,可以明確:GsonAutoConfiguration類是一個配置。
看到這里,大家就應(yīng)該明白為什么可以完成自動配置了,原理就是在配置類中定義一個@Bean標(biāo)識的方法,而Spring會自動調(diào)用配置類中使用@Bean標(biāo)識的方法,并把方法的返回值注冊到IOC容器中。
3.2.4:自動配置源碼小結(jié)
自動配置原理源碼入口就是@SpringBootApplication注解,在這個注解中封裝了3個注解,分別是:
@SpringBootConfiguration? | 聲明當(dāng)前類是一個配置類 |
@ComponentScan? | ?進(jìn)行組件掃描(SpringBoot中默認(rèn)掃描的是啟動類所在的當(dāng)前 |
@EnableAutoConfiguration? ? | ?封裝了@Import注解(Import注解中指定了一個ImportSelector接口的實(shí)現(xiàn)類) |
?在實(shí)現(xiàn)類重寫的selectImports()方法,讀取當(dāng)前項目下所有依賴jar包中META- INF/spring.factories、META-
INF/spring/org.springframework.boot.autoconfigure.AutoConfigurat?ion.imports兩個文件里面定義的配置類(配置類中定義了@Bean注解標(biāo)識的方法)。
當(dāng)SpringBoot程序啟動時,就會加載配置文件當(dāng)中所定義的配置類,并將這些配置類信息(類的全限定名)封裝到String類型的數(shù)組中,最終通過@Import注解將這些配置類全部加載到Spring的IOC容器中,交給IOC容器管理。
最后呢給大家拋出一個問題:在META- INF/spring/org.springframework.boot.autoconfigure.AutoConfiguration.imp orts文件中定義的配置類非常多,而且每個配置類中又可以定義很多的bean,那這些bean都會注冊到Spring的IOC容器中嗎?
答案:并不是。???在聲明bean對象時,上面有加一個以@Conditional開頭的注解,這種注解的作用就是按照條件進(jìn)行裝配,只有滿足條件之后,才會將bean注冊到Spring的IOC容器中(下面會詳細(xì)來講解)
@Conditional
? ? ?我們在跟蹤SpringBoot自動配置的源碼的時候,在自動配置類聲明bean的時候,除了在方法上加了一個@Bean注解以外,還會經(jīng)常用到一個注解,就是以Conditional開頭的這一類的注解。以 Conditional開頭的這些注解都是條件裝配的注解。下面我們就來介紹下條件裝配注解。
@Conditional注解:
作用:按照一定的條件進(jìn)行判斷,在滿足給定條件后才會注冊對應(yīng)的bean對象到Spring的IOC容器中。
位置:方法、類
?@Conditional本身是一個父注解,派生出大量的子注解:
?@ConditionalOnClass:判斷環(huán)境中有對應(yīng)字節(jié)碼文件,才注冊bean到IOC容器。
?@ConditionalOnMissingBean:判斷環(huán)境中沒有對應(yīng)的bean(類型或名稱),才注冊 bean到? ? ? IOC容器。
?@ConditionalOnProperty:判斷配置文件中有對應(yīng)屬性和值,才注冊bean到IOC容器。
下面我們通過代碼來演示下Conditional注解的使用:
@ConditionalOnClass注解
測試類:
? ?
@ConditionalOnMissingBean注解
再次修改@ConditionalOnMissingBean注解:
再次修改@ConditionalOnMissingBean注解:
@ConditionalOnProperty注解(這個注解和配置文件當(dāng)中配置的屬性有關(guān)系)
先在application.yml配置文件中添加如下的鍵值對:
修改@ConditionalOnProperty注解: havingValue的值修改為"itheima2"
我們再回頭看看之前講解SpringBoot源碼時提到的一個配置類:GsonAutoConfiguration
最后再給大家梳理一下自動配置原理:
自動配置的核心就在@SpringBootApplication注解上,SpringBootApplication這個注解底層包含了3個注解,分別是:
@SpringBootConfiguration?
@ComponentScan? ?
@EnableAutoConfiguration
? ? ?@EnableAutoConfiguration這個注解才是自動配置的核心。
它封裝了一個@Import注解,Import注解里面指定了一個ImportSelector接口的實(shí)現(xiàn)類。
在這個實(shí)現(xiàn)類中,重寫了ImportSelector接口中的selectImports()方法。
而selectImports()方法中會去讀取兩份配置文件,并將配置文件中定義的配置類做為 selectImports()方法的返回值返回,返回值代表的就是需要將哪些類交給Spring的IOC容器進(jìn)行管理。
? ? ?那么所有自動配置類的中聲明的bean都會加載到Spring的IOC容器中嗎??其實(shí)并不會,因為這些配置類中在聲明bean時,通常都會添加@Conditional開頭的注解,這個注解就是進(jìn)行條件裝配。而Spring會根據(jù)Conditional注解有選擇性的進(jìn)行bean的創(chuàng)建。
@Enable 開頭的注解底層,它就封裝了一個注解 import 注解,它里面指定了一個類,是?ImportSelector?接口的實(shí)現(xiàn)類。在實(shí)現(xiàn)類當(dāng)中,我們需要去實(shí)現(xiàn) ?ImportSelector?接口當(dāng)中的一個方法 ?selectImports?這個方法。這個方法的返回值代表的就是我需要將哪些類交給 spring 的 IOC容器進(jìn)行管理。
? ? ?此時它會去讀取兩份配置文件,一份兒是?spring.factories,另外一份兒是 autoConfiguration.imports。而在 autoConfiguration.imports 這份兒文件當(dāng)中,它就會去配置大量的自動配置的類。
? ? ?而前面我們也提到過這些所有的自動配置類當(dāng)中,所有的??bean都會加載到??spring?的 IOC?容器當(dāng)中嗎?其實(shí)并不會,因為這些配置類當(dāng)中,在聲明??bean?的時候,通常會加上這么一類@Conditional?開頭的注解。這個注解就是進(jìn)行條件裝配。所以SpringBoot非常的智能,它會根據(jù)??@Conditional?注解來進(jìn)行條件裝配。只有條件成立,它才會聲明這個bean,才會將這個??bean?交給??IOC?容器管理。
3.2.4:案例
3.2.4.1:自定義starter分析
前面我們解析了SpringBoot中自動配置的原理,下面我們就通過一個自定義starter案例來加深大家對于自動配置原理的理解。首先介紹一下自定義starter的業(yè)務(wù)場景,再來分析一下具體的操作步驟。
所謂starter指的就是SpringBoot當(dāng)中的起步依賴。在SpringBoot當(dāng)中已經(jīng)給我們提供了很多的起步依賴了,我們?yōu)槭裁催€需要自定義???starter?起步依賴?這是因為在實(shí)際的項目開發(fā)當(dāng)中,我們可能會用到很多第三方的技術(shù),并不是所有的第三方的技術(shù)官方都給我們提供了與SpringBoot整合的 starter起步依賴,但是這些技術(shù)又非常的通用,在很多項目組當(dāng)中都在使用。
業(yè)務(wù)場景:
???我們前面案例當(dāng)中所使用的阿里云OSS對象存儲服務(wù),現(xiàn)在阿里云的官方是沒有給我們提供對應(yīng)的起步依賴的,這個時候使用起來就會比較繁瑣,我們需要引入對應(yīng)的依賴。我們還需要在配置文件當(dāng)中進(jìn)行配置,還需要基于官方SDK示例來改造對應(yīng)的工具類,我們在項目當(dāng)中才可以進(jìn)行使用。
???大家想在我們當(dāng)前項目當(dāng)中使用了阿里云OSS,我們需要進(jìn)行這么多步的操作。在別的項目組當(dāng)中要想使用阿里云OSS,是不是也需要進(jìn)行這么多步的操作,所以這個時候我們就可以自定義一些公共組件,在這些公共組件當(dāng)中,我就可以提前把需要配置的bean都提前配置好。將來在項目當(dāng)
中,我要想使用這個技術(shù),我直接將組件對應(yīng)的坐標(biāo)直接引入進(jìn)來,就已經(jīng)自動配置好了,就可以直接使用了。我們也可以把公共組件提供給別的項目組進(jìn)行使用,這樣就可以大大的簡化我們的開發(fā)。
在SpringBoot項目中,一般都會將這些公共組件封裝為SpringBoot當(dāng)中的starter,也就是我們所說的起步依賴。
?SpringBoot官方starter命名: ?spring-boot-starter-xxxx
第三組織提供的starter命名: xxxx-spring-boot-starter
Mybatis提供了配置類,并且也提供了springboot會自動讀取的配置文件。當(dāng)SpringBoot項目啟動時,會讀取到spring.factories配置文件中的配置類并加載配置類,生成相關(guān)bean對象注冊到IOC容器中。
結(jié)果:我們可以直接在SpringBoot程序中使用Mybatis自動配置的bean對象。
在自定義一個起步依賴starter的時候,按照規(guī)范需要定義兩個模塊:
starter模塊(進(jìn)行依賴管理[把程序開發(fā)所需要的依賴都定義在starter起步依賴中)
???????autoconfigure模塊(自動配置)
將來在項目當(dāng)中進(jìn)行相關(guān)功能開發(fā)時,只需要引入一個起步依賴就可以了,因為它會將
autoconfigure自動配置的依賴給傳遞下來。
上面我們簡單介紹了自定義starter的場景,以及自定義starter時涉及到的模塊之后,接下來我們就來完成一個自定義starter的案例。
需求:自定義aliyun-oss-spring-boot-starter,完成阿里云OSS操作工具類AliyunOSSUtils的自動配置。
目標(biāo):引入起步依賴引入之后,要想使用阿里云OSS,注入AliyunOSSUtils直接使用即可。
之前阿里云OSS的使用:
配置文件
當(dāng)我們在項目當(dāng)中要使用阿里云OSS,就可以注入AliOSSUtils工具類來進(jìn)行文件上傳。但這種方式其實(shí)是比較繁瑣的。
大家再思考,現(xiàn)在我們使用阿里云OSS,需要做這么幾步,將來大家在開發(fā)其他的項目的時候,你使用阿里云OSS,這幾步你要不要做?當(dāng)團(tuán)隊中其他小伙伴也在使用阿里云OSS的時候,步驟???不也是一樣的。
所以這個時候我們就可以制作一個公共組件(自定義starter)。starter定義好之后,將來要使用阿里云OSS進(jìn)行文件上傳,只需要將起步依賴引入進(jìn)來之后,就可以直接注入AliOSSUtils使用了。
需求明確了,接下來我們再來分析一下具體的實(shí)現(xiàn)步驟:
?第1步:創(chuàng)建自定義starter模塊(進(jìn)行依賴管理)?
?把阿里云OSS所有的依賴統(tǒng)一管理起來
?第2步:創(chuàng)建autoconfigure模塊
??在starter中引入autoconfigure?(我們使用時只需要引入starter起步依賴即可)?
?第3步:在autoconfigure中完成自動配置
- 定義一個自動配置類,在自動配置類中將所要配置的bean都提前配置好
- 定義配置文件,把自動配置類的全類名定義在配置文件中
我們分析完自定義阿里云OSS自動配置的操作步驟了,下面我們就按照分析的步驟來實(shí)現(xiàn)自定義
starter。
-
-
-
- 自定義starter實(shí)現(xiàn)
-
-
自定義starter的步驟我們剛才已經(jīng)分析了,接下來我們就按照分析的步驟來完成自定義starter的開發(fā)。
首先我們先來創(chuàng)建兩個Maven模塊:
- aliyun-oss-spring-boot-starter模塊
?
創(chuàng)建完starter模塊后,刪除多余的文件,最終保留內(nèi)容如下:
?
?刪除pom.xml文件中多余的內(nèi)容后:
- aliyun-oss-spring-boot-autoconfigure模塊???????
?
創(chuàng)建完starter模塊后,刪除多余的文件,最終保留內(nèi)容如下:
?刪除pom.xml文件中多余的內(nèi)容后:
按照我們之前的分析,是需要在starter模塊中來引入autoconfigure這個模塊的。打開starter模塊中的pom文件:?
在autoconfigure模塊當(dāng)中來完成自動配置操作。
我們將之前案例中所使用的阿里云OSS部分的代碼直接拷貝到autoconfigure模塊下,然后進(jìn)行改造就行了。?
?
拷貝過來后,還缺失一些相關(guān)的依賴,需要把相關(guān)依賴也拷貝過來:
?
現(xiàn)在大家思考下,在類上添加的@Component注解還有用嗎?
答案:沒用了。 在SpringBoot項目中,并不會去掃描com.aliyun.oss這個包,不掃描這個包那類上的注解也就失去了作用。
下面我們就要定義一個自動配置類了,在自動配置類當(dāng)中來聲明AliOSSUtils的bean對象。
?AliOSSAutoConfiguration類:
AliOSSProperties類:
?
AliOSSUtils類:
?
?
在aliyun-oss-spring-boot-autoconfigure模塊中的resources下,新建自動配置文件:
META-
INF/spring/org.springframework.boot.autoconfigure.AutoConfiguration.impo?rts
?1 com.aliyun.oss.AliOSSAutoConfiguration
?
-
-
-
- 自定義starter測試
-
-
阿里云OSS的starter我們剛才已經(jīng)定義好了,接下來我們就來做一個測試。
今天的課程資料當(dāng)中,提供了一個自定義starter的測試工程。我們直接打開文件夾,里面有一個測試工程。測試工程就是springboot-autoconfiguration-test,我們只需要將測試工程直接導(dǎo)入到Idea當(dāng)中即可。
?
測試前準(zhǔn)備:
???????在test工程中引入阿里云starter依賴
通過依賴傳遞,會把autoconfigure依賴也引入了
???????在test工程中的application.yml文件中,配置阿里云OSS配置參數(shù)信息(從以前的工程中拷貝即可)
- 在test工程中的UploadController類編寫代碼
編寫完代碼后,我們啟動當(dāng)前的SpringBoot測試工程:
??隨著SpringBoot項目啟動,自動配置會把AliOSSUtils的bean對象裝配到IOC容器中
?用postman工具進(jìn)行文件上傳:
?通過斷點(diǎn)可以看到自動注入AliOSSUtils的bean對象:
?
???????4.Web后端開發(fā)總結(jié)
到此基于SpringBoot進(jìn)行web后端開發(fā)的相關(guān)知識我們已經(jīng)學(xué)習(xí)完畢了。下面我們一起針對這段web課程做一個總結(jié)。
我們來回顧一下關(guān)于web后端開發(fā),我們都學(xué)習(xí)了哪些內(nèi)容,以及每一塊知識,具體是屬于哪個框架的。
web后端開發(fā)現(xiàn)在基本上都是基于標(biāo)準(zhǔn)的三層架構(gòu)進(jìn)行開發(fā)的,在三層架構(gòu)當(dāng)中,Controller控制器層負(fù)責(zé)接收請求響應(yīng)數(shù)據(jù),Service業(yè)務(wù)層負(fù)責(zé)具體的業(yè)務(wù)邏輯處理,而Dao數(shù)據(jù)訪問層也叫持久層,就是用來處理數(shù)據(jù)訪問操作的,來完成數(shù)據(jù)庫當(dāng)中數(shù)據(jù)的增刪改查操作。
在三層架構(gòu)當(dāng)中,前端發(fā)起請求首先會到達(dá)Controller(不進(jìn)行邏輯處理),然后Controller會直接調(diào)用Service?進(jìn)行邏輯處理,???Service再調(diào)用Dao完成數(shù)據(jù)訪問操作。
如果我們在執(zhí)行具體的業(yè)務(wù)處理之前,需要去做一些通用的業(yè)務(wù)處理,比如:我們要進(jìn)行統(tǒng)一的登錄校驗,我們要進(jìn)行統(tǒng)一的字符編碼等這些操作時,我們就可以借助于Javaweb當(dāng)中三大組件之一的過濾器?Filter或者是Spring當(dāng)中提供的攔截器Interceptor來實(shí)現(xiàn)。
而為了實(shí)現(xiàn)三層架構(gòu)層與層之間的解耦,我們學(xué)習(xí)了Spring框架當(dāng)中的第一大核心:IOC控制反轉(zhuǎn)與DI依賴注入。
所謂控制反轉(zhuǎn),指的是將對象創(chuàng)建的控制權(quán)由應(yīng)用程序自身交給外部容器,這個容器就是我們常說的IOC容器或Spring容器。
而DI依賴注入指的是容器為程序提供運(yùn)行時所需要的資源。
除了IOC與DI我們還講到了AOP面向切面編程,還有Spring中的事務(wù)管理、全局異常處理器,以及傳遞會話技術(shù)Cookie、Session以及新的會話跟蹤解決方案JWT令牌,阿里云OSS對象存儲服務(wù),以及通過?Mybatis持久層架構(gòu)操作數(shù)據(jù)庫等技術(shù)。
?我們在學(xué)習(xí)這些web后端開發(fā)技術(shù)的時候,我們都是基于主流的SpringBoot進(jìn)行整合使用的。而 SpringBoot又是用來簡化開發(fā),提高開發(fā)效率的。像過濾器、攔截器、IOC、DI、AOP、事務(wù)管理等這些技術(shù)到底是哪個框架提供的核心功能?
Filter過濾器、Cookie、 Session這些都是傳統(tǒng)的JavaWeb提供的技術(shù)。 JWT令牌、阿里云OSS對象存儲服務(wù),是現(xiàn)在企業(yè)項目中常見的一些解決方案。
IOC控制反轉(zhuǎn)、DI依賴注入、AOP面向切面編程、事務(wù)管理、全局異常處理、攔截器等,這些技術(shù)
都是 Spring Framework框架當(dāng)中提供的核心功能。 Mybatis就是一個持久層的框架,是用來操作數(shù)據(jù)庫的。
在Spring框架的生態(tài)中,對web程序開發(fā)提供了很好的支持,如:全局異常處理器、攔截器這些都是Spring框架中web開發(fā)模塊所提供的功能,而Spring框架的web開發(fā)模塊,我們也稱為:SpringMVC
?SpringMVC不是一個單獨(dú)的框架,它是Spring框架的一部分,是Spring框架中的web開發(fā)模塊,是用來簡化原始的Servlet程序開發(fā)的。
外界俗稱的SSM,就是由:SpringMVC、Spring??Framework、Mybatis三塊組成。
基于傳統(tǒng)的SSM框架進(jìn)行整合開發(fā)項目會比較繁瑣,而且效率也比較低,所以在現(xiàn)在的企業(yè)項目開發(fā)當(dāng)中,基本上都是直接基于SpringBoot整合SSM進(jìn)行項目開發(fā)的。
???????
?結(jié)尾:
至此,我們已沿著 Spring Boot 的原理脈絡(luò)游歷一番,從依賴注入的巧思,到自動化配置的便捷,再到內(nèi)嵌服務(wù)器的高效整合,無一不讓人折服。希望這篇博客不僅為你答疑解惑,更如同一束光,照亮你后續(xù)深入學(xué)習(xí)、優(yōu)化項目乃至自主創(chuàng)新的技術(shù)之路,愿你在編程的浩瀚星空中持續(xù)閃耀。