<em>Mac</em>Book项目 2009年学校开始实施<em>Mac</em>Book项目,所有师生配备一本<em>Mac</em>Book,并同步更新了校园无线网络。学校每周进行电脑技术更新,每月发送技术支持资料,极大改变了教学及学习方式。因此2011
2021-06-01 09:32:01
之前為什麼會去了解一些底層註解,其實就是為了後續更好的瞭解 springboot 底層的一些原理,比如自動設定原理。
從 MainApplication 中的@SpringBootApplication開始。
進入@SpringBootApplication,可以看到這是一個合成註解(紅框中是要關注的)。
這個註解幹嘛的?
直接點進去,發現有一個@Configuration註解,那這不就是個設定類嘛。
進而也說明了,MainApplication 也是一個設定類。
這個已經很熟悉了,可以指定掃描哪些 Spring 註解。
只不過這裡,加了一些其他的過濾條件,暫時不關注。
這個是最重要的註解了,聽名字就不一般,開啟自動設定。
點進去,發現也是一個合成註解(紅框需要關注)。
(1)@AutoConfigurationPackage
聽名字像是自動設定包?依舊點進去。
可以看到原來是匯入了一個叫Registrar的元件,繼續點進 Registrar。
這裡是利用Registrar()給容器中匯入一系列元件,也就是批次註冊元件。
在這裡打個斷點,debug 啟動一下。
registerBeanDefinitions()方法中有個傳參:
metadata,是註解的元資訊,可以看到這個註解是被標註在com.pingguo.boot.MainApplication。
而在registerBeanDefinitions()方法體內,new 了一個AutoConfigurationPackages.PackageImports(),裡面傳入的是元註解,通過getPackageNames()獲取到包名。
AutoConfigurationPackages.register( registry, (String[])(new AutoConfigurationPackages.PackageImports(metadata)).getPackageNames().toArray(new String[0]) );
在 idea 中可以單獨執行下片段程式碼
(new AutoConfigurationPackages.PackageImports(metadata)).getPackageNames()。
選中右擊,再點選 Evaluate。
得到的結果就是com.pingguo.boot。為什麼是這個?因為註解標註在MainApplication類,而這個類就屬於com.pingguo.boot。
拿到包名之後,封裝到陣列裡,也就是上述程式碼片段中的toArray(new String[0]),最後註冊進去。
所以,這裡的Registrar()就是把指定的包下的所有元件批次註冊到容器中。
(2)@Import(AutoConfigurationImportSelector.class)
上面指定好預設包規則之後,就需要去匯入需要的包了,利用的是AutoConfigurationImportSelector,繼續點進去看。
這裡有個selectImports方法,這個方法決定了要具體匯入哪些,返回的是一個陣列。
方法體內,又是呼叫了getAutoConfigurationEntry()方法來獲取設定入口,進而再通過getConfigurations()方法獲取具體設定,最終轉成陣列返回。
顯然getAutoConfigurationEntry()是個重點。
往下翻一點,就是getAutoConfigurationEntry()的實現,在這裡打個斷點(把上面的斷點取消掉)。
debug重新執行一下,往下走到getCandidateConfigurations()。
這裡是獲取所有候選設定,目前可以看到這裡是共有 127 個。
為什麼是這 127 個?其實是在組態檔裡寫死了,在 springboot 啟動時候,給容器載入的所有場景的設定類。
定義的位置是在這:spring-boot-autoconfigure2.3.4.RELEASEspring-boot-autoconfigure-2.3.4.RELEASE.jar!META-INFspring.factories
雖然這些一股腦的在啟動時候會去載入到容器,但是最終會按需開啟設定。
比如點開aop,看到@ConditionalOnClass({Advice.class})這個條件,是當存在Advice類時候才匯入元件,但實際上這裡並沒有Advice。
這就是基於 springboot 的按條件裝配@Conditional,根據規則最終實現按需裝配。
分別用最終未生效、和生效的自動設定來加深理解。
比如 cache。
可以看到CacheAutoConfiguration上是加了幾個條件裝配的。
(1)@ConditionalOnClass({CacheManager.class})
在 idea 中使用ctrl+N搜尋一下CacheManager,發現是存在的,那麼這個條件滿足。
(2)@ConditionalOnBean({CacheAspectSupport.class})
這個條件是要求容器中存在CacheAspectSupport這個元件才可以。
現在來判斷一下是否存在這個元件,在 main 方法裡增加測試程式碼:
... ... String[] beanNamesForType = run.getBeanNamesForType(CacheAspectSupport.class); System.out.println("==CacheAspectSupport型別元件的數量==" + beanNamesForType.length); ... ...
執行檢視輸出。
發現數量等於 0,也就是不存在該型別的元件。
也就是說@ConditionalOnBean({CacheAspectSupport.class})這個條件不滿足,所以整個類CacheAutoConfiguration裡的設定都不生效。
之前寫過 web 的demo,那麼 web 相關的設定自然是生效的,找到它。
這裡有不少字尾是**AutoConfiguration的設定,直接來看DispatcherServletAutoConfiguration。
還有 2 個註解直接沒見過,這裡不用太多關注,瞭解一下:
所以,類上的幾個條件都是滿足的,就可以進一步到類中了,繼續往下找:
看到DispatcherServletConfiguration類上也有條件:
@Conditional({DispatcherServletAutoConfiguration.DefaultDispatcherServletCondition.class}):
別看這麼長,其實就是上面的一個類
@ConditionalOnClass({ServletRegistration.class}): 這個也存在。
@EnableConfigurationProperties({WebMvcProperties.class}):
這個很熟悉了,使用前面剛學習完不久,它並不是條件裝配,而是用來繫結外部組態檔的,點進去。
可以看到,會與組態檔中字首是spring.mvc的所有屬性進行繫結。
另外,還可以自動把元件註冊到容器中去。
這裡可以試一下,在 main 方法裡增加輸出:
String[] beanNamesForType1 = run.getBeanNamesForType(WebMvcProperties.class); System.out.println("==WebMvcProperties型別元件的數量==" + beanNamesForType1.length);
執行一下,果然是有一個:
到此,說明DispatcherServletConfiguration這個設定類也是生效的。
繼續往下就看到方法dispatcherServlet(),而且是加了@Bean註解,就是給容器中註冊DispatcherServlet型別的元件。
這裡的經過是:
DispatcherServlet()
物件dispatcherServlet
。dispatcherServlet
一通 set 設定。dispatcherServlet
。在之前學習 springMVC 時候,還要手動去設定關於DispatcherServlet的一堆東西。而在 springboot 裡已經在底層設定好了,並且註冊到容器中去了,所以我們能直接使用。
隨著進一步跟著原始碼來理解自動設定的原理,使得自己更深的體會到 springboot 的優點。
那麼多東西不需要我們手動去設定了,並不是說用不上,而是在底層springboot已經幫我們完成好了設定。
當然,目前的重點還是學會使用 springboot,但是帶著之前對 springboot 的疑問來學習,還是更有收穫的。
以上就是SpringBoot2入門自動設定原理及原始碼分析的詳細內容,更多關於SpringBoot2自動設定的資料請關注it145.com其它相關文章!
相關文章
<em>Mac</em>Book项目 2009年学校开始实施<em>Mac</em>Book项目,所有师生配备一本<em>Mac</em>Book,并同步更新了校园无线网络。学校每周进行电脑技术更新,每月发送技术支持资料,极大改变了教学及学习方式。因此2011
2021-06-01 09:32:01
综合看Anker超能充系列的性价比很高,并且与不仅和iPhone12/苹果<em>Mac</em>Book很配,而且适合多设备充电需求的日常使用或差旅场景,不管是安卓还是Switch同样也能用得上它,希望这次分享能给准备购入充电器的小伙伴们有所
2021-06-01 09:31:42
除了L4WUDU与吴亦凡已经多次共事,成为了明面上的厂牌成员,吴亦凡还曾带领20XXCLUB全队参加2020年的一场音乐节,这也是20XXCLUB首次全员合照,王嗣尧Turbo、陈彦希Regi、<em>Mac</em> Ova Seas、林渝植等人全部出场。然而让
2021-06-01 09:31:34
目前应用IPFS的机构:1 谷歌<em>浏览器</em>支持IPFS分布式协议 2 万维网 (历史档案博物馆)数据库 3 火狐<em>浏览器</em>支持 IPFS分布式协议 4 EOS 等数字货币数据存储 5 美国国会图书馆,历史资料永久保存在 IPFS 6 加
2021-06-01 09:31:24
开拓者的车机是兼容苹果和<em>安卓</em>,虽然我不怎么用,但确实兼顾了我家人的很多需求:副驾的门板还配有解锁开关,有的时候老婆开车,下车的时候偶尔会忘记解锁,我在副驾驶可以自己开门:第二排设计很好,不仅配置了一个很大的
2021-06-01 09:30:48
不仅是<em>安卓</em>手机,苹果手机的降价力度也是前所未有了,iPhone12也“跳水价”了,发布价是6799元,如今已经跌至5308元,降价幅度超过1400元,最新定价确认了。iPhone12是苹果首款5G手机,同时也是全球首款5nm芯片的智能机,它
2021-06-01 09:30:45