spring容器启动的加载过程(二)
第六步:
public abstract class AbstractApplicationContext extends DefaultResourceLoader
implements ConfigurableApplicationContext, DisposableBean {
protected ConfigurableListableBeanFactory obtainFreshBeanFactory() {
refreshBeanFactory();//具体实现调用子类容器的refreshBeanFactory()方法
ConfigurableListableBeanFactory beanFactory = getBeanFactory();
if (logger.isDebugEnabled()) {
logger.debug("Bean factory for " + getDisplayName() + ": " + beanFactory);
}
return beanFactory;
} ... protected abstract void refreshBeanFactory() throws BeansException, IllegalStateException;
}
第七步:
public abstract class AbstractRefreshableApplicationContext extends AbstractApplicationContext {
/** Bean factory for this context */
private DefaultListableBeanFactory beanFactory;
protected final void refreshBeanFactory() throws BeansException {
//如果已经有beanfactory了,则销毁所有的bean,关闭beanfactory
if (hasBeanFactory()) {
destroyBeans();
closeBeanFactory();
}
try {
//得到一个默认的DefaultListableBeanFactory
DefaultListableBeanFactory beanFactory = createBeanFactory();
beanFactory.setSerializationId(getId());
//对IoC容器进行定制化,如设置启动参数,开启注解的自动装配等
customizeBeanFactory(beanFactory);
//调用载入Bean定义的方法,主要这里又使用了一个委派模式,在当前类中只定义了抽象的loadBeanDefinitions方法,具体的实现调用子类容器
loadBeanDefinitions(beanFactory);
synchronized (this.beanFactoryMonitor) {
this.beanFactory = beanFactory;
}
}
catch (IOException ex) {
throw new ApplicationContextException("I/O error parsing bean definition source for " + getDisplayName(), ex);
}
}
//创建beanfactory
protected DefaultListableBeanFactory createBeanFactory() {
return new DefaultListableBeanFactory(getInternalParentBeanFactory());
}
...
protected abstract void loadBeanDefinitions(DefaultListableBeanFactory beanFactory)
throws BeansException, IOException;
}
第八步:
public class XmlWebApplicationContext extends AbstractRefreshableWebApplicationContext {
/** Default config location for the root context */
public static final String DEFAULT_CONFIG_LOCATION = "/WEB-INF/applicationContext.xml";
/** Default prefix for building a config location for a namespace */
public static final String DEFAULT_CONFIG_LOCATION_PREFIX = "/WEB-INF/";
/** Default suffix for building a config location for a namespace */
public static final String DEFAULT_CONFIG_LOCATION_SUFFIX = ".xml";
@Override
protected void loadBeanDefinitions(DefaultListableBeanFactory beanFactory) throws BeansException, IOException {
// Create a new XmlBeanDefinitionReader for the given BeanFactory.
//创建XmlBeanDefinitionReader,即创建Bean读取器,并通过回调设置到容器中去,容器使用该读取器读取Bean定义资源
XmlBeanDefinitionReader beanDefinitionReader = new XmlBeanDefinitionReader(beanFactory);
// Configure the bean definition reader with this context's
// resource loading environment.
//设置环境
beanDefinitionReader.setEnvironment(this.getEnvironment());
//为Bean读取器设置Spring资源加载器,AbstractXmlApplicationContext的祖先父类AbstractApplicationContext,他继承DefaultResourceLoader,因此容器本身也是一个资源加载器
beanDefinitionReader.setResourceLoader(this);
//为Bean读取器设置SAX xml解析器
beanDefinitionReader.setEntityResolver(new ResourceEntityResolver(this));
// Allow a subclass to provide custom initialization of the reader,
// then proceed with actually loading the bean definitions.
//当Bean读取器读取Bean定义的Xml资源文件时,启用Xml的校验机制
initBeanDefinitionReader(beanDefinitionReader);
//Bean读取器真正实现加载的方法
loadBeanDefinitions(beanDefinitionReader);
}
...
protected void loadBeanDefinitions(XmlBeanDefinitionReader reader) throws IOException {
//获取配置资源的定位
String[] configLocations = getConfigLocations();
if (configLocations != null) {
for (String configLocation : configLocations) {
//XmlBean读取器调用其父类AbstractBeanDefinitionReader读取定位的Bean定义资源
reader.loadBeanDefinitions(configLocation);
}
}
}
}
第九步:
public abstract class AbstractBeanDefinitionReader implements EnvironmentCapable, BeanDefinitionReader {
//从指定的资源加载bean定义,返回bean定义的数量
public int loadBeanDefinitions(String location, Set<Resource> actualResources) throws BeanDefinitionStoreException {
ResourceLoader resourceLoader = getResourceLoader();//得到资源加载器
if (resourceLoader == null) {
throw new BeanDefinitionStoreException(
"Cannot import bean definitions from location [" + location + "]: no ResourceLoader available");
}
if (resourceLoader instanceof ResourcePatternResolver) {
// Resource pattern matching available.
try {
Resource[] resources = ((ResourcePatternResolver) resourceLoader).getResources(location);
int loadCount = loadBeanDefinitions(resources);//得到加载bean定义的数量,而且在这里将bean定义注入进了spring容器中
if (actualResources != null) {
for (Resource resource : resources) {
actualResources.add(resource);
}
}
if (logger.isDebugEnabled()) {
logger.debug("Loaded " + loadCount + " bean definitions from location pattern [" + location + "]");
}
return loadCount;
}
catch (IOException ex) {
throw new BeanDefinitionStoreException(
"Could not resolve bean definition resource pattern [" + location + "]", ex);
}
}
else {
// Can only load single resources by absolute URL.
Resource resource = resourceLoader.getResource(location);
int loadCount = loadBeanDefinitions(resource);
if (actualResources != null) {
actualResources.add(resource);
}
if (logger.isDebugEnabled()) {
logger.debug("Loaded " + loadCount + " bean definitions from location [" + location + "]");
}
return loadCount;
}
}
public int loadBeanDefinitions(Resource... resources) throws BeanDefinitionStoreException {
Assert.notNull(resources, "Resource array must not be null");
int counter = 0;
for (Resource resource : resources) {
counter += loadBeanDefinitions(resource);//加载不同的资源类型,使用不同的具体子类来加载,这里使用的是xml。所以他的子类是XmlBeanDefinitionReader,还有一个子类是PropertiesBeanDefinitionReader
}
return counter;
}
}
spring容器启动的加载过程(二)的更多相关文章
- spring容器启动的加载过程(三)
第十步: public class XmlBeanDefinitionReader extends AbstractBeanDefinitionReader { /** * Load bean def ...
- spring容器启动的加载过程(一)
使用spring,我们在web.xml都会配置ContextLoaderListener <listener> <listener-class> org.springframe ...
- 微服务架构 | *2.3 Spring Cloud 启动及加载配置文件源码分析(以 Nacos 为例)
目录 前言 1. Spring Cloud 什么时候加载配置文件 2. 准备 Environment 配置环境 2.1 配置 Environment 环境 SpringApplication.prep ...
- 1. spring5源码 -- Spring整体脉络 IOC加载过程 Bean的生命周期
可以学习到什么? 0. spring整体脉络 1. 描述BeanFactory 2. BeanFactory和ApplicationContext的区别 3. 简述SpringIoC的加载过程 4. ...
- Tomcat源码分析三:Tomcat启动加载过程(一)的源码解析
Tomcat启动加载过程(一)的源码解析 今天,我将分享用源码的方式讲解Tomcat启动的加载过程,关于Tomcat的架构请参阅<Tomcat源码分析二:先看看Tomcat的整体架构>一文 ...
- jvm(1)类的加载(二)(自定义类加载器)
[深入Java虚拟机]之四:类加载机制 1,从Java虚拟机的角度,只存在两种不同的类加载器: 1,启动类加载器:它使用C++实现(这里仅限于Hotspot,也就是JDK1.5之后默认的虚拟机,有其他 ...
- 深入理解 spring 容器,源码分析加载过程
Spring框架提供了构建Web应用程序的全功能MVC模块,叫Spring MVC,通过Spring Core+Spring MVC即可搭建一套稳定的Java Web项目.本文通过Spring MVC ...
- spring启动component-scan类扫描加载过程(转)
文章转自 http://www.it165.net/pro/html/201406/15205.html 有朋友最近问到了 spring 加载类的过程,尤其是基于 annotation 注解的加载过程 ...
- 【Spring源码分析系列】启动component-scan类扫描加载过程
原文地址:http://blog.csdn.net/xieyuooo/article/details/9089441/ 在spring 3.0以上大家都一般会配置一个Servelet,如下所示: &l ...
随机推荐
- jsp中使用java函数
<%@ taglib uri="http://java.sun.com/jsp/jstl/functions" prefix="fn"%> ${fn ...
- QT学习笔记—1
1.模态和非模态的区别:非模态可以同时操作两个窗口,模态的只能在顶层窗口关闭之后才能使用其他窗口 //同时显示出widget和dialog窗口,非模态 QDialog *dialog = ne ...
- phpDocumentor2安装配置和使用
今天弄了下 phpDocumentor2生成项目文档,感觉效果还是不错的 不过因为已经安装过了,之前没有截图,现在没法办重新截图了,下次补上 官网地址 http://phpdoc.org 一.安装: ...
- CodeForces 706E Working routine
十字链表. 开一个十字链表,矩阵中每一格作为一个节点,记录五个量: $s[i].L$:$i$节点左边的节点编号 $s[i].R$:$i$节点右边的节点编号 $s[i].U$:$i$节点上面的节点编号 ...
- ios监听ScrollView/TableView滚动的正确姿势
主要介绍 监测tableView垂直滚动的舒畅姿势 监测scrollView/collectionView横向滚动的正确姿势 1.监测tableView垂直滚动的舒畅姿势 通常我们用KVO或者在scr ...
- CentOS7 citus9.5 集群安装及管理
1 所有节点配置 #------服务安装 服务yum update -y #------扩展依赖安装yum install -y epel-release && yum update ...
- maven 运行tomcatrun -Dmaven.multiModuleProjectDirectory system property is not set. Check $M2_HOME environment variable and mvn script match.
解决-Dmaven.multiModuleProjectDirectory system property is not set. Check $M2_HOME environment varia ...
- Activiti(工作流)学习资源总结
刚进公司第一个项目就是oa项目,不会activiti,只得自学,途中搜集到的activiti学习资源总结 1.activiti初体验 http://blog.csdn.net/bluejoe2000/ ...
- 去掉word冗余格式 java正则表达式
word转换html时,会留下很多格式,有些格式并不是我们所需要的,然而这些格式比真正的文章内容还要多,严重影响页面的加载速度,因此就需要找个一个好的解决方案把这些多余的格式个去掉.网上有很多去除wo ...
- was性能调优前期准备
http://www.ibm.com/developerworks/cn/websphere/library/techarticles/0707_wudan/#resources was应用服务器环境 ...