Spring Bean Scopes – @Scope 注解

选中文字可对指定文章内容进行评论啦,→和←可快速切换按钮,绿色背景文字可以点击查看评论额。

Spring Bean Scopes – @Scope 注解

创建bean意味着,您创建类的实际实例,并根据bean定义注入依赖项。Bean 定义就像一个配方,您可以使用相同的配方创建该类的多个实例。 Scope 控制需要创建的实例数量和 bean 的生命周期。

Spring Framework 支持六个Scope,此外,您还可以创建自定义Scope。

1、单例scope —— @Scope("singleton") ——bean 的默认Scope。

2、原型scope——@Scope("prototype")——你每次都会得到一个类的新对象实例。

3、Request scope——@RequestScope——为每个单独的 Http 请求创建一个对象实例。

4、Session scope——@SessionScope——将单个 bean 定义的范围限定为 Http 会话的生命周期。

5、Application scope —— @ApplicationScope - 将单个 bean定义限定为ServletContext 的生命周期。

6、WebSocket scope – @Scope("websocket") – 将单个 bean 定义限定为 WebSocket 的生命周期。

7、自定义scope - Spring 还允许您创建自定义scope bean。

 

Singleton bean 作用域——@Scope(“singleton”)

当您将 bean 定义为 Singleton 范围时,Spring IoC 会根据 bean 定义精确地创建对象的一个​​实例。这个单例实例存储在缓存中,spring IoC 为同一个 bean 的所有后续请求和引用返回这个存储的实例。

简单来说,假设我将 itemDao 声明为单例 bean。无论我尝试在多少地方获取这个 DAO bean,Spring 都只会创建这个 bean 的一个实例,并在我使用的任何地方注入相同的实例。

请记住:Singleton 是 Spring IoC 中的默认 bean 范围。

当然,有几种方法可以声明 bean 范围。我们将使用@Scope 注释。 使用 Singleton 范围定义 ItemDao bean。

@Configuration
public class BasicIocConfig {
  @Bean
  @Scope("singleton")
  public ItemDao itemDao() {
    return new ItemDao();
  }
}

您还可以重写@Scope,如下所示

@Scope(ConfigurableBeanFactory.SCOPE_SINGLETON)

您可以将@Scope 注释与@Component、@Repository 或@Service 注释一起使用。

@Scope("singleton")
@Component
public class ItemDao {
  public void doSomething(){ //... }
}

在 XML 配置中,您可以设置scope如下。

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
       xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
       xsi:schemaLocation="http://www.springframework.org/schema/beans
       http://www.springframework.org/schema/beans/spring-beans.xsd">
  <bean id="itemDao" scope="singleton" class="basic.ioc.demo.ItemDao"/>
</beans>

Prototype bean 作用域——@Scope(“prototype”)

这个作用域与 Singleton 正好相反。每次您请求 bean 时,Spring IoC 都会创建一个新 bean。

注意:您应该始终为所有有状态的 bean 使用原型scope,例如 pojo、命令对象、模型对象等。 并对 DAO、服务、控制器等无状态 bean 使用单例scope。

就像单例一样,原型scope也可以定义如下。

@Configuration
public class BasicIocConfig {
  @Bean
  @Scope("prototype")
  public Item item() {
    return new Item();
  }

使用以下方法优化字符串池并避免拼写错误。

@Scope(ConfigurableBeanFactory.SCOPE_PROTOTYPE)

或者,如果您使用 XML 配置,请使用以下方法。

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
       xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
       xsi:schemaLocation="http://www.springframework.org/schema/beans
       http://www.springframework.org/schema/beans/spring-beans.xsd">
  <bean id="item" scope="prototype" class="basic.ioc.constructor.xml.Item"/>
</beans>

Request scope spring bean – @RequestScope

request、session、application和 websocket scope在 Spring web-aware ApplicationContext 中可用。简单来说,这些范围仅在 Spring Web 应用程序中可用。在使用它们之前,请确保您已经完成了正确的 web-app/web MVC 配置。

请求范围为每个 Http 请求创建一个新的 bean 实例。

与其他范围类似,如果您使用带注释的 java 配置,请使用 RequestScope 注释。

@RequestScope
@Component
public class LoginRequestAction {
    // ...
}

同样,如果您使用的是纯 XML 配置

<bean id="loginRequestAction" class="com.something.LoginRequestAction" scope="request"/>

Session scope bean – @SessionScope

在session scope的 bean 中,spring Ioc 为整个 Http Session 创建 bean 的一个实例。用户偏好、购物车等数据配置为会话范围是有意义的。

同样,如果您使用 XML 配置

<bean id="shoppingCart" class="com.shopping.ShoppingCart" scope="session"/>

Application scope bean – @ApplicationScope

application scope的 bean 的范围在 ServletContext 级别,并存储为常规 ServletContext 属性。pplication scope bean 可能听起来像singleton scope bean,但在两个重要方面有所不同。

1、应用程序范围的 bean 是每个 ServletContext 的单例,而不是每个 ApplicationContext。

2、它作为 ServletContext 属性公开和可见。

可以使用注释或基于 XML 的配置来完成,如下所示,

@ApplicationScope
@Component
public class AppThemePreferences {
    // ...
}
<bean id="appThemePreferences" class="com.global.AppThemePreferences" scope="application"/>

WebSocket scope bean – @Scope(“websocket”)

WebSocket 范围的 bean 存储在 WebSocket 会话属性中。每当在整个 WebSocket 会话期间引用 bean 时,都会返回相同的 bean 实例。

@Scope("websocket")
@Component
public class UpdateNotifier {
 //do tasks
}

大多数情况下,我们将在我们的应用程序中使用原型和单例scope。

版权声明:著作权归作者所有。

相关推荐

Java 数值相等判断详解(特别注意包装类型之间的比较)

Java数值类型分为基本类型,包装类型。基本类型:byte、short、 int、long、float和double包装类型:Byte、Short、Integer、Long、Float和Double数值比较可分为基本类型之间比较,基本类型与包装类类型比较,包装类型之间的比较。基本类型比较基本类型之间只能使用“==”做相等比较。比较结果就是数值是否相等。int a=1, 

Kotlin使用kotlin-kapt插件支持Android的注解处理

在Kotlin可以使用kapt插件来支持Android的注解处理。在Gradle配置kotlin-kapt插件如下:在app的build.gradle添加插件apply plugin: 'kotlin-kapt' 使用kapt添加注解依赖java使用annotationProcessor 添加的依赖改为使用kapt。例如添加dagger依赖dependencies {

PHP添加csrf token的注意点

首先不建议使用rand(),unique()来生成,如$token = md5(uniqid(rand(), TRUE));这是因为rand()函数产生的随机字符串是可以预测的。runiqid()和md5()增加的复杂度不高。产生tokenPHP 7session_start();if (empty($_SESSION['token'])) { $_SESSION['token'] = bi

Spirng Security使用注解对方法做权限安全控制

 Spring Security默认情况下是关闭了对方法级的安全控制。可以通过xml或者是在添加了@Configuration注解的bean上添加@EnableGlobalMethodSecurity来开启对方法级别的安全控制。Spring Security 支持三种方法级注解, 分别是 JSR-205/Secured 注解/prePostEnabled,可以在开启对方法级的安全控制时设

解决Spring session报错JedisDataException: ERR unknown command 'CONFIG'

在线上部署服务时,spring-session报了一个redis的错误,如下:redis.clients.jedis.exceptions.JedisDataException: ERR unknown command 'CONFIG'原因是spring-session调用了CONFIG命令来配置Keyspace notifications功能。而线上环境的redis基于权限的考虑,禁止应用服务执

Spring Cloud集成ZooKeeper注册中心绑定指定ip,解决UnknownHostException

Spring Cloud集成Zookeeper作为注册中心,从网关Spring Cloud GateWay转发给微服务里,在微服务里看到发送请求过来是以主机别名为url,如主机别名是server1.cluster,那么访问的地址是http://server.cluster/xxx。在GateWay有时会导致找不到服务。报类似如下的错误:500 Server Error for HTTP GET "

Spring boot maven打包后文件变大原因以及解决方法

在一个Spring boot项目中,添加了一些zip压缩文件。在开发过程中,从项目中下载的文件能够正常打开。但一旦打成jar包后,下载的zip包就打不开了。原因定位查看下载的zip压缩包,我们发现下载的zip文件要比我们原来的要大。所以我们怀疑是spring boot打包导致。通过查找相关资料,原因是我们在maven打包资源是设置了filtering。示例:<resource> &l