我们学习spring源码最好的方式就是阅读较早的版本,早期版本代码结构简单,模块较少,使得初学者能将更多的精力放在spring的核心原理上。本文使用的源码为0.9.1版本。源码下载地址:
git@gitee.com:limengg/spring-0.9.1-annotated.git
下载完成后,使用开发工具导入项目,就可以进行代码的跟着调试了。
代码结构如下图所示:

源码中带有测试用例:Test。在Test的useFactoryTest方法中,展示了加载一个bean的加载、获取和使用的过程。
Test类测试代码:
String file = "/Users/limeng/code/SRC_CODE/spring-0.9.1-annotated/src/test/resources/pets.xml";
XmlBeanFactory fac = new XmlBeanFactory(file, null);
// Find bean isabelle
Owner isabelle = (Owner)fac.getBean("isabelle");
System.out.println("Found bean: " + isabelle.getName() + " with pets: ");
ListIterator iter = isabelle.getPets().listIterator();
while (iter.hasNext()) {
IPet pet = (IPet) iter.next();
ISpecies sp = pet.getSpecies();
System.out.println(pet.getName() + " of species " + sp.getName());
}
我们把断点打在创建XmlBeanFactory这一行。
XmlBeanFactory fac = new XmlBeanFactory(file, null);
XmlBeanFactory的构造有两个参数,第一个为bean定义的xml文件路径,第二个参数为要加载的bean的父BeanFactory。启动测试类后,进入XmlBeanFactory构造函数。构造函数如下:
public XmlBeanFactory(String filename, BeanFactory parentBeanFactory) throws BeansException {
super(parentBeanFactory);
loadBeanDefinitions(filename);
}
构造方法中一共做了两件事。首先调用父类构造函数,调用路径为 XmlBeanFactory -> ListableBeanFactoryImpl -> AbstractBeanFactory.
最终,AbstractBeanFactory将传入的父BeanFactory进行保存。
然后来到构建BeanFactory初始化代码的第二行:加载bean的定义。将断点打在这一行,并调试进入loadBeanDefinitions方法实现。
loadBeanDefinitions中,构造DocumentBuilder解析xml inputstream得到Document对象。Document中持有解析xml中定义的全部标签及属性。代码如下

本文详细介绍了通过阅读Spring 0.9.1版本源码来理解其核心原理。首先,通过加载XML配置文件创建XmlBeanFactory,解析bean定义并注册到BeanFactory中,只保存属性信息并未实例化bean。接着,在调用getBean方法时,实际执行bean的实例化,处理依赖注入,确保bean的完整初始化。整个过程涉及BeanFactory的构造、bean定义加载、bean实例化和依赖处理,是深入理解Spring机制的关键。
最低0.47元/天 解锁文章
766

被折叠的 条评论
为什么被折叠?



