在上一篇博客springMVC源码分析--容器初始化(二)DispatcherServlet中,我们队SpringMVC整体生命周期有一个简单的说明,并没有进行详细的源码分析,接下来我们会根据博客中提供的springMVC的生命周期图来详细的对SpringMVC的相关源码进行分析。

在上一篇博客中我们了解到,SpringMVC初始化配置是在父类HttpServletBean的init方法中,其实HttServletBean是一个比较简单的类,在这个类中并没有太复杂的功能,主要的函数是init函数中,源码如下:

主要工作就是设置我们在web.xml中配置的contextConfigLocation属性,当然这个属性是springMVC文件的配置文件地址,当然也可以不用配置,使用默认名称加载。

initBeanWrapper 函数并没有具体实现

initServletBean()是模板方法,是在子类FrameworkServlet中实现的,接下来我们会详细分析,这样HttpServletBean的主体功能就介绍完了。

        public final void init() throws ServletException {
		if (logger.isDebugEnabled()) {
			logger.debug("Initializing servlet '" + getServletName() + "'");
		}

		// Set bean properties from init parameters.
		try {
			//获得web.xml中的contextConfigLocation配置属性,就是spring MVC的配置文件
			PropertyValues pvs = new ServletConfigPropertyValues(getServletConfig(), this.requiredProperties);
			BeanWrapper bw = PropertyAccessorFactory.forBeanPropertyAccess(this);
			//获取服务器的各种信息
			ResourceLoader resourceLoader = new ServletContextResourceLoader(getServletContext());
			bw.registerCustomEditor(Resource.class, new ResourceEditor(resourceLoader, getEnvironment()));
			//模板方法,可以在子类中调用,做一些初始化工作,bw代表DispatcherServelt
			initBeanWrapper(bw);
			//将配置的初始化值设置到DispatcherServlet中
			bw.setPropertyValues(pvs, true);
		}
		catch (BeansException ex) {
			logger.error("Failed to set bean properties on servlet '" + getServletName() + "'", ex);
			throw ex;
		}

		// Let subclasses do whatever initialization they like.
		//模板方法,子类初始化的入口方法
		initServletBean();

		if (logger.isDebugEnabled()) {
			logger.debug("Servlet '" + getServletName() + "' configured successfully");
		}
	}

当然HttpServletBean还是提供了一些其他方法的,其实都是一些比较简单的get和set方法,就不做过多介绍了,HttpServletBean的完整源码如下:

/**
 *HttpServlet的一个简单扩展类
 */
