【Spring學習19】作用域:使用代理
阿新 • • 發佈:2019-01-22
接上篇
請這樣做
如果想把一個web作用域的Bean注入到另一個週期長的作用域的Bean中(比如單例的bean),就需要選擇注入一個AOP代理來替換這個web作用域Bean。在定義時,web作用域的Bean都需要宣告使用代理模式:配置中加上<aop:scoped-proxy/>
元素
官方文件的例子:
<!-- 一個HTTP session作用域的Bean 作為代理暴露出去 -->
<bean id="userPreferences" class="com.foo.UserPreferences" scope="session">
<!--指示容器代理這個Bean -->
<aop:scoped-proxy/>
</bean>
<!--一個單例Bean注入一個代理Bean -->
<bean id="userManager" class="com.foo.UserManager">
<!-- 實際使用的是userPreferences的代理物件 -->
<property name="userPreferences" ref="userPreferences"/>
</bean>
為什麼要這樣做?
上例中,HTTP Session作用域的userPreferences bean注入給單例userManger bean。因為userManager bean是單例的,即每個容器只會例項化一個,所以它的依賴物件userPreferences bean也僅會注入一次。這樣下來,userManagerbean只能操作相同的userPreferences物件,就是初始化時注入的那一個。
將一個短生命週期作用域bean注入給長生命週期作用域bean都會存在此類問題。
我們期望的是userManager物件中的userPreferences beans與session同生命週期和同作用域。
在userPreferences bean配置中加入<aop:scoped-proxy/>
後,容器將建立一個代理物件,該物件擁有和UserPreferences完全相同的public介面並暴露。代理物件每次呼叫時會從 Session範圍內獲取真正的UserPreferences物件,而userManager類卻不知道。