Spring(一) IOC核心类

Posted by ZhouJ000 on August 19, 2018
最后更新于:2018-08-26

Spring(一) IOC核心类
Spring(二) Resource定位与载入
Spring(三) BeanDefinition解析与注册
Spring(四) 自定义标签解析
Spring(五) 其他初始化步骤
Spring(六) bean的加载01
Spring(七) bean的加载02
Spring(八) SpringBean的生命周期
Spring(九) IOC时序图
Spring(十) AOP 01
Spring(十一) AOP 02
Spring(十二) spring事务

准备

github上clone spring 最新源码。当前github最新版本5.1.0.BUILD-SNAPSHOT(v5.1.0.RC2),正式版本5.0.8.RELEASE。

spring由gradle编译。

分层

spring-model

core部分包含4个模块:
1 . spring-core:基本的核心工具类,Spring的其他组件都要使用到这个包里的类,Core模块是其他组件的基本核心:Resource、ResourceLoader
2 . spring-beans:IoC/DI操作相关的所有类,Bean工厂与bean的创建管理装配:DefaultListableBeanFactor->…->BeanFactory;RootBeanDefinition
3 . spring-context:为Spring核心提供了大量扩展,提供了对国际化(如资源绑定)、事件传播、资源加载和对Context的透明创建的支持:ApplicationContext
4 . spring-expression:spring表达式语言EL

aop部分包含3个模块:
1 . spring-aop:面向切面编程
2 . spring-aspects:集成AspectJ框架
3 . spring-instrument:提供一些类级的工具支持和ClassLoader级的实现,用于服务器

data access部分包含5个模块:
1 . spring-jdbc:jdbc的抽象层
2 . spring-tx:事务控制
3 . spring-orm:对象关系映射,集成orm框架
4 . spring-oxm:对象xml映射
5 . spring-jms:java消息服务

web部分包含4个模块:
1 . spring-web:基础web功能,主要建立于核心容器之上,通过Servlet或者Listeners来初始化IOC容器,也包含一些与Web相关的支持。如文件上传
2 . spring-webmvc: Web-Servlet模块,实现了Spring MVC(model-view-Controller)的Web应用
3 . spring-websocket:主要是与Web前端的全双工通讯的协议
4 . spring-webflux:是一个新的非堵塞函数式Reactive Web框架,可以用来建立异步的,非阻塞,事件驱动的服务,并且扩展性非常好

报文发送部分只有一个模块:
1 . spring-messaging:从Spring4开始新加入的一个模块,主要职责是为Spring框架集成一些基础的报文传送应用

test部分只有一个模块:
1 . spring-test:spring测试提供支持,提供junit与mock测试功能

其他
1 . spring-framework-bom:用于解决jar包依赖,只要项目中引入了它,外部集成时依赖关系无需版本号,Spring IO platform
2 . spring-context-support:spring额外支持包,比如邮件服务、视图解析等
3 . spring-jcl:日志,采用了设计模式中的“适配器模式”,它对外提供统一的接口,然后在适配类中将对日志的操作委托给具体的日志框架,比如Log4J,Java Logging API等
4 . spring-context-indexer:索引功能。就是第一次扫描之后生成一个静态文件记录所有的组件,然后下一次扫描就直接读取文件中的内容,而不去执行扫描过程

spring-relevance

Spring IOC核心

BeanFactory

BeanFactory是IOC容器的核心接口,它定义了IOC的基本功能,负责读取bean配置文档,管理bean的加载,实例化,维护bean之间的依赖关系,负责bean的声明周期。它主要定义了getBean方法。getBean方法是IOC容器获取bean对象和引发依赖注入的起点。BeanFactory只能管理单例(Singleton)Bean的生命周期。它不能管理原型(prototype非单例)Bean的生命周期。这是因为原型Bean实例被创建之后便被传给了客户端,容器失去了对它们的引用。

/**
 * 用来引用一个实例,或把它和工厂产生的Bean区分开,就是说,如果一个FactoryBean的名字为myJndiObject,那么,&myJndiObject会得到那个Factory
 */
String FACTORY_BEAN_PREFIX = "&";

<T> T getBean(Class<T> requiredType) throws BeansException;
<T> T getBean(Class<T> requiredType, Object... args) throws BeansException;
Object getBean(String name) throws BeansException;
<T> T getBean(String name, Class<T> requiredType) throws BeansException;
Object getBean(String name, Object... args) throws BeansException;

DefaultListableBeanFactory

I:ListableBeanFactory: 可以列举所有bean实例,实现预加载所有bean定义。
I:HierarchicalBeanFactory: 管理双亲IoC容器规范,比如说getParentBeanFactory()这样的方法。
I:AutowireCapableBeanFactory: 定义了bean的自动装配规则。

