Bean的作用域@Scope、ProxyMode


原文地址:https://www.cnblogs.com/shamgod/p/5236060.html

一、

Spring的bean默認是單例的

But sometimes you may find yourself working with a mutable class that does main-
tain some state and therefore isn’t safe for reuse. In that case, declaring the class as a
singleton bean probably isn’t a good idea because that object can be tainted and cre-
ate unexpected problems when reused later.
Spring defines several scopes under which a bean can be created, including the
following:
 Singleton—One instance of the bean is created for the entire application.
 Prototype—One instance of the bean is created every time the bean is injected
into or retrieved from the Spring application context.
 Session—In a web application, one instance of the bean is created for each session.
 Request—In a web application, one instance of the bean is created for each request.

二、@Scope的三種用法

1.在自動掃描中

@Component
@Scope(ConfigurableBeanFactory.SCOPE_PROTOTYPE)
public class Notepad { ... }

2.在java配置文件中

@Bean
@Scope(ConfigurableBeanFactory.SCOPE_PROTOTYPE)
public Notepad notepad() {
    return new Notepad();
}

 

 

3.在xml配置文件中

<bean id="notepad" class="com.myapp.Notepad" scope="prototype" />

三、

若不指明proxyMode,當把一個session或request的bean注入到sigleton的bean時,會出現問題。如把購物車bean注入到service bean

@Component
@Scope(
value = WebApplicationContext.SCOPE_SESSION,
proxyMode = ScopedProxyMode.INTERFACES)
public ShoppingCart cart() {... }
@Component
public class StoreService {
    @Autowired
    public void setShoppingCart(ShoppingCart shoppingCart) {
            this.shoppingCart = shoppingCart;
        }
        ...
}

 

 

因為StoreService是signleton,是在容器啟動就會創建,而shoppingcart是session,只有用戶訪問時才會創建,所以當StoreService企圖要注入shoppingcart時,很有可能shoppingcart還沒創建。spring用代理解決這個問題,當ShoppingCart是接口時,指定 ScopedProxyMode.INTERFACES。當ShoppingCart是一個類時,則指定ScopedProxy- Mode.TARGET_CLASS,srping會通過CGLib來創建基於類的代理對象。當request注入到signleton bean時,也是一樣。

在xml中聲明proxy策略

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:aop="http://www.springframework.org/schema/aop" xsi:schemaLocation="
http://www.springframework.org/schema/aop
http://www.springframework.org/schema/aop/spring-aop.xsd
 http://www.springframework.org/schema/beans
 http://www.springframework.org/schema/beans/spring-beans.xsd">
  <bean id="cart" class="com.myapp.ShoppingCart" scope="session">
        <aop:scoped-proxy />
   </bean>
</beans>

 

 

<aop:scoped-proxy> is the Spring XML configuration’s counterpart to the @Scope
annotation’s proxyMode attribute. It tells Spring to create a scoped proxy for the bean.
By default, it uses CGL ib to create a target class proxy. But you can ask it to generate an
interface-based proxy by setting the proxy-target-class attribute to false :

<bean id="cart" class="com.myapp.ShoppingCart" scope="session">
    <aop:scoped-proxy proxy-target-class="false" />
</bean>


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM