Spring Bean学习

一、什么是Spring Bean?

Spring Bean是Spring中最基本的组成单元,Spring 官方文档对 Bean 的解释是这样的:
In Spring, the objects that form the backbone of your application and that are managed by the Spring IoC container are called beans. A bean is an object that is instantiated, assembled, and managed by a Spring IoC container.
翻译过来就是:
在 Spring 中,构成应用程序主干并由Spring IoC容器管理的对象称为Bean。Bean是一个由Spring IoC容器实例化、组装和管理的对象。
Spring Bean
Spring是通过声明式配置的方式来定义Bean的,所有创建Bean需要的前置依赖或者参数都是通过配置文件先声明,Spring启动以后会解析这些声明好的配置内容。那么,我们该如何去定义Spring中的Bean呢?

二、定义Spring Bean的方式

一般来说,Spring Bean的定义配置有三种方式:基于XML的方式配置、基于注解扫描的方式配置、基于Java类的配置。

2.1 基于XML的方式配置

这种配置方式主要适用于以下两类场景:

  • Bean实现类来自第三方类库、比如DataSource等;
  • 需要定义命名空间的配置,如:context、aop、mvc等。

举例:

<beans>    
   <import resource=“resource1.xml” />//导入其他配置文件Bean的定义    
   <import resource=“resource2.xml” />
      <bean id="userService" class="com.gupaoedu.vip.UserService" init-method="init" destory-method="destory"> </bean>
      <bean id="message" class="java.lang.String">
         <constructor-arg index="0" value="test"></constructor-arg>
      </bean>
</beans>

这段代码是标准的Spring配置内容,咱们从上往下来看,首先导入一个叫做resource1.xml的标准配置文件,然后,导入了第二个标准的配置文件resource2.xml,接着,定义了一个叫做userService的Bean,对应的类是com.gupaoedu.vip.UserService,并且声明了在userService实例化之后要调用init()方法,在userService销毁之后调用destory()方法。

2.2 基于注解扫描的方式配置

这种配置方式主要适用于:在开发中需要引用的类,如Controller、Service、Dao等。

两种配置方法:

<context:component-scan base-package="com.gupaoedu.vip">
   <context:include-filter type="regex" expression="com.gupaoedu.vip.mall.*"/>//包含的目标类
   <context:exclude-filter type="aspectj" expression="com.gupaoedu.vip.mall..*Controller+"/>//排除的目标类
</context:component-scan>

在这段配置中,context:component-scan相当于使用了Spring内置的扫描注解的组件 @ComponentScan ,声明了需要扫描的基础包路径com.gupaoedu.vip,把所有com.gupaoedu.vip.mall下面的子包全部纳入扫描范围。并且排除了com.gupaoedu.vip.mall 包下面所有以Controller结尾或者包含Controller结尾的类。

使用Spring容器管理组件的beanName规则,默认是类名首字母变小写,可以自己修改。Spring主要提供了4种内置的注解用来声明Bean。它们分别是@Controller,声明为控制层组件的Bean,@Service,声明为业务逻辑层组件的Bean,@Repository,声明为数据访问层组件的Bean,当对组件的层次难以定位的时候使用@Component注解来声明。

2.3 基于Java类的配置

这种配置方式主要适用于以下两类场景:

  • 需要通过代码控制对象创建逻辑的场景;
  • 实现零配置,消除XML配置文件的场景。
@Configuration  
public class BeansConfiguration {        
   @Bean      
   public Student student(){                
       Student student = new Student();        
       student.setName("张三");        
       student.setTeacher(teacher());        
       return student;            
       }      
   @Bean      
   public Teacher teacher(){                
       Teacher teacher = new Teacher();        
       teacher.setName("Tom");        
       return teacher;            
       }    
}

通过分析这段代码,我可以了解到使用基于类的配置需要以下步骤:

  1. 首先,在BeansConfiguration类上配置@Configuration注解,表示将BeansConfiguration类将定义Bean的元数据;
  2. 在方法上使用@Bean注解,方法名默认就是Bean的名称,方法返回值就是Bean的实例;
  3. 通过AnnotationConfigApplicationContext或子类来启动Spring容器,从而加载这些已经声明好的注解配置。

三、Spring容器如何加载Bean?

Spring解析这些声明好的配置内容,将这些配置内容都转化为BeanDefinition对象,BeanDefinition中几乎保存了配置文件中声明的所有内容,再将BeanDefinition存到一个叫做beanDefinitionMap中。以beanName作为Key,以BeanDefinition对象作为Value。之后Spring容器,根据beanName找到对应的BeanDefinition,再去选择具体的创建策略。Spring Bean

Spring Bean的生命周期

Spring Bean

  1. Spring 启动,查找并加载需要被 Spring 管理的 Bean,进行 Bean 的实例化;
  2. Bean 实例化后,对 Bean 的引入和值注入到 Bean 的属性中;
  3. 如果 Bean 实现了 BeanNameAware 接口的话,Spring 将 Bean 的 Id 传递给 setBeanName() 方法;
  4. 如果 Bean 实现了 BeanFactoryAware 接口的话,Spring 将调用 setBeanFactory() 方法,将 BeanFactory 容器实例传入;
  5. 如果 Bean 实现了 ApplicationContextAware 接口的话,Spring 将调用 Bean 的 setApplicationContext() 方法,将 Bean 所在应用上下文引用传入进来;
  6. 如果 Bean 实现了 BeanPostProcessor 接口,Spring 就将调用它们的postProcessBeforeInitialization() 方法;
  7. 如果 Bean 实现了 InitializingBean 接口,Spring 将调用它们的 afterPropertiesSet() 方法。类似地,如果 Bean 使用 init-method 声明了初始化方法,该方法也会被调用;
  8. 如果 Bean 实现了 BeanPostProcessor 接口,Spring 就将调用它们的postProcessAfterInitialization() 方法;
  9. 此时,Bean 已经准备就绪,可以被应用程序使用了。它们将一直驻留在应用上下文中,直到应用上下文被销毁;
  10. 如果 Bean 实现了 DisposableBean 接口,Spring 将调用它的 destory() 接口方法,同样,如果 Bean 使用了 destory-method 声明销毁方法,该方法也会被调用。

参考文章:
https://baijiahao.baidu.com/s?id=1730064966023804126
https://blog.csdn.net/weixin_44129618/article/details/121989474

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值