dubbo-DefaultListableBeanFactory

继承自AbstractAutowireCapableBeanFactory,并实现了一个外来接口BeanDefinitionRegistry,是整个bean加载的核心部分,是spring注册及加载bean的默认实现。XmlBeanFactory就是继承自DefaultListableBeanFactory。

ApplicationContext

BeanFactorty接口提供了配置框架及基本功能,但是无法支持spring的aop功能和web应用。而ApplicationContext接口作为BeanFactory的派生,因而提供BeanFactory所有的功能。ApplicationContext是IOC容器另一个重要接口,是spring提供的一个高级IOC容器,而且ApplicationContext还在功能上做了扩展,相较于BeanFactorty,ApplicationContext还提供了以下的功能:
1 . MessageSource,提供国际化的消息访问
2 . 资源访问,如URL和文件
3 . 事件传播特性,即支持aop特性
4 . 载入多个(有继承关系)上下文 ,使得每一个上下文都专注于一个特定的层次,比如应用的web层 + 上下文嵌套,通过保持父上下文可以维持一个上下文体系,对于bean的查找可以在这个上下文体系中发生。首先检查当前上下文,其次是父上下文,逐级向上,这样为不同的spring应用提供了一个共享的bean定义环境

XmlWebApplicationContext

XmlWebApplicationContext

从web应用的根目录读取配置文件,需要先在web.xml中配置,可以配置监听器或者servlet来实现

<context-param>
	<param-name>contextConfigLocation</param-name>
	<param-value>/WEB-INF/myApplicationContext.xml</param-value>
</context-param>

<listener>
	<listener-class>org.springframework.web.context.ContextLoaderListener</listener-class>
</listener>

<servlet>
	<servlet-name>context</servlet-name>
	<servlet-class>org.springframework.web.context.ContextLoaderServlet</servlet-class>
	<load-on-startup>1</load-on-startup>
</servlet>

ClassPathXmlApplicationContext

ClassPathXmlApplicationContext

从classpath的xml配置文件创建,可以从jar包中读取配置文件

ApplicationContext factory = new ClassPathXmlApplicationContext("classpath:applicationContext.xml");
ApplicationContext factory = new ClassPathXmlApplicationContext("applicationContext.xml"); 
ApplicationContext factory = new ClassPathXmlApplicationContext("file:E:/Workspaces/Test/.../applicationContext.xml");

Resource

用于封装底层资源,抽象了所有Spring内部使用到的底层资源:File、URL、Classpath等。定义了3个判断当前资源状态的方法:存在性(exists)、可读性(isReadable)、是否打开(isOpen)。还提供了不同资源到URL、URI、File类型的转换,以及获取相关信息的方法。有了Resource接口便可以对所有资源文件进行统一处理。

对不同来源的资源文件都有对应的Resource实现:文件(FileSystemResource)、Classpath资源(ClassPathResource)、URL资源(UrlResource)、InputStream资源(InputStreamResource)、Byte数组(ByteArrayResource)等。

BeanDefinitionReader

BeanDefinitionReader

该类的作用是读取Spring的配置文件的内容,并将其转换成Ioc容器内部的数据结构,而容器的数据结构就是BeanDefinition。 该类的功能概括的讲可分为两步:
1 . 负责BeanDefinition的资源定位,是获取Resource实例对象的过程。BeanDefinitionReader本身不具备该功能,而是通过ResourceLoader获取Resource实例
2 . 负责BeanDefinition的载入,指的是读取Resource内容并加载为Doucument的过程,然后利用documentReader对配置文件的内容进行解析,生成beanDefinition及注册到容器中

int loadBeanDefinitions(Resource resource) throws BeanDefinitionStoreException;
int loadBeanDefinitions(Resource... resources) throws BeanDefinitionStoreException;
int loadBeanDefinitions(String location) throws BeanDefinitionStoreException;
int loadBeanDefinitions(String... locations) throws BeanDefinitionStoreException;

BeanDefinitionReader-flow

从xml配置文件读取就是XmlBeanDefinitionReader。

BeanDefinition

Spring容器启动的过程中,会将Bean解析成Spring内部的BeanDefinition结构,BeanDefintion定义了Bean在IoC容器内的基本数据结构。

BeanDefinition

Spring 源码之 BeanDefinition阅读

AbstractBeanDefinition

提供了BeanDefinition接口的全部实现。是一个基本的框架。
其子类有:
1 . RootBeanDefinition(表示父级) 2 . ChildBeanDefinition(表示子级) 3 . GenericBeanDefinition(一般的BeanDefinition实现)