@SuppressWarnings("serial")
public abstract class HttpServletBean extends HttpServlet
		implements EnvironmentCapable, EnvironmentAware {

	protected final Log logger = LogFactory.getLog(getClass());

	private final Set<String> requiredProperties = new HashSet<String>();

	private ConfigurableEnvironment environment;

	protected final void addRequiredProperty(String property) {
		this.requiredProperties.add(property);
	}
	@Override
	public final void init() throws ServletException {
		if (logger.isDebugEnabled()) {
			logger.debug("Initializing servlet '" + getServletName() + "'");
		}

		// Set bean properties from init parameters.
		try {
			//获得web.xml中的contextConfigLocation配置属性,就是spring MVC的配置文件
			PropertyValues pvs = new ServletConfigPropertyValues(getServletConfig(), this.requiredProperties);
			BeanWrapper bw = PropertyAccessorFactory.forBeanPropertyAccess(this);
			//获取服务器的各种信息
			ResourceLoader resourceLoader = new ServletContextResourceLoader(getServletContext());
			bw.registerCustomEditor(Resource.class, new ResourceEditor(resourceLoader, getEnvironment()));
			//模板方法,可以在子类中调用,做一些初始化工作,bw代表DispatcherServelt
			initBeanWrapper(bw);
			//将配置的初始化值设置到DispatcherServlet中
			bw.setPropertyValues(pvs, true);
		}
		catch (BeansException ex) {
			logger.error("Failed to set bean properties on servlet '" + getServletName() + "'", ex);
			throw ex;
		}

		// Let subclasses do whatever initialization they like.
		//模板方法,子类初始化的入口方法
		initServletBean();

		if (logger.isDebugEnabled()) {
			logger.debug("Servlet '" + getServletName() + "' configured successfully");
		}
	}

	/**
	 * Initialize the BeanWrapper for this HttpServletBean,
	 * possibly with custom editors.
	 * <p>This default implementation is empty.
	 * @param bw the BeanWrapper to initialize
	 * @throws BeansException if thrown by BeanWrapper methods
	 * @see org.springframework.beans.BeanWrapper#registerCustomEditor
	 */
	protected void initBeanWrapper(BeanWrapper bw) throws BeansException {
	}

	//获取servletName
	@Override
	public final String getServletName() {
		return (getServletConfig() != null ? getServletConfig().getServletName() : null);
	}

	//获取ServletContext
	@Override
	public final ServletContext getServletContext() {
		return (getServletConfig() != null ? getServletConfig().getServletContext() : null);
	}

	protected void initServletBean() throws ServletException {
	}

	@Override
	public void setEnvironment(Environment environment) {
		Assert.isInstanceOf(ConfigurableEnvironment.class, environment);
		this.environment = (ConfigurableEnvironment) environment;
	}

	@Override
	public ConfigurableEnvironment getEnvironment() {
		if (this.environment == null) {
			this.environment = this.createEnvironment();
		}
		return this.environment;
	}

	protected ConfigurableEnvironment createEnvironment() {
		return new StandardServletEnvironment();
	}

	private static class ServletConfigPropertyValues extends MutablePropertyValues {

		public ServletConfigPropertyValues(ServletConfig config, Set<String> requiredProperties)
			throws ServletException {

			Set<String> missingProps = (requiredProperties != null && !requiredProperties.isEmpty()) ?
					new HashSet<String>(requiredProperties) : null;

			Enumeration<String> en = config.getInitParameterNames();
			while (en.hasMoreElements()) {
				String property = en.nextElement();
				Object value = config.getInitParameter(property);
				addPropertyValue(new PropertyValue(property, value));
				if (missingProps != null) {
					missingProps.remove(property);
				}
			}
			// Fail if we are still missing properties.
			if (missingProps != null && missingProps.size() > 0) {
				throw new ServletException(
					"Initialization from ServletConfig for servlet '" + config.getServletName() +
					"' failed; the following required properties were missing: " +
					StringUtils.collectionToDelimitedString(missingProps, ", "));
			}
		}
	}

}

SpringMVC源码分析--容器初始化(三)HttpServletBean的更多相关文章

  1. SpringMVC源码分析--容器初始化(四)FrameworkServlet

    在上一篇博客SpringMVC源码分析--容器初始化(三)HttpServletBean我们介绍了HttpServletBean的init函数,其主要作用是初始化了一下SpringMVC配置文件的地址 ...

  2. SpringMVC源码分析--容器初始化(五)DispatcherServlet

    上一篇博客SpringMVC源码分析--容器初始化(四)FrameworkServlet我们已经了解到了SpringMVC容器的初始化,SpringMVC对容器初始化后会进行一系列的其他属性的初始化操 ...

  3. springMVC源码分析--容器初始化(二)DispatcherServlet

    在上一篇博客springMVC源码分析--容器初始化(一)中我们介绍了spring web初始化IOC容器的过程,springMVC作为spring项目中的子项目,其可以和spring web容器很好 ...

  4. springMVC源码分析--容器初始化(一)ContextLoaderListener

    在spring Web中,需要初始化IOC容器,用于存放我们注入的各种对象.当tomcat启动时首先会初始化一个web对应的IOC容器,用于初始化和注入各种我们在web运行过程中需要的对象.当tomc ...

  5. springMVC源码分析--AbstractUrlHandlerMapping(三)

    上一篇博客springMVC源码分析--AbstractHandlerMapping(二)中我们介绍了AbstractHandlerMapping了,接下来我们介绍其子类AbstractUrlHand ...

  6. springMVC源码分析--SimpleControllerHandlerAdapter(三)

    上一篇博客springMVC源码分析--HandlerAdapter(一)中我们主要介绍了一下HandlerAdapter接口相关的内容,实现类及其在DispatcherServlet中执行的顺序,接 ...

  7. springMVC源码分析--DispatcherServlet请求获取及处理

    在之前的博客springMVC源码分析--容器初始化(二)DispatcherServlet中我们介绍过DispatcherServlet,是在容器初始化过程中出现的,我们之前也说过Dispatche ...

  8. springMVC源码分析--AbstractDetectingUrlHandlerMapping(五)

    上一篇博客springMVC源码分析--AbstractUrlHandlerMapping(三)中我们介绍了AbstractUrlHandlerMapping,主要介绍了一个handlerMap的ur ...

  9. springMVC源码分析--SimpleUrlHandlerMapping(四)

    上一篇博客springMVC源码分析--AbstractUrlHandlerMapping(三)中我们介绍了AbstractUrlHandlerMapping,主要介绍了一个handlerMap的ur ...

随机推荐

  1. Linux下解决无法远程连接数据库问题

    起因 今天在ubuntu16.04环境下通过mysql workbench访问远程数据库时,发现无法连接问题,解决思路及方法记录如下,不足之处,请多指教. 问题 通过workbench输入密码访问时报 ...

  2. 记录一次widora sdk编译ipk 实战编译redis

      因为业务需求,需要用到redis存储一点简单的数据,因为redis有良好的哈希机制,可以完美实现我的某些需求,但openwrt官方提供memcached的ipk并没有提供redis,没办法,只能自 ...

  3. SQL Server数据库账号密码变更后导致vCenter Server无法访问数据库

    SQL Server数据库账号密码变更后导致vCenter Server无法访问数据库 1.1状况描述: 若SQL Server数据库的账号(这里以sa为例)密码发生了变更,那么连接数据的客户端vCe ...

  4. 在Spring Boot中使用Spring Security实现权限控制

    丢代码地址 https://gitee.com/a247292980/spring-security 再丢pom.xml <properties> <project.build.so ...

  5. SSH构造struts2项目

    第一在pom.xml导入相应的包 (网上有很多导入多个包的教程,我缩减到一个了) <project xmlns="http://maven.apache.org/POM/4.0.0&q ...

  6. ubuntu 14.04 64位 安装Opencv3.1.0 (包含opencv_contrib模块)

    写在前边: 据官方说法,目前还不是太稳定的算法模块都在opencv_contrib里边,由于不稳定,所以不能在release版本里发行,只有在稳定以后才会放进release里边.但是这里边有很多我们经 ...

  7. Tomcat安装及问题排查方法

    简介: Apache Jakarta的开源项目 JSP/Servlet容器 安装: 1.1进入 Tomcat 官方下载地址 选择合适版本下载,并解压到本地. (备注)Tomcat 8.5 要求 JDK ...

  8. PHP 实例 AJAX 投票

    AJAX 投票 在下面的实例中,我们将演示一个投票程序,通过它,投票结果在网页不进行刷新的情况下被显示. Do you like PHP and AJAX so far? Yes: No: 实例解释 ...

  9. CentOS 安装Docker

    CentOS 系列安装 Docker Docker 支持 CentOS6 及以后的版本. CentOS6 对于 CentOS6,可以使用 EPEL 库安装 Docker,命令如下 $ sudo yum ...

  10. Windows下Java调用BAT批处理不弹出cmd窗口

    常规Windows下Java调用BAT方式肯定会弹出cmd窗口 Runtime.getRuntime().exec("cmd.exe /C start D:\\test.bat") ...