Spring父子容器特性 bug案例

2021-08-11 18:05:44 字數 2583 閱讀 2818

昨天,給資料組寫介面,不小心掉進坑里掙扎了半天,最後發現是spring和springmvc它們雖是父子但並不和諧,於是在此一記。

spring和springmvc作為bean管理容器和mvc層的預設框架,已被眾多web應用採用,而在實際開發中,由於有了強大的註解功能,很多基於xml的配置方式已經被替代,但在實際專案中,我們經常會同時配置spring和springmvc的配置檔案,分層來管理它們,但是有時候就會出現那麼一些奇怪的異常,一旦進坑,讓你無法自拔,就在昨天給資料組寫介面時,我進坑了,就在坑里渾渾噩噩得度分如年,雖然當時很難受很浮躁,但是此刻在總寫這篇博文時我心裡是很高興的,真的各位。

首先,我得幫助大家理解一下父子容器(2個容器)以及它們是如何初始化的,還有就是它們父子如何共享bean資源的。打個比方:老子的資產兒子可以使用,但是兒子的財產老子一般是不使用的;反過來說,spring父容器中對於springmvc子容器中的bean是不可見的,反之,子容器中對於父容器中的bean是可見的。意思就是這個意思,這些概念我也是這倆天才腦補的,以前也沒個正形,各位將就讀讀吧,文章末尾是我專門去給各位扒的美圖,請各位慢用(是關於父子容器中bean的可見性和web容器如何初始化它們的)。

到這兒,我廢話不多說了,直接給大家把我昨天進坑和出坑的場景簡單描述一下。

場景一:由父子容器參與的專案中開啟定時任務,由於包掃瞄的範圍大小,兒子的定時任務失效了?各位他們雖為父子,但是也不和諧啊,你以為是相親相愛一家人資源共享啊,我滴孩啊不是的。在springmvc的核心配置檔案中掃瞄了com.zxz.action包結構,在spring的管理配置檔案中首先開啟了掃瞄定時任務的註解配置,然後掃瞄了com.zxz.service包結構,但是沒有觸及到子容器的地盤,這下壞了這蒙在鼓裡的我菜鳥,同時開啟倆個世界的定時任務,還在傻傻的開啟控制台等著執行呢,但是只有爹的定時任務如願以償,但是兒子的定時任務掛了,.........經過一段時間的糾結,發現了問題,因為它們是2個容器,2個容器啊,不是你在這個容器裡配置了,就代表那個容器也會生效啊,不會的,你得分清,爹的是爹的,兒子的是兒子的。

專案包結構如下:官網:www.fhadmin.org

service層的定時任務:

1      /**

2 * 開啟spring容器掃瞄包範圍內的定時任務

3

*/4 @scheduled(cron = "0/3 * * * * ? ")

5 public

void

servicetask()

controller層的定時任務:

1      /**

2 * 開啟springmvc容器掃瞄包範圍內的定時任務

3

*/4 @scheduled(cron = "0/6 * * * * ? ")

5 public

void

webtask()

兒子的定時任務沒有執行的配置:

1 

2 3

4 5 package="com.zxz.service"/>

擴大定時任務掃瞄的包結構的配置:

1 

2 3

4 5 package="com.zxz"/>

場景二:由父子容器參與的專案中載入配置檔案中的常量值,由於疏忽導致在父容器的配置檔案中沒有配置載入資源檔案的那項配置,在service層的**中始終沒有獲取到相關常量的值?上面說了,2個容器各自使用各自的。我們在開發中經常有這麼乙個動作,就是將專案中不變的常量和它們的值都習慣儲存到某個資源檔案中,如果在**中需要使用它們的值則可以直接獲取,不用再去**中查詢到對應的常量並修改他們的值,那是愚蠢的做法,極其不方便,聰明人都是會提取出來的為了修改方便維護方便。我這個專案裡所有的常量和它們值都放在resource.propertie資源檔案裡了,但是由於我的忽視,我高看了spring他們一家人的關係,導致我service層的**一直報nullpointerexception異常,讓我斷點除錯卡了半天.......哎,最後發現我沒有在父容器的配置檔案中沒有配置載入項,我徹底恍惚了,不知道自己是大意還是菜,總之這些就是一些非常細微的細節,各位官網:www.fhadmin.org。

controller層和service層同時載入常量(如果使用spring和springmvc來作為容器,則記得同時配置哦):

父子容器中載入資源檔案的配置:

1

2<

context:property-placeholder

location

="classpath*:properties/*.propertie"

/>

圖一:父子容器中bean的可見性。  

圖二:父子容器的初始化情況。

spring父子容器

spring會生成父容器,一般用來載入dao和service,springmvc會生成子容器,一般用來載入controller,子容器可以看見父容器註冊的bean,父容器看不到子容器註冊的bean,配置預設子容器不查詢父容器註冊的bean,如果在父子容器中都註冊service,但是只有父容器註冊的s...

Spring 父子容器

必須要說的是,父子容器是通過設定形成的關係。或configurablebeanfactory介面,這兩個介面中分別有setparent及setparentbeanfactory方法,可以將指定容器設定為當前容器的父容器。contextattribute為key,將其儲存到servletcontext...

理解spring父子容器

一般來說,我們在整合spring和springmvc這兩個框架中,web.xml會這樣寫到 平時我們在專案中注入關係是這樣的順序 結合圖來說 在service中注入dao 初始化自動注入,利用 autowired 接著在controller裡注入service 初始化自動注入,利用 autowire...