您的位置:首页 > 编程语言 > Java开发

白话Spring源码(五):Bean的创建过程

2018-12-09 16:07 113 查看

我们知道可以通过name从beanFactory获取对应bean对象,那bean是怎么创建的呢?

我们先设想如果我们来创建对象需要哪几步呢?

1.找到对象的class

2.通过反射创建对象

3.设置对象的属性值

其实spring创建对象的也是主要分这几步,下面我们进入源码看看吧!

上篇博客我们了解了beanFactory的结构,但那都是接口并没有具体实现,beanFactory的getBean(String name)是获取bean实例的方法,他的第一个实现是在AbstractBeanFactory的抽象类里

AbstractBeanFactory的getBean:

[code]	public Object getBean(String name) throws BeansException {
String beanName = transformedBeanName(name);//转换name,主要是对FactoryBean进行处理,下面博客会讲解FactoryBean
Object sharedInstance = this.singletonCache.get(beanName);//看看单例里有没有bean实例,因为单例是先创建好,放到map里的
if (sharedInstance != null) {
if (logger.isDebugEnabled()) {
logger.debug("Returning cached instance of singleton bean '" + beanName + "'");
}
return getObjectForSharedInstance(name, sharedInstance);//如果单列里有对直接从map中get出来
}
else {//如果单例的map里没有就创建
RootBeanDefinition mergedBeanDefinition = null;
try {
mergedBeanDefinition = getMergedBeanDefinition(beanName, false);//获取bean对应的class信息,class信息封装在RootBeanDefinition
}
catch (NoSuchBeanDefinitionException ex) {
if (this.parentBeanFactory != null) {
return this.parentBeanFactory.getBean(name);//如果当前工厂没找到class,就从父级的工厂里找
}
throw ex;
}
// create bean instance
if (mergedBeanDefinition.isSingleton()) {//判断是不是配置成单例,如果是单列,创建好,放到单例的map里
synchronized (this.singletonCache) {
// re-check singleton cache within synchronized block
sharedInstance = this.singletonCache.get(beanName);
if (sharedInstance == null) {
logger.info("Creating shared instance of singleton bean '" + beanName + "'");
sharedInstance = createBean(beanName, mergedBeanDefinition);
addSingleton(beanName, sharedInstance);
}
}
return getObjectForSharedInstance(name, sharedInstance);
}
else {//如果不是配置成单例,则创建对象
return createBean(name, mergedBeanDefinition);//创建对象
}
}
}

这里只是先对name进行转换(这里涉及FactoryBean,后面会专门讲解),然后从单例的map里查,如果有则返回,没有就从xml加载配置的类的信息,封装在RootBeanDefinition 里(以后博客会分析BeanDefinition),到这里还是没讲怎么创建对象,创建过程在createBean(name, mergedBeanDefinition)方法里,createBean是在AbstractAutowireCapableBeanFactory的抽象类里实现的。

AbstractAutowireCapableBeanFactory的createBean方法

[code]	protected Object createBean(String beanName, RootBeanDefinition mergedBeanDefinition) throws BeansException {
if (logger.isDebugEnabled()) {
logger.debug("Creating instance of bean '" + beanName + "' with merged definition [" + mergedBeanDefinition + "]");
}

if (mergedBeanDefinition.getDependsOn() != null) {//判断是否配置依赖,有则先创建依赖的对象
for (int i = 0; i < mergedBeanDefinition.getDependsOn().length; i++) {
// guarantee initialization of beans that the current one depends on
getBean(mergedBeanDefinition.getDependsOn()[i]);
}
}

BeanWrapper instanceWrapper = null;//BeanWrapper这个是创建对象的包装类
if (mergedBeanDefinition.getResolvedAutowireMode() == RootBeanDefinition.AUTOWIRE_CONSTRUCTOR ||
mergedBeanDefinition.hasConstructorArgumentValues()) {//判断是否通过构造方法创建的,如果是则装配构造方法参数没返回BeanWrapper
instanceWrapper = autowireConstructor(beanName, mergedBeanDefinition);
}
else {//如果没有配置构造方法的参数
instanceWrapper = new BeanWrapperImpl(mergedBeanDefinition.getBeanClass());//new BeanWrapper
initBeanWrapper(instanceWrapper);//设置自定义属性
}
Object bean = instanceWrapper.getWrappedInstance();//直接通过无参的方式new对象,好了对象创建出来了

//如果是单列放到单例的map里
if (mergedBeanDefinition.isSingleton()) {
addSingleton(beanName, bean);
}

populateBean(beanName, mergedBeanDefinition, instanceWrapper);//设置对象的属性

//判断是否Aware,这后面会专门讲
try {
if (bean instanceof BeanNameAware) {
if (logger.isDebugEnabled()) {
logger.debug("Invoking setBeanName() on BeanNameAware bean '" + beanName + "'");
}
((BeanNameAware) bean).setBeanName(beanName);
}

if (bean instanceof BeanFactoryAware) {
if (logger.isDebugEnabled()) {
logger.debug("Invoking setBeanFactory() on BeanFactoryAware bean '" + beanName + "'");
}
((BeanFactoryAware) bean).setBeanFactory(this);
}

bean = applyBeanPostProcessorsBeforeInitialization(bean, beanName);//执行初始化前执行的自定义方法
invokeInitMethods(bean, beanName, mergedBeanDefinition);//执行初始化方法
bean = applyBeanPostProcessorsAfterInitialization(bean, beanName);//执行初始化后执行的自定义方法
}
catch (InvocationTargetException ex) {
throw new BeanCreationException(mergedBeanDefinition.getResourceDescription(), beanName,
"Initialization of bean failed", ex.getTargetException());
}
catch (Exception ex) {
throw new BeanCreationException(mergedBeanDefinition.getResourceDescription(), beanName,
"Initialization of bean failed", ex);
}
return bean;
}

这里主要讲通过RootBeanDefinition来创建对象,设置对象的属性值。创建对象是通过BeanWrapper 来实现的。其实new对象时很简单的,就用反射实例无参的构造方法,这里复杂的是设置对象属性,设置属性有两种方式:构造方法,set方法,其实也是通过反射实现的,具体的实现都在BeanWrapper里,有兴趣的可以自己去看,因为这里细节太多就不展开了。

 

这里只讲解了怎么创建出一个对象,但怎么加载类的信息的呢?请看下篇博客。

 

内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: