专栏首页JavaWebSpring源码-父子容器

Spring源码-父子容器

Spring源码-父子容器

什么是IOC容器?

最主要是完成了完成对象的创建和依赖的管理注入等等。

Spring的容器主要用途?

在Spring整体框架的核心概念中,容器是核心思想,就是用来管理Bean的整个生命周期的,而在一个项目中,容器不一定只有一个,Spring中可以包括多个容器,而且容器有上下层关系。

Spring父子容器流程图

Spring父子容器源代码分析

首先,我们先看看web.xml中常用的核心配置。

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

<context-param>
	<param-name>contextConfigLocation</param-name>
	<param-value>classpath:spring/applicationContext-core.xml</param-value>
</context-param>

<servlet>
	<servlet-name>spring-dispatcher</servlet-name>
	<servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
	<init-param>
		<param-name>contextConfigLocation</param-name>
		<param-value>classpath:spring/spring-dispatcher.xml</param-value>
	</init-param>
	<init-param>
		<param-name>detectAllHandlerMappings</param-name>
		<param-value>true</param-value>
	</init-param>
	<load-on-startup>1</load-on-startup>
</servlet>

上面xml配置包含了一个监听器ContextLoaderListener,一个父容器配置Bean的配置文件applicationContext-core.xml和一个Servlet DispatcherServlet,它们之间的关系在父子关系流程图中已经介绍。

在源码中,父容器调用的是ContextLoaderListener#contextInitialized。

// 父容器初始化 
@Override
public void contextInitialized(ServletContextEvent event) {
	initWebApplicationContext(event.getServletContext());
}

子容器Servlet调用的是FrameworkServlet#initServletBean。

@Override
protected final void initServletBean() throws ServletException {
	// 子容器初始化
	this.webApplicationContext = initWebApplicationContext();
	initFrameworkServlet();
}

父子容器在创建的时候都调用了同一个initWebApplicationContext方法。

其实在FrameworkServlet#initWebApplicationContext方法内存在如下的父子容器关系。

protected WebApplicationContext initWebApplicationContext() {
	// 父容器
	WebApplicationContext rootContext = WebApplicationContextUtils.getWebApplicationContext(getServletContext()); 
	// 当前容器
	WebApplicationContext wac = null;

	if (this.webApplicationContext != null) {
		wac = this.webApplicationContext;
		if (wac instanceof ConfigurableWebApplicationContext) {
			ConfigurableWebApplicationContext cwac = (ConfigurableWebApplicationContext) wac;
			if (!cwac.isActive()) {
				// 是否存在父容器
				if (cwac.getParent() == null) {
					// 给子容器设置父容器
					cwac.setParent(rootContext);
				}
				configureAndRefreshWebApplicationContext(cwac);
			}
		}
	}
}

由上图可以得出在Spring如果存在多个容器,多个容器是存在父子关系的,而父子关系重要的一点就是:父容器不可见子容器注册的Bean,子容器是可见父容器的Bean。

Spring的父子容器要怎么应用?

常见的方式有二种: 传统型、激进型。

传统型:

父上下文容器中保存数据源、服务层、DAO层、事务的Bean。 子上下文容器中保存Mvc相关的Controller的Bean。 事务控制在服务层,由于父上下文容器不能访问子上下文容器中内容,事务的Bean在父上下文容器中,无法访问子上下文容器中内容,就无法对子上下文容器中Controller进行AOP(事务)。

激进型:

只使用子上下文容器,不要父上下文容器,这个时候我们就直接通过一个配置文件就能解决所有了。

本文参与腾讯云自媒体分享计划,欢迎正在阅读的你也加入,一起分享。

我来说两句

0 条评论
登录 后参与评论

相关文章

  • API管理-舍弃springfox-swagger-ui,采用功能更加丰富的swagger-bootstrap-ui

    上一篇博客(API管理-基于SpringBoot项目集成swagger实现接口文档自动生成)中我已经提到过使用springfox-swagger-ui的部分问题...

    秋日芒草
  • Mysql索引原理深入剖析

    秋日芒草
  • 协议-应用层的协议分类

    1.超文本传输协议HTTP:  这是一种最基本的客户机/服务器的访问协议。浏览器向服务器发送请求,而服务器回应相应的网页。 

    秋日芒草
  • 容器技术及其应用白皮书--附录介绍

    版权声明:本文为木偶人shaon原创文章,转载请注明原文地址,非常感谢。 https://b...

    shaonbean
  • 想要使用容器技术 这5类遗留工具就应该被淘汰

    充分利用容器并不只是安装Dockers和激活容器应用程序那么简单。你需要改进的同样还有监控方法、安全性能等。 这么做的理由是,容器并不只是对你过去工作中使用到的...

    静一
  • Docker--docker ps 命令与结果解析

    里面包含ps的详细使用教程,虽然是英文的但是实例有一点英语功底就可以看懂,其中包含ps的模糊查询等。

    洋仔聊编程
  • 容器技术及其应用白皮书(上)-- 容器技术

    图2.2 容器技术框架

    shaonbean
  • 支持100+业务线、累计发布17万次|宜信容器云的A点与B点(分享实录)

    宜信公司从2018年初开始建设容器云,至今,容器云的常用基本功能已经趋于完善,主要包括服务管理、应用商店、Nginx配置、存储管理、CI/CD、权限管理等,支持...

    宜信技术学院
  • Docker已经再见,替代 Docker 的五种容器选择

    据 2018 年统计,Docker 占据了 83% 的容器市场份额。可是就在 2017 年,这个数字还是 99%,Docker 的统治地位无疑受到了削弱。不可...

    Java帮帮
  • 深入玩转K8S之智能化的业务弹性伸缩和滚动更新操作

    在上篇我们讲到了较为傻瓜初级的弹性伸缩和滚动更新,那么接下来我们来看看较为高级的智能的滚动更新。本节的知识点呢是K8S的liveness和readiness探测...

    DevinGeng

扫码关注云+社区

领取腾讯云代金券