Spring IOC容器和元信息来源

BeanFactory和ApplicationContext谁才是Spring Ioc容器?

BeanFactory 接口提供了能够管理任何类型对象的高级配置机制。ApplicationContext 是BeanFactory 的子接口。ApplicationContext添加了以下特性:

  1. 更容易与 Spring 的 AOP 特性集成
  2. 消息资源处理(用于国际化)
  3. 事件发布。
  4. 应用层特定的上下文,例如 web 应用程序中使用的 WebApplicationContext。
  1. public interface ApplicationContext extends EnvironmentCapableListableBeanFactoryHierarchicalBeanFactory,
  2.   MessageSourceApplicationEventPublisherResourcePatternResolver {

  1. public interface ListableBeanFactory extends BeanFactory {

简而言之,BeanFactory 提供了配置框架和基本功能,ApplicationContext 添加了更多特定于企业的功能。

总结:BeanFactory和ApplicationContext可以说都是Spring Ioc容器,在底层实现时,ApplicationContext不止实现了BeanFactory接口,同时还组合了BeanFactory的另一个实现类DefaultListableBeanFactory。

  1. public class ClassPathXmlApplicationContext extends AbstractXmlApplicationContext {
  2. public abstract class AbstractXmlApplicationContext extends AbstractRefreshableConfigApplicationContext {
  3. public abstract class AbstractRefreshableConfigApplicationContext extends AbstractRefreshableApplicationContext
  4.   implements BeanNameAwareInitializingBean {
  5. public abstract class AbstractRefreshableApplicationContext extends AbstractApplicationContext {
  6.  @Nullable
  7.  private Boolean allowBeanDefinitionOverriding;
  8.  @Nullable
  9.  private Boolean allowCircularReferences;
  10.  /** Bean factory for this context. */
  11.  @Nullable
  12.  private DefaultListableBeanFactory beanFactory;
  13. @Override
  14.  public final ConfigurableListableBeanFactory getBeanFactory() {
  15.   synchronized (this.beanFactoryMonitor) {
  16.    if (this.beanFactory == null) {
  17.     throw new IllegalStateException("BeanFactory not initialized or already closed - " +
  18.       "call 'refresh' before accessing beans via the ApplicationContext");
  19.    }
  20.    return this.beanFactory;
  21.   }
  22.  }

configurableApplicationContext <-ApplicationContext<-BeanFactory
configurableApplicationContext#getBeanFactory()

Spring容器启动的过程中,会将Bean解析成Spring内部的BeanDefinition结构。 不管是是通过xml配置文件的 <Bean> 标签,还是通过注解配置的 @Bean ,还是 @Compontent 标注的类,还是扫描得到的类,它最终都会被解析成一个BeanDefinition对象,最后Bean工厂就会根据这份Bean的定义信息,对bean进行实例化、初始化等等操作。

Bean定义配置注意基于xml文件、properties文件、Java注解以及java Api;

Ioc容器配置注意基于xml文件、Java注解以及Java Api;

外部化属性配置基于Java注解 @Value。

Spring IoC依赖注入

  1. public class UserRepository {
  2.     /**
  3.      * 自定义bean
  4.      */
  5.     private Collection<User> users;
  6.     /**
  7.      * bean工厂
  8.      * 内建非bean对象
  9.      */
  10.     private BeanFactory beanFactory;
  11.     private ObjectFactory<User> userObjectFactory;
  12.     private ObjectFactory<ApplicationContext> objectFactory;
  13.     public ObjectFactory<ApplicationContext> getObjectFactory() {
  14.         return objectFactory;
  15.     }
  16.     public void setObjectFactory(ObjectFactory<ApplicationContext> objectFactory) {
  17.         this.objectFactory = objectFactory;
  18.     }
  19.     public ObjectFactory<User> getUserObjectFactory() {
  20.         return userObjectFactory;
  21.     }
  22.     public void setUserObjectFactory(ObjectFactory<User> userObjectFactory) {
  23.         this.userObjectFactory = userObjectFactory;
  24.     }
  25.     public Collection<User> getUsers() {
  26.         return users;
  27.     }
  28.     public BeanFactory getBeanFactory() {
  29.         return beanFactory;
  30.     }
  31.     public void setBeanFactory(BeanFactory beanFactory) {
  32.         this.beanFactory = beanFactory;
  33.     }
  34.     public void setUsers(Collection<User> users) {
  35.         this.users = users;
  36.     }
  37. }

Xml配置信息

  1. <?xml version="1.0" encoding="UTF-8"?>
  2. <beans xmlns="http://www.springframework.org/schema/beans"
  3.        xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
  4.        xsi:schemaLocation="http://www.springframework.org/schema/beans
  5.         https://www.springframework.org/schema/beans/spring-beans.xsd">
  6.     <bean id="user" class="org.mango.spring.ioc.overview.domain.User" >
  7.         <property name="id" value="1"/>
  8.         <property name="name" value="mango"/>
  9.     </bean>
  10.     <bean id="superUser" class="org.mango.spring.ioc.overview.domain.SuperUser" parent="user" primary="true">
  11.         <property name="address" value="西安"></property>
  12.     </bean>
  13.     <bean id="objectFactory" class="org.springframework.beans.factory.config.ObjectFactoryCreatingFactoryBean" >
  14.         <property name="targetBeanName" value="user"></property>
  15.     </bean>
  16. </beans>

  1. <?xml version="1.0" encoding="UTF-8"?>
  2. <beans xmlns="http://www.springframework.org/schema/beans"
  3.        xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
  4.        xmlns:util="http://www.springframework.org/schema/util"
  5.        xsi:schemaLocation="
  6.         http://www.springframework.org/schema/beans https://www.springframework.org/schema/beans/spring-beans.xsd
  7.         http://www.springframework.org/schema/util https://www.springframework.org/schema/util/spring-util.xsd">
  8.     <!--通过导入复用 dependency-->
  9.     <import resource="dependency-lookup-context.xml"></import>
  10.     <!--autowire自动注入-->
  11.     <bean id="userRepository" class="org.mango.spring.ioc.overview.repository.UserRepository"
  12.           autowire="byType"> 
  13.         <!--硬编码-->
  14.      <!--   <property name="users">
  15.             <util:list>
  16.                 <ref bean="user"/>
  17.                 <ref bean="superUser"/>
  18.             </util:list>
  19.         </property>-->
  20.     </bean>
  21. </beans>
  1.  //配置xml文件 启动spring 应用上下文
  2.         BeanFactory beanFactory = new ClassPathXmlApplicationContext("META-INF/dependency-injection-context.xml");
  3.         //来源1: 自定义bean
  4.         UserRepository userRepository = (UserRepository) beanFactory.getBean("userRepository");
  5.         //实时注入bean
  6.         userRepository.getUsers().forEach(System.out::println);
  7.         //来源2: 依赖注入 (内建依赖)
  8.         System.out.println(userRepository.getBeanFactory());
  9.         System.out.println(userRepository.getBeanFactory() == beanFactory);
  10.         //延时注入
  11.         ObjectFactory userFactory = userRepository.getUserObjectFactory();
  12.         System.out.println(userFactory.getObject());
  13.         ObjectFactory objectFactory = userRepository.getObjectFactory();
  14.         System.out.println(objectFactory.getObject());
  15.         System.out.println(objectFactory.getObject() == beanFactory);
  16.         //来源三: 容器内建 bean
  17.         Environment environment = beanFactory.getBean(Environment.class);

                 System.out.println("获取Environment类型的bean" + environment);

 System.out.println(userRepository.getBeanFactory() == beanFactory); 输出为false

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值