版权声明
- 本文原创作者:谷哥的小弟
- 作者博客地址:http://blog.csdn.net/lfdfhl
1. BeanFactory 概述
BeanFactory
是 Spring IoC 容器的最基础接口,它定义了获取、配置和管理 Bean 的核心方法。它是 Spring 框架中容器体系的顶层接口之一,提供了最基本的依赖注入功能。
1.1 接口定义
public interface BeanFactory {String FACTORY_BEAN_PREFIX = "&";Object getBean(String name) throws BeansException;<T> T getBean(String name, Class<T> requiredType) throws BeansException;<T> T getBean(Class<T> requiredType) throws BeansException;boolean containsBean(String name);boolean isSingleton(String name) throws BeansException;boolean isPrototype(String name) throws BeansException;boolean isTypeMatch(String name, ResolvableType typeToMatch) throws BeansException;Class<?> getType(String name) throws BeansException;String[] getAliases(String name);
}
getBean
:获取容器中已注册的 Bean 实例。containsBean
:判断某个名称的 Bean 是否存在。isSingleton
/isPrototype
:判断 Bean 的作用域。getType
/isTypeMatch
:获取或匹配 Bean 的类型。getAliases
:获取某个 Bean 的所有别名。
1.2 与 ApplicationContext 的关系
BeanFactory
是 Spring 容器的基础接口。ApplicationContext
是其子接口,扩展了BeanFactory
的功能,增加了国际化、事件发布、资源加载等高级功能。BeanFactory
是“按需加载”,而ApplicationContext
是“预加载单例 Bean”。
2. 核心实现类
DefaultListableBeanFactory
是 Spring 中最常用的 BeanFactory
实现类,它实现了 BeanDefinitionRegistry
接口,支持注册和管理 Bean 定义。
2.1. 核心属性
public class DefaultListableBeanFactory extends AbstractAutowireCapableBeanFactoryimplements ConfigurableListableBeanFactory, BeanDefinitionRegistry {private final Map<String, BeanDefinition> beanDefinitionMap = new ConcurrentHashMap<>(256);private volatile List<String> beanDefinitionNames = new ArrayList<>(256);
}
beanDefinitionMap
:存储 Bean 名称与BeanDefinition
的映射关系。beanDefinitionNames
:存储所有已注册的 Bean 名称列表。
2.2 注册 Bean 定义
public void registerBeanDefinition(String beanName, BeanDefinition beanDefinition)throws BeanDefinitionStoreException {this.beanDefinitionMap.put(beanName, beanDefinition);if (!this.beanDefinitionNames.contains(beanName)) {this.beanDefinitionNames.add(beanName);}
}
- 将 Bean 定义放入
beanDefinitionMap
中。 - 将 Bean 名称加入
beanDefinitionNames
列表。
3. Bean 的加载过程
getBean()
是获取 Bean 的核心方法。其调用链如下:
getBean()
→ doGetBean()
→ getSingleton()
→ createBean()
→ doCreateBean()
→ populateBean()
→ initializeBean()
3.1 doGetBean()
方法
protected <T> T doGetBean(final String name, @Nullable final Class<T> requiredType,@Nullable final Object[] args, boolean typeCheckOnly) throws BeansException {final String beanName = transformedBeanName(name);Object sharedInstance = getSingleton(beanName);if (sharedInstance != null && args == null) {// 如果是 FactoryBean,处理 & 前缀bean = getObjectForBeanInstance(sharedInstance, name, beanName, null);} else {// 创建 Beanbean = createBean(beanName, mbd, args);}return (T) bean;
}
transformedBeanName
:处理&
前缀(用于获取 FactoryBean 本身)。getSingleton
:尝试从单例缓存中获取 Bean。createBean
:如果不存在,调用createBean
创建新实例。
3.2 单例 Bean 的创建
3.2.1 getSingleton()
方法
public Object getSingleton(String beanName) {return this.singletonObjects.get(beanName);
}
singletonObjects
:是一个Map<String, Object>
,缓存所有已创建的单例 Bean。
3.2.2 创建 Bean 的流程
protected Object createBean(String beanName, RootBeanDefinition mbd, @Nullable Object[] args) {// 1. 解析 Bean 的 ClassClass<?> resolvedClass = resolveBeanClass(mbd, beanName);// 2. 实例化 BeanObject beanInstance = instantiateBean(beanName, mbd);// 3. 属性注入populateBean(beanName, mbd, instanceWrapper);// 4. 初始化 BeanexposedObject = initializeBean(beanName, exposedObject, mbd);// 5. 注册为单例addSingleton(beanName, exposedObject);return exposedObject;
}
4. Bean 的生命周期
Spring 中 Bean 的生命周期由 BeanFactory
管理,其流程如下:
- 实例化:通过构造方法或工厂方法创建 Bean 实例。
- 属性注入:注入依赖的其他 Bean 或配置值。
- 初始化前回调:如
BeanNameAware
、BeanFactoryAware
等接口的回调。 - 初始化方法调用:如
@PostConstruct
、InitializingBean
接口或配置的init-method
。 - 使用 Bean:Bean 可以被使用。
- 销毁前回调:如
@PreDestroy
、DisposableBean
接口或配置的destroy-method
。 - 销毁 Bean:清理资源。
初始化 Bean 示例如下:
protected Object initializeBean(String beanName, Object bean, @Nullable RootBeanDefinition mbd) {// 调用 Aware 接口方法invokeAwareMethods(beanName, bean);// 调用初始化方法if (mbd == null || !mbd.isSynthetic()) {wrappedBean = applyBeanPostProcessorsBeforeInitialization(wrappedBean, beanName);}invokeInitMethods(beanName, wrappedBean, mbd);if (mbd == null || !mbd.isSynthetic()) {wrappedBean = applyBeanPostProcessorsAfterInitialization(wrappedBean, beanName);}return wrappedBean;
}
5. 工厂 Bean(FactoryBean)
FactoryBean
是一种特殊的 Bean,它本身是一个工厂,用于创建其他 Bean。
5.1 接口定义
public interface FactoryBean<T> {T getObject() throws Exception;Class<?> getObjectType();boolean isSingleton();
}
5.2 获取 FactoryBean 实例
Object bean = getBean("&myFactoryBean");
assertTrue(bean instanceof FactoryBean);
- 使用
&
前缀获取 FactoryBean 本身。 - 不带前缀则获取其
getObject()
返回的 Bean。
6. Bean 的作用域(Scope)
Spring 支持多种作用域,包括:
- singleton(默认):每个容器中只有一个实例。
- prototype:每次调用
getBean()
都返回一个新实例。 - request / session(Web 作用域):每个请求或会话一个实例。
作用域实现机制如下:
public boolean isSingleton(String name) throws NoSuchBeanDefinitionException {String beanName = transformedBeanName(name);RootBeanDefinition mbd = getMergedLocalBeanDefinition(beanName);return mbd.isSingleton();
}
RootBeanDefinition
中保存了 Bean 的作用域配置。
7. BeanFactory 的扩展机制
7.1 BeanFactoryPostProcessor
允许在 Bean 实例化之前修改 BeanDefinition
。
public interface BeanFactoryPostProcessor {void postProcessBeanFactory(ConfigurableListableBeanFactory beanFactory) throws BeansException;
}
示例:
public class CustomBeanFactoryPostProcessor implements BeanFactoryPostProcessor {public void postProcessBeanFactory(ConfigurableListableBeanFactory beanFactory) {BeanDefinition beanDef = beanFactory.getBeanDefinition("myBean");beanDef.setScope(BeanDefinition.SCOPE_PROTOTYPE);}
}
7.2 BeanPostProcessor
允许在 Bean 实例化前后进行干预。
public interface BeanPostProcessor {default Object postProcessBeforeInitialization(Object bean, String beanName) throws BeansException {return bean;}default Object postProcessAfterInitialization(Object bean, String beanName) throws BeansException {return bean;}
}
8. BeanFactory 与 ApplicationContext 的对比
特性 | BeanFactory | ApplicationContext |
---|---|---|
初始化时机 | 按需加载(懒加载) | 启动时预加载单例 Bean |
功能特性 | 仅提供基本的依赖注入 | 提供国际化、事件发布、资源加载等高级功能 |
资源加载 | 仅支持类路径加载 | 支持多种资源加载方式(如 Ant 路径) |
扩展点支持 | 需手动注册 BeanPostProcessor 等组件 | 自动注册并调用扩展点 |
9. 核心代码示例与解释
9.1 手动注册 Bean 定义并获取 Bean
DefaultListableBeanFactory factory = new DefaultListableBeanFactory();
RootBeanDefinition definition = new RootBeanDefinition(MyBean.class);
factory.registerBeanDefinition("myBean", definition);MyBean bean = factory.getBean("myBean", MyBean.class);
System.out.println(bean);
- 创建
DefaultListableBeanFactory
。 - 定义
BeanDefinition
。 - 注册 Bean 定义。
- 获取 Bean 实例。
9.2 使用 BeanFactoryPostProcessor
修改 Bean 定义
factory.addBeanPostProcessor(new CustomBeanFactoryPostProcessor());
- 将自定义的
BeanFactoryPostProcessor
添加到容器中。
10. 总结
BeanFactory
是 Spring IoC 容器的核心接口之一,它提供了最基本的依赖注入功能。其设计体现了模块化、可扩展性和灵活性,是构建 Spring 容器体系的基础。通过理解其源码结构、生命周期管理、Bean 加载机制以及扩展机制,开发者可以更深入地掌握 Spring 的运行原理,并在实际项目中更好地进行配置和优化。实践建议如下:
- 优先使用
ApplicationContext
:在企业级应用中推荐使用,因其提供了更全面的功能。 - 理解
BeanFactory
的懒加载机制:适用于资源受限的场景。 - 合理使用
BeanPostProcessor
和BeanFactoryPostProcessor
:用于扩展容器行为。 - 避免过度依赖
BeanFactory
的底层 API:保持代码的可测试性和可维护性。