一.Spring简单Ioc 容器 XmlBeanFactory 实现源码分析
xmlBeanFactory初始化加载资源
public XmlBeanFactory(Resource resource, BeanFactory parentBeanFactory) throws BeansException {
super(parentBeanFactory);
this.reader = new XmlBeanDefinitionReader(this);
this.reader.loadBeanDefinitions(resource); // 利用xmlBeanDefinitionReader来加载
}
public int loadBeanDefinitions(Resource resource) throws BeanDefinitionStoreException {
// 将资源进一步编码
return this.loadBeanDefinitions(new EncodedResource(resource));
}
public int loadBeanDefinitions(EncodedResource encodedResource) throws BeanDefinitionStoreException {
Assert.notNull(encodedResource, "EncodedResource must not be null");
if (this.logger.isInfoEnabled()) {
this.logger.info("Loading XML bean definitions from " + encodedResource.getResource());
} else {
int var5;
try {
// 获取资源流。
InputStream inputStream = encodedResource.getResource().getInputStream();
try {
// 将资源流封装成InputSource
InputSource inputSource = new InputSource(inputStream);
if (encodedResource.getEncoding() != null) {
inputSource.setEncoding(encodedResource.getEncoding());
}
// 调用xmlBean中的doLoadBeanDefinitions方法,继续执行加载
var5 = this.doLoadBeanDefinitions(inputSource, encodedResource.getResource());
} finally {
inputStream.close();
}
}
return var5;
}
}
protected int doLoadBeanDefinitions(InputSource inputSource, Resource resource) throws BeanDefinitionStoreException {
try {
// 将资源变成文档的形式,为了方面获取xml文件的root元素。
Document doc = this.doLoadDocument(inputSource, resource);
// 继续进行 核心 资源的加载
return this.registerBeanDefinitions(doc, resource);
}
}
上面的代码,作用就是把Spring的xml文件变成Document文档对象来表示,接下来就是真正的通过 BeanDefinitionDocumentReader 解析xml文件
public int registerBeanDefinitions(Document doc, Resource resource) {
BeanDefinitionDocumentReader documentReader = this.createBeanDefinitionDocumentReader();
int countBefore = this.getRegistry().getBeanDefinitionCount();
// 通过documentReader 进行 核心 的资源加载
documentReader.registerBeanDefinitions(doc, this.createReaderContext(resource));
return this.getRegistry().getBeanDefinitionCount() - countBefore;
}
public void registerBeanDefinitions(Document doc, XmlReaderContext readerContext) {
this.readerContext = readerContext;
// 通过文档对象获取到根元素 得到的结果是 <beans>
Element root = doc.getDocumentElement();
// 继续进行核心资源的加载
this.doRegisterBeanDefinitions(root);
}
protected void doRegisterBeanDefinitions(Element root) {
BeanDefinitionParserDelegate parent = this.delegate;
//获取 BeanDefinitionParserDelegate
this.delegate = this.createDelegate(this.getReaderContext(), root, parent);
if (this.delegate.isDefaultNamespace(root)) {
/* spring中通过profile来选择多种环境下的xml文件,比如开发环境,和生产环境。 <beans profile="development"> <context:property-placeholder location="classpath*:common/*.properties, classpath*:development/*.properties" /> </beans> */
//获取到<beans>标签上的profile属性。
String profileSpec = root.getAttribute("profile");
if (StringUtils.hasText(profileSpec)) {
// 如果获取到的profile和 希望得到的不一样,那就直接停止加载bean。直接返回。
String[] specifiedProfiles = StringUtils.tokenizeToStringArray(profileSpec, ",; ");
if (!this.getReaderContext().getEnvironment().acceptsProfiles(specifiedProfiles)) {
if (this.logger.isInfoEnabled()) {
this.logger.info("Skipped XML bean definition file due to specified profiles [" + profileSpec + "] not matching: " + this.getReaderContext().getResource());
}
return;
}
}
}
// 如果条件符合,那就继续
// 解析前处理
this.preProcessXml(root);
// 解析加载的核心方法
this.parseBeanDefinitions(root, this.delegate);
// 解析后处理, 这样加前后处理方法是为了更好的扩展。用到了模版模式
this.postProcessXml(root);
this.delegate = parent;
}
上面代码其中有个 判断 profile 的代码,这使得spring.xml 可以有多种环境可以选择。
protected void parseBeanDefinitions(Element root, BeanDefinitionParserDelegate delegate) {
if (delegate.isDefaultNamespace(root)) {
NodeList nl = root.getChildNodes();
for(int i = 0; i < nl.getLength(); ++i) {
// 循环获取xml中的元素
Node node = nl.item(i);
//是否是xml定义的Element元素类型,比如xml文档中的 <!-- -->也算一个node,但不是Element
if (node instanceof Element) {
//转化为Element
Element ele = (Element)node;
if (delegate.isDefaultNamespace(ele)) {
// 如果是 <bean>这样原生默认的标签,采用parseDefaultElement来解析。
this.parseDefaultElement(ele, delegate);
} else {
/* 如果是这样的自定义标签,采用parseCustomElement方法解析。 <context:component-scan base-package="demo.controller" /> <mvc:annotation-driven /> */
delegate.parseCustomElement(ele);
}
}
}
} else {
delegate.parseCustomElement(root);
}
}
上面代码说明ApplicationContext.xml 中除了Spring默认标签,如<bean>
还有其他自定义标签,如<aop:pointcut >
针对两种不同类型的标签分别有不同的处理方式。
1.1 针对自定义标签的处理方法
// 针对自定一标签的处理方法
public BeanDefinition parseCustomElement(Element ele, BeanDefinition containingBd) {
String namespaceUri = this.getNamespaceURI(ele);
//根据命名空间uri,得到相应的NamespaceHandler 比如对于<context:component-scan 这个标签,
//得到的handler就是ContextNamespaceHandler。
NamespaceHandler handler = this.readerContext.getNamespaceHandlerResolver().resolve(namespaceUri);
//如果是这样的自定义标签 <zk:zz> 没有在spring中扩展的,随便写的,那么 handler==null;
if (handler == null) {
this.error("Unable to locate Spring NamespaceHandler for XML schema namespace [" + namespaceUri + "]", ele);
return null;
} else {
//如果是 <context:component-scan base-package="demo.controller" /> 这样在spring中有的标签,
//那么就调用parse方法去解析这个标签。
return handler.parse(ele, new ParserContext(this.readerContext, this, containingBd));
}
}
public BeanDefinition parse(Element element, ParserContext parserContext) {
//继续调用findParserForElement 得到 BeanDefinitionParser ,然后利用它的parse方法解析
return this.findParserForElement(element, parserContext).parse(element, parserContext);
}
public BeanDefinition parse(Element element, ParserContext parserContext) {
// 获取其中的basePackage属性,即得到这个标签包的作用范围。
String basePackage = element.getAttribute("base-package");
basePackage = parserContext.getReaderContext().getEnvironment().resolvePlaceholders(basePackage);
String[] basePackages = StringUtils.tokenizeToStringArray(basePackage, ",; \t\n");
ClassPathBeanDefinitionScanner scanner = this.configureScanner(parserContext, element);
// 通过doScan去找包下面的相关类,并将他们解析成BeanDefinitions
Set<BeanDefinitionHolder> beanDefinitions = scanner.doScan(basePackages);
this.registerComponents(parserContext.getReaderContext(), beanDefinitions, element);
return null;
}
protected Set<BeanDefinitionHolder> doScan(String... basePackages) {
// 创建一个Set集合去装载BeanDefinitionHolder
Set<BeanDefinitionHolder> beanDefinitions = new LinkedHashSet();
String[] var3 = basePackages;
int var4 = basePackages.length;
for(int var5 = 0; var5 < var4; ++var5) {
String basePackage = var3[var5];
Set<BeanDefinition> candidates = this.findCandidateComponents(basePackage);
Iterator var8 = candidates.iterator();
while(var8.hasNext()) {
BeanDefinition candidate = (BeanDefinition)var8.next();
ScopeMetadata scopeMetadata = this.scopeMetadataResolver.resolveScopeMetadata(candidate);
candidate.setScope(scopeMetadata.getScopeName());
String beanName = this.beanNameGenerator.generateBeanName(candidate, this.registry);
// 判断扫描到的类属于哪种Bean,如果是AbstractBeanDefinition类型
if (candidate instanceof AbstractBeanDefinition) {
this.postProcessBeanDefinition((AbstractBeanDefinition)candidate, beanName);
}
// 如果是支持暴露元数据信息的 这里还要解析元数据。
if (candidate instanceof AnnotatedBeanDefinition) {
AnnotationConfigUtils.processCommonDefinitionAnnotations((AnnotatedBeanDefinition)candidate);
}
// 检验扫描的类是否已经被注册了,没有的话,就返回true,继续执行if代码块中数据。
if (this.checkCandidate(beanName, candidate)) {
//生成BeanDefinitionHolder 包装了beanDefinition 和 beanname
BeanDefinitionHolder definitionHolder = new BeanDefinitionHolder(candidate, beanName);
definitionHolder = AnnotationConfigUtils.applyScopedProxyMode(scopeMetadata, definitionHolder, this.registry);
beanDefinitions.add(definitionHolder);
this.registerBeanDefinition(definitionHolder, this.registry);
}
}
}
return beanDefinitions;
}
public static void registerBeanDefinition(BeanDefinitionHolder definitionHolder, BeanDefinitionRegistry registry) throws BeanDefinitionStoreException {
String beanName = definitionHolder.getBeanName();
registry.registerBeanDefinition(beanName, definitionHolder.getBeanDefinition());
}
public void registerBeanDefinition(String beanName, BeanDefinition beanDefinition) throws BeanDefinitionStoreException {
if (beanDefinition instanceof AbstractBeanDefinition) {
try {
((AbstractBeanDefinition)beanDefinition).validate();
} catch (BeanDefinitionValidationException var9) {
throw new BeanDefinitionStoreException(beanDefinition.getResourceDescription(), beanName, "Validation of bean definition failed", var9);
}
}
// 去容器中看这个bean是否已经注册
BeanDefinition oldBeanDefinition = (BeanDefinition)this.beanDefinitionMap.get(beanName);
if (oldBeanDefinition != null) {
// 如果已经注册,那么就报异常,不能重复注册
if (!this.isAllowBeanDefinitionOverriding()) {
throw new BeanDefinitionStoreException(beanDefinition.getResourceDescription(), beanName, "Cannot register bean definition [" + beanDefinition + "] for bean '" + beanName + "': There is already [" + oldBeanDefinition + "] bound.");
}
if (oldBeanDefinition.getRole() < beanDefinition.getRole()) {
if (this.logger.isWarnEnabled()) {
this.logger.warn("Overriding user-defined bean definition for bean '" + beanName + "' with a framework-generated bean definition: replacing [" + oldBeanDefinition + "] with [" + beanDefinition + "]");
}
} else if (!beanDefinition.equals(oldBeanDefinition)) {
if (this.logger.isInfoEnabled()) {
this.logger.info("Overriding bean definition for bean '" + beanName + "' with a different definition: replacing [" + oldBeanDefinition + "] with [" + beanDefinition + "]");
}
} else if (this.logger.isDebugEnabled()) {
this.logger.debug("Overriding bean definition for bean '" + beanName + "' with an equivalent definition: replacing [" + oldBeanDefinition + "] with [" + beanDefinition + "]");
}
this.beanDefinitionMap.put(beanName, beanDefinition);
} else {
// 如果不是正在创建,即还没有开始创建,跳到else
if (this.hasBeanCreationStarted()) {
Map var4 = this.beanDefinitionMap;
synchronized(this.beanDefinitionMap) {
this.beanDefinitionMap.put(beanName, beanDefinition);
List<String> updatedDefinitions = new ArrayList(this.beanDefinitionNames.size() + 1);
updatedDefinitions.addAll(this.beanDefinitionNames);
updatedDefinitions.add(beanName);
this.beanDefinitionNames = updatedDefinitions;
if (this.manualSingletonNames.contains(beanName)) {
Set<String> updatedSingletons = new LinkedHashSet(this.manualSingletonNames);
updatedSingletons.remove(beanName);
this.manualSingletonNames = updatedSingletons;
}
}
} else {
// 向beanDefinitionMap中添加beanDefinition
this.beanDefinitionMap.put(beanName, beanDefinition);
this.beanDefinitionNames.add(beanName);
this.manualSingletonNames.remove(beanName);
}
this.frozenBeanDefinitionNames = null;
}
if (oldBeanDefinition != null || this.containsSingleton(beanName)) {
this.resetBeanDefinition(beanName);
}
}
1.2 针对默认标签的处理方法
private void parseDefaultElement(Element ele, BeanDefinitionParserDelegate delegate) {
if (delegate.nodeNameEquals(ele, "import")) {
// 如果标签名是 import 调用这个处理方法
this.importBeanDefinitionResource(ele);
} else if (delegate.nodeNameEquals(ele, "alias")) {
// 如果标签名是 alias 调用这个处理方法
this.processAliasRegistration(ele);
} else if (delegate.nodeNameEquals(ele, "bean")) {
// 如果标签名是 bean 调用这个处理方法 ,接下来重点分析
this.processBeanDefinition(ele, delegate);
} else if (delegate.nodeNameEquals(ele, "beans")) {
// 如果标签名是 beans 调用这个处理方法
this.doRegisterBeanDefinitions(ele);
}
}
protected void processBeanDefinition(Element ele, BeanDefinitionParserDelegate delegate) {
// 通过delegate 解析 bean 标签,并生成 BeanDefinitionHolder
BeanDefinitionHolder bdHolder = delegate.parseBeanDefinitionElement(ele);
if (bdHolder != null) {
// 通过delegate 对获取的 BeanDefinitionHolder 进行装饰,如果有必要的话。
bdHolder = delegate.decorateBeanDefinitionIfRequired(ele, bdHolder);
try {
// 注册Bean
BeanDefinitionReaderUtils.registerBeanDefinition(bdHolder, this.getReaderContext().getRegistry());
} catch (BeanDefinitionStoreException var5) {
this.getReaderContext().error("Failed to register bean definition with name '" + bdHolder.getBeanName() + "'", ele, var5);
}
this.getReaderContext().fireComponentRegistered(new BeanComponentDefinition(bdHolder));
}
}
public BeanDefinitionHolder parseBeanDefinitionElement(Element ele) {
// 调用重载的方法
return this.parseBeanDefinitionElement(ele, (BeanDefinition)null);
}
public BeanDefinitionHolder parseBeanDefinitionElement(Element ele, BeanDefinition containingBean) {
// 获取id
String id = ele.getAttribute("id");
// 获取name
String nameAttr = ele.getAttribute("name");
List<String> aliases = new ArrayList();
if (StringUtils.hasLength(nameAttr)) {
String[] nameArr = StringUtils.tokenizeToStringArray(nameAttr, ",; ");
aliases.addAll(Arrays.asList(nameArr));
}
// 把id作为beanName
String beanName = id;
if (!StringUtils.hasText(id) && !aliases.isEmpty()) {
beanName = (String)aliases.remove(0);
if (this.logger.isDebugEnabled()) {
this.logger.debug("No XML 'id' specified - using '" + beanName + "' as bean name and " + aliases + " as aliases");
}
}
if (containingBean == null) {
this.checkNameUniqueness(beanName, aliases, ele);
}
// 根据beanName 和 元素生成 AbstractBeanDefinition 方法在下。
AbstractBeanDefinition beanDefinition = this.parseBeanDefinitionElement(ele, beanName, containingBean);
if (beanDefinition != null) {
// 是否beanName不存在
if (!StringUtils.hasText(beanName)) {
try {
if (containingBean != null) {
// 如果beanName不存在,即id不存在,那根据规则生成beanName 比如UserDao 变成 userDao
beanName = BeanDefinitionReaderUtils.generateBeanName(beanDefinition, this.readerContext.getRegistry(), true);
} else {
beanName = this.readerContext.generateBeanName(beanDefinition);
String beanClassName = beanDefinition.getBeanClassName();
if (beanClassName != null && beanName.startsWith(beanClassName) && beanName.length() > beanClassName.length() && !this.readerContext.getRegistry().isBeanNameInUse(beanClassName)) {
aliases.add(beanClassName);
}
}
if (this.logger.isDebugEnabled()) {
this.logger.debug("Neither XML 'id' nor 'name' specified - using generated bean name [" + beanName + "]");
}
} catch (Exception var9) {
this.error(var9.getMessage(), ele);
return null;
}
}
String[] aliasesArray = StringUtils.toStringArray(aliases);
// 将一个拥有所有信息的BeanDefinition包装成BeanDefinitionHolder。
return new BeanDefinitionHolder(beanDefinition, beanName, aliasesArray);
} else {
return null;
}
}
public AbstractBeanDefinition parseBeanDefinitionElement(Element ele, String beanName, BeanDefinition containingBean) {
try {
AbstractBeanDefinition bd = this.createBeanDefinition(className, parent);
// 一系列解析的方法,实际上,都没有真正加载,只是把标签信息转化,存入到 AbstractBeanDefinition bd 中
this.parseBeanDefinitionAttributes(ele, beanName, containingBean, bd);
bd.setDescription(DomUtils.getChildElementValueByTagName(ele, "description"));
this.parseMetaElements(ele, bd);
this.parseLookupOverrideSubElements(ele, bd.getMethodOverrides());
this.parseReplacedMethodSubElements(ele, bd.getMethodOverrides());
this.parseConstructorArgElements(ele, bd);
this.parsePropertyElements(ele, bd);
this.parseQualifierElements(ele, bd);
bd.setResource(this.readerContext.getResource());
bd.setSource(this.extractSource(ele));
AbstractBeanDefinition var7 = bd;
return var7;
} catch (ClassNotFoundException var13) {
this.error("Bean class [" + className + "] not found", ele, var13);
} catch (NoClassDefFoundError var14) {
this.error("Class that bean class [" + className + "] depends on not found", ele, var14);
} catch (Throwable var15) {
this.error("Unexpected failure during bean definition parsing", ele, var15);
} finally {
this.parseState.pop();
}
return null;
}
// 解析Bean标签的元素,将bean标签属性都加到BeanDefinition中去
public AbstractBeanDefinition parseBeanDefinitionAttributes(Element ele, String beanName, BeanDefinition containingBean, AbstractBeanDefinition bd) {
// 是否单例
if (ele.hasAttribute("singleton")) {
this.error("Old 1.x 'singleton' attribute in use - upgrade to 'scope' declaration", ele);
} else if (ele.hasAttribute("scope")) {
bd.setScope(ele.getAttribute("scope"));
} else if (containingBean != null) {
bd.setScope(containingBean.getScope());
}
if (ele.hasAttribute("abstract")) {
bd.setAbstract("true".equals(ele.getAttribute("abstract")));
}
// 懒加载
String lazyInit = ele.getAttribute("lazy-init");
if ("default".equals(lazyInit)) {
lazyInit = this.defaults.getLazyInit();
}
bd.setLazyInit("true".equals(lazyInit));
String autowire = ele.getAttribute("autowire");
// 自动注入属性解析
bd.setAutowireMode(this.getAutowireMode(autowire));
String dependencyCheck = ele.getAttribute("dependency-check");
bd.setDependencyCheck(this.getDependencyCheck(dependencyCheck));
String autowireCandidate;
if (ele.hasAttribute("depends-on")) {
autowireCandidate = ele.getAttribute("depends-on");
bd.setDependsOn(StringUtils.tokenizeToStringArray(autowireCandidate, ",; "));
}
autowireCandidate = ele.getAttribute("autowire-candidate");
String destroyMethodName;
if (!"".equals(autowireCandidate) && !"default".equals(autowireCandidate)) {
bd.setAutowireCandidate("true".equals(autowireCandidate));
} else {
destroyMethodName = this.defaults.getAutowireCandidates();
if (destroyMethodName != null) {
String[] patterns = StringUtils.commaDelimitedListToStringArray(destroyMethodName);
bd.setAutowireCandidate(PatternMatchUtils.simpleMatch(patterns, beanName));
}
}
if (ele.hasAttribute("primary")) {
bd.setPrimary("true".equals(ele.getAttribute("primary")));
}
if (ele.hasAttribute("init-method")) {
destroyMethodName = ele.getAttribute("init-method");
if (!"".equals(destroyMethodName)) {
bd.setInitMethodName(destroyMethodName);
}
} else if (this.defaults.getInitMethod() != null) {
bd.setInitMethodName(this.defaults.getInitMethod());
bd.setEnforceInitMethod(false);
}
if (ele.hasAttribute("destroy-method")) {
destroyMethodName = ele.getAttribute("destroy-method");
bd.setDestroyMethodName(destroyMethodName);
} else if (this.defaults.getDestroyMethod() != null) {
bd.setDestroyMethodName(this.defaults.getDestroyMethod());
bd.setEnforceDestroyMethod(false);
}
if (ele.hasAttribute("factory-method")) {
bd.setFactoryMethodName(ele.getAttribute("factory-method"));
}
if (ele.hasAttribute("factory-bean")) {
bd.setFactoryBeanName(ele.getAttribute("factory-bean"));
}
return bd;
}
// 解析bean标签的property标签,需要注入的元素。
public void parsePropertyElements(Element beanEle, BeanDefinition bd) {
NodeList nl = beanEle.getChildNodes();
for(int i = 0; i < nl.getLength(); ++i) {
Node node = nl.item(i);
if (this.isCandidateElement(node) && this.nodeNameEquals(node, "property")) {
// 核心方法
this.parsePropertyElement((Element)node, bd);
}
}
}
// 核心方法 实质上还是把property标签的信息,写入到BeanDefinition中去。 只是将信息写入,并没有解析。
public void parsePropertyElement(Element ele, BeanDefinition bd) {
// 获取property标签的名字。
String propertyName = ele.getAttribute("name");
if (!StringUtils.hasLength(propertyName)) {
this.error("Tag 'property' must have a 'name' attribute", ele);
} else {
this.parseState.push(new PropertyEntry(propertyName));
try {
if (bd.getPropertyValues().contains(propertyName)) {
this.error("Multiple 'property' definitions for property '" + propertyName + "'", ele);
return;
}
Object val = this.parsePropertyValue(ele, bd, propertyName);
PropertyValue pv = new PropertyValue(propertyName, val);
this.parseMetaElements(ele, pv);
pv.setSource(this.extractSource(ele));
bd.getPropertyValues().addPropertyValue(pv);
} finally {
this.parseState.pop();
}
}
}
// 装饰获取的BeanDefinitionHolder
public BeanDefinitionHolder decorateBeanDefinitionIfRequired(Element ele, BeanDefinitionHolder definitionHolder, BeanDefinition containingBd) {
BeanDefinitionHolder finalDefinition = definitionHolder;
// 获取bean标签上的attributes 默认有4种 autowire, autowire-candidate, class, lazy-init
/* 而如果lazy-init属性配置为true,那么就会进行懒加载了,这样在容器初始化的过程中不会进行依赖注入, 只有当第一个getBean的时候才会实例化Bean。 默认为false */
NamedNodeMap attributes = ele.getAttributes();
// 循环修饰bdh。
for(int i = 0; i < attributes.getLength(); ++i) {
Node node = attributes.item(i);
finalDefinition = this.decorateIfRequired(node, finalDefinition, containingBd);
}
// 获取bean标签的子标签
NodeList children = ele.getChildNodes();
// 进行装饰
for(int i = 0; i < children.getLength(); ++i) {
Node node = children.item(i);
if (node.getNodeType() == 1) {
// 这个装饰,只装饰不属于spring默认标签的东西,<property > 属于默认,所以,直接返回。
finalDefinition = this.decorateIfRequired(node, finalDefinition, containingBd);
}
}
return finalDefinition;
}
public BeanDefinitionHolder decorateIfRequired(Node node, BeanDefinitionHolder originalDef, BeanDefinition containingBd) {
String namespaceUri = this.getNamespaceURI(node);
// 如果是默认的,那么if(false)不进行操作
if (!this.isDefaultNamespace(namespaceUri)) {
NamespaceHandler handler = this.readerContext.getNamespaceHandlerResolver().resolve(namespaceUri);
if (handler != null) {
return handler.decorate(node, originalDef, new ParserContext(this.readerContext, this, containingBd));
}
return originalDef;
}
// 注册bean
public static void registerBeanDefinition(BeanDefinitionHolder definitionHolder, BeanDefinitionRegistry registry) throws BeanDefinitionStoreException {
String beanName = definitionHolder.getBeanName();
registry.registerBeanDefinition(beanName, definitionHolder.getBeanDefinition());
}
// 实际注册的bean
public void registerBeanDefinition(String beanName, BeanDefinition beanDefinition) throws BeanDefinitionStoreException {
if (beanDefinition instanceof AbstractBeanDefinition) {
try {
((AbstractBeanDefinition)beanDefinition).validate();
} catch (BeanDefinitionValidationException var9) {
throw new BeanDefinitionStoreException(beanDefinition.getResourceDescription(), beanName, "Validation of bean definition failed", var9);
}
}
// 去容器中看这个bean是否已经注册
BeanDefinition oldBeanDefinition = (BeanDefinition)this.beanDefinitionMap.get(beanName);
if (oldBeanDefinition != null) {
// 如果已经注册,那么就报异常,不能重复注册
if (!this.isAllowBeanDefinitionOverriding()) {
throw new BeanDefinitionStoreException(beanDefinition.getResourceDescription(), beanName, "Cannot register bean definition [" + beanDefinition + "] for bean '" + beanName + "': There is already [" + oldBeanDefinition + "] bound.");
}
if (oldBeanDefinition.getRole() < beanDefinition.getRole()) {
if (this.logger.isWarnEnabled()) {
this.logger.warn("Overriding user-defined bean definition for bean '" + beanName + "' with a framework-generated bean definition: replacing [" + oldBeanDefinition + "] with [" + beanDefinition + "]");
}
} else if (!beanDefinition.equals(oldBeanDefinition)) {
if (this.logger.isInfoEnabled()) {
this.logger.info("Overriding bean definition for bean '" + beanName + "' with a different definition: replacing [" + oldBeanDefinition + "] with [" + beanDefinition + "]");
}
} else if (this.logger.isDebugEnabled()) {
this.logger.debug("Overriding bean definition for bean '" + beanName + "' with an equivalent definition: replacing [" + oldBeanDefinition + "] with [" + beanDefinition + "]");
}
this.beanDefinitionMap.put(beanName, beanDefinition);
} else {
// 如果不是正在创建,即还没有开始创建,跳到else
if (this.hasBeanCreationStarted()) {
Map var4 = this.beanDefinitionMap;
synchronized(this.beanDefinitionMap) {
this.beanDefinitionMap.put(beanName, beanDefinition);
List<String> updatedDefinitions = new ArrayList(this.beanDefinitionNames.size() + 1);
updatedDefinitions.addAll(this.beanDefinitionNames);
updatedDefinitions.add(beanName);
this.beanDefinitionNames = updatedDefinitions;
if (this.manualSingletonNames.contains(beanName)) {
Set<String> updatedSingletons = new LinkedHashSet(this.manualSingletonNames);
updatedSingletons.remove(beanName);
this.manualSingletonNames = updatedSingletons;
}
}
} else {
// 向beanDefinitionMap中添加beanDefinition
this.beanDefinitionMap.put(beanName, beanDefinition);
this.beanDefinitionNames.add(beanName);
this.manualSingletonNames.remove(beanName);
}
this.frozenBeanDefinitionNames = null;
}
if (oldBeanDefinition != null || this.containsSingleton(beanName)) {
this.resetBeanDefinition(beanName);
}
}
上面两种方式去解析标签,解释都在代码里。
总结:
对于XmlBeanFactory这个简单实现的Ioc来说,它初始化实际只做了两件事:
- 1.把xml文件变成Document对象。
- 2.解析Document对象,将其中标签都解析成 BeanDefinition。注意,BeanDefinition只是一个基础接口,它有很多实现类,例如注解@Controller等生命的bean,会被解析成 AnnotatedGenericBeanDefinition
注意:bean标签上的lazy-init 懒加载属性,在XmlBeanFactory 初始化的时候是没有用到的,因为XmlBeanFactory初始化并不会去实例化Bean对象,只是存储各个BeanDefinition对象。