BeanDefinition的作用是用于在spring容器初始化的时,将bean的参数转化为spring内部的BeanDefinition的结构:
在spring中BeanDefinition的接口类关系如下:
AttributeAccessor, BeanMetadataElement的作用和源码,在之前的文章中我已经分析过:
Spring源码分析-IOC之AttributeAccessor,Spring源码分析-IOC之BeanMetadataElement
下面我们来具体看下BeanDefinition:
public interface BeanDefinition extends AttributeAccessor, BeanMetadataElement {
//setScope的常量值,这是单例
String SCOPE_SINGLETON = ConfigurableBeanFactory.SCOPE_SINGLETON;
//setScope的常量值,这是原型
String SCOPE_PROTOTYPE = ConfigurableBeanFactory.SCOPE_PROTOTYPE;
//bean的角色:
//用户
int ROLE_APPLICATION = 0;
//某些复杂的配置
int ROLE_SUPPORT = 1;
//完全内部使用
int ROLE_INFRASTRUCTURE = 2;
//获取父beandefinition的名称
String getParentName();
//设置父beandefinition的名称
void setParentName(String parentName);
//获取bean的类名
String getBeanClassName();
//设置bean的类名
void setBeanClassName(String beanClassName);
//获取FactoryBean的名称
String getFactoryBeanName();
//设置FactoryBean的名称
void setFactoryBeanName(String factoryBeanName);
//得到一个工厂方法
String getFactoryMethodName();
//设置工厂方法
void setFactoryMethodName(String factoryMethodName);
//获取当前bean的Scope对应上面的常量值
String getScope();
//设置当前bean的Scope对应上面的常量值
void setScope(String scope);
//判断是否是懒加载
boolean isLazyInit();
//设置懒加载的值
void setLazyInit(boolean lazyInit);
//获取依赖的bean
String[] getDependsOn();
//设置依赖的beans
void setDependsOn(String... dependsOn);
//判断是否是自动装配
boolean isAutowireCandidate();
//设置是否自动装配
void setAutowireCandidate(boolean autowireCandidate);
//判断是否是自动装配是唯一的的bean对象
boolean isPrimary();
//设置为自动装配是唯一的的bean对象
void setPrimary(boolean primary);
//获取该bean的构造函数的值
ConstructorArgumentValues getConstructorArgumentValues();
//获取bean的普通属性集合
MutablePropertyValues getPropertyValues();
//判断bean是否是单例
boolean isSingleton();
//判断bean是否是原型
boolean isPrototype();
//判断bean是否是抽象的
boolean isAbstract();
//获取bean的角色对应上面的常量
int getRole();
//获取bean的描述
String getDescription();
//获取配置文件的描述
String getResourceDescription();
//返回原来的beanDefinition
BeanDefinition getOriginatingBeanDefinition();
}
但是在spring的ioc容器解析的时候用的比较多的是:RootBeanDefinition,ChildBeanDefinition,GenericBeanDefinition以及抽象类AbstractBeanDefinition,
我们首先看BeanDefinitionParserDelegate:
public AbstractBeanDefinition parseBeanDefinitionElement(
Element ele, String beanName, BeanDefinition containingBean) {
this.parseState.push(new BeanEntry(beanName));
String className = null;
if (ele.hasAttribute(CLASS_ATTRIBUTE)) {
className = ele.getAttribute(CLASS_ATTRIBUTE).trim();
}
try {
String parent = null;
if (ele.hasAttribute(PARENT_ATTRIBUTE)) {
parent = ele.getAttribute(PARENT_ATTRIBUTE);
}
//创建一个抽象的AbstractBeanDefinition实际类型GenericBeanDefinition
AbstractBeanDefinition bd = createBeanDefinition(className, parent);
//解析设置beanDefinition的属性
parseBeanDefinitionAttributes(ele, beanName, containingBean, bd);
bd.setDescription(DomUtils.getChildElementValueByTagName(ele, DESCRIPTION_ELEMENT));
parseMetaElements(ele, bd);
parseLookupOverrideSubElements(ele, bd.getMethodOverrides());
parseReplacedMethodSubElements(ele, bd.getMethodOverrides());
parseConstructorArgElements(ele, bd);
parsePropertyElements(ele, bd);
parseQualifierElements(ele, bd);
bd.setResource(this.readerContext.getResource());
bd.setSource(extractSource(ele));
return bd;
}
catch (ClassNotFoundException ex) {
error("Bean class [" + className + "] not found", ele, ex);
}
catch (NoClassDefFoundError err) {
error("Class that bean class [" + className + "] depends on not found", ele, err);
}
catch (Throwable ex) {
error("Unexpected failure during bean definition parsing", ele, ex);
}
finally {
this.parseState.pop();
}
return null;
}
还在此类中:
protected AbstractBeanDefinition createBeanDefinition(String className, String parentName)
throws ClassNotFoundException {
//具体创建在BeanDefinitionReaderUtils中
return BeanDefinitionReaderUtils.createBeanDefinition(
parentName, className, this.readerContext.getBeanClassLoader());
}
我们来看下BeanDefinitionReaderUtils的createBeanDefinition:
public static AbstractBeanDefinition createBeanDefinition(
String parentName, String className, ClassLoader classLoader) throws ClassNotFoundException {
//创建的实际类型为GenericBeanDefinition
GenericBeanDefinition bd = new GenericBeanDefinition();
bd.setParentName(parentName);
if (className != null) {
if (classLoader != null) {
bd.setBeanClass(ClassUtils.forName(className, classLoader));
}
else {
bd.setBeanClassName(className);
}
}
return bd;
}
BeanDefinition创建好了接下来我们看BeanDefinition的属性设置:
扫描二维码关注公众号,回复:
11246429 查看本文章
public AbstractBeanDefinition parseBeanDefinitionAttributes(Element ele, String beanName,
BeanDefinition containingBean, AbstractBeanDefinition bd) {
//此属性只在1.x中支持
if (ele.hasAttribute(SINGLETON_ATTRIBUTE)) {
error("Old 1.x 'singleton' attribute in use - upgrade to 'scope' declaration", ele);
}
//判断是否有scope属性
else if (ele.hasAttribute(SCOPE_ATTRIBUTE)) {
bd.setScope(ele.getAttribute(SCOPE_ATTRIBUTE));
}
else if (containingBean != null) {
// Take default from containing bean in case of an inner bean definition.
bd.setScope(containingBean.getScope());
}
//设置抽象属性
if (ele.hasAttribute(ABSTRACT_ATTRIBUTE)) {
bd.setAbstract(TRUE_VALUE.equals(ele.getAttribute(ABSTRACT_ATTRIBUTE)));
}
//设置懒加载属性
String lazyInit = ele.getAttribute(LAZY_INIT_ATTRIBUTE);
if (DEFAULT_VALUE.equals(lazyInit)) {
lazyInit = this.defaults.getLazyInit();
}
bd.setLazyInit(TRUE_VALUE.equals(lazyInit));
//设置自动加载属性
String autowire = ele.getAttribute(AUTOWIRE_ATTRIBUTE);
bd.setAutowireMode(getAutowireMode(autowire));
String dependencyCheck = ele.getAttribute(DEPENDENCY_CHECK_ATTRIBUTE);
bd.setDependencyCheck(getDependencyCheck(dependencyCheck));
if (ele.hasAttribute(DEPENDS_ON_ATTRIBUTE)) {
String dependsOn = ele.getAttribute(DEPENDS_ON_ATTRIBUTE);
bd.setDependsOn(StringUtils.tokenizeToStringArray(dependsOn, MULTI_VALUE_ATTRIBUTE_DELIMITERS));
}
String autowireCandidate = ele.getAttribute(AUTOWIRE_CANDIDATE_ATTRIBUTE);
if ("".equals(autowireCandidate) || DEFAULT_VALUE.equals(autowireCandidate)) {
String candidatePattern = this.defaults.getAutowireCandidates();
if (candidatePattern != null) {
String[] patterns = StringUtils.commaDelimitedListToStringArray(candidatePattern);
bd.setAutowireCandidate(PatternMatchUtils.simpleMatch(patterns, beanName));
}
}
else {
bd.setAutowireCandidate(TRUE_VALUE.equals(autowireCandidate));
}
//设置PRIMARY属性
if (ele.hasAttribute(PRIMARY_ATTRIBUTE)) {
bd.setPrimary(TRUE_VALUE.equals(ele.getAttribute(PRIMARY_ATTRIBUTE)));
}
//设置初始化方法
if (ele.hasAttribute(INIT_METHOD_ATTRIBUTE)) {
String initMethodName = ele.getAttribute(INIT_METHOD_ATTRIBUTE);
if (!"".equals(initMethodName)) {
bd.setInitMethodName(initMethodName);
}
}
else {
if (this.defaults.getInitMethod() != null) {
bd.setInitMethodName(this.defaults.getInitMethod());
bd.setEnforceInitMethod(false);
}
}
//设置销毁方法
if (ele.hasAttribute(DESTROY_METHOD_ATTRIBUTE)) {
String destroyMethodName = ele.getAttribute(DESTROY_METHOD_ATTRIBUTE);
if (!"".equals(destroyMethodName)) {
bd.setDestroyMethodName(destroyMethodName);
}
}
else {
if (this.defaults.getDestroyMethod() != null) {
bd.setDestroyMethodName(this.defaults.getDestroyMethod());
bd.setEnforceDestroyMethod(false);
}
}
//设置工厂方法名称
if (ele.hasAttribute(FACTORY_METHOD_ATTRIBUTE)) {
bd.setFactoryMethodName(ele.getAttribute(FACTORY_METHOD_ATTRIBUTE));
}
//设置FactoryBean的bean的名称
if (ele.hasAttribute(FACTORY_BEAN_ATTRIBUTE)) {
bd.setFactoryBeanName(ele.getAttribute(FACTORY_BEAN_ATTRIBUTE));
}
return bd;
}
注意:此处只是将bean对应的属性到beanDefinition中,将beanDefinition放到对应的map中,并没有实际初始化相应的bean。
小结:spring的bean的解析过程比较复杂,需要耐心的结合idea工具,一步步debug源码,同时还需要理解spring的设计思想,多思考这样设计的好处.