springmvc第三篇 --DispatcherServlet

本文深入探讨了Spring MVC框架中DispatcherServlet的初始化过程,详细分析了onRefresh方法如何调用initStrategies来初始化九大核心组件,包括HandlerMapping、HandlerAdapter等。特别关注了initHandlerMappings方法,展示了如何在容器中检测和初始化HandlerMapping策略。

//onRefresh方法是DispatcherServlet类的入口,onRefresh中调用了initStrategies方法,在initStrategies中调用了9个初始化方法。

public class DispatcherServlet extends FrameworkServlet {
protected void onRefresh(ApplicationContext context) {
        this.initStrategies(context);
    }
    protected void initStrategies(ApplicationContext context) {
	    //初始化9大组件
        this.initMultipartResolver(context);
        this.initLocaleResolver(context);
        this.initThemeResolver(context);
        this.initHandlerMappings(context);
        this.initHandlerAdapters(context);
        this.initHandlerExceptionResolvers(context);
        this.initRequestToViewNameTranslator(context);
        this.initViewResolvers(context);
        this.initFlashMapManager(context);
    }
}
**下面已其中的initHandlerMappings为例:**
 private void initHandlerMappings(ApplicationContext context) {
        this.handlerMappings = null;
        //判断是不是检测所欲的handlerMappings
        if (this.detectAllHandlerMappings) {
        //从容器中获取所有的HandlerMapping类型的对象
            Map<String, HandlerMapping> matchingBeans = BeanFactoryUtils.beansOfTypeIncludingAncestors(context, HandlerMapping.class, true, false);
            //不为空的话就添加到handlerMappings中并进行排序
            if (!matchingBeans.isEmpty()) {
                this.handlerMappings = new ArrayList(matchingBeans.values());
                AnnotationAwareOrderComparator.sort(this.handlerMappings);
            }
        } else {
            try {
            	//通过名称和类型取获取HandlerMapping,并添加到handlerMappings中
                HandlerMapping hm = (HandlerMapping)context.getBean("handlerMapping", HandlerMapping.class);
                this.handlerMappings = Collections.singletonList(hm);
            } catch (NoSuchBeanDefinitionException var3) {
            }
        }
        //如果handlerMappings 为空的话使用默认策略
        if (this.handlerMappings == null) {
            this.handlerMappings = this.getDefaultStrategies(context, HandlerMapping.class);
            if (this.logger.isTraceEnabled()) {
                this.logger.trace("No HandlerMappings declared for servlet '" + this.getServletName() + "': using default strategies from DispatcherServlet.properties");
            }
        }
        
protected <T> List<T> getDefaultStrategies(ApplicationContext context, Class<T> strategyInterface) {
        String key = strategyInterface.getName();
        //从defaultStrategies中获取策略类型
        String value = defaultStrategies.getProperty(key);
        if (value == null) {
            return new LinkedList();
        } else {
        	//如果有多个默认值转换成数组
            String[] classNames = StringUtils.commaDelimitedListToStringArray(value);
            List<T> strategies = new ArrayList(classNames.length);
            String[] var7 = classNames;
            int var8 = classNames.length;

            for(int var9 = 0; var9 < var8; ++var9) {
                String className = var7[var9];
                try {
                	//按取到的类型进行初始化策略	
                    Class<?> clazz = ClassUtils.forName(className, DispatcherServlet.class.getClassLoader());
                    Object strategy = this.createDefaultStrategy(context, clazz);
                    strategies.add(strategy);
                } catch (ClassNotFoundException var13) {
                    throw new BeanInitializationException("Could not find DispatcherServlet's default strategy class [" + className + "] for interface [" + key + "]", var13);
                } catch (LinkageError var14) {
                    throw new BeanInitializationException("Unresolvable class definition for DispatcherServlet's default strategy class [" + className + "] for interface [" + key + "]", var14);
                }
            }
            return strategies;
        }
    }
    

主要的数据就是classNames,通过className进行初始化,classNames又来自于value,value的值是调用defaultStrategies.getProperty(key),所以关键点是defaultStrategies!defaultStrategies是一个静态属性,在static中进行初始化

static {
        try {
            ClassPathResource resource = new ClassPathResource("DispatcherServlet.properties", DispatcherServlet.class);
            defaultStrategies = PropertiesLoaderUtils.loadProperties(resource);
        } catch (IOException var1) {
            throw new IllegalStateException("Could not load 'DispatcherServlet.properties': " + var1.getMessage());
        }
    }
	**//我们看到defaultStrategies 是DispatcherServlet.properties中的属性,所以defaultStrategies 中存放的是DispatcherServlet.properties的属性。**
# Default implementation classes for DispatcherServlet's strategy interfaces.
# Used as fallback when no matching beans are found in the DispatcherServlet context.
# Not meant to be customized by application developers.
org.springframework.web.servlet.LocaleResolver=org.springframework.web.servlet.i18n.AcceptHeaderLocaleResolver
org.springframework.web.servlet.ThemeResolver=org.springframework.web.servlet.theme.FixedThemeResolver
org.springframework.web.servlet.HandlerMapping=org.springframework.web.servlet.handler.BeanNameUrlHandlerMapping,\
	org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerMapping
org.springframework.web.servlet.HandlerAdapter=org.springframework.web.servlet.mvc.HttpRequestHandlerAdapter,\
	org.springframework.web.servlet.mvc.SimpleControllerHandlerAdapter,\
	org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerAdapter
org.springframework.web.servlet.HandlerExceptionResolver=org.springframework.web.servlet.mvc.method.annotation.ExceptionHandlerExceptionResolver,\
	org.springframework.web.servlet.mvc.annotation.ResponseStatusExceptionResolver,\
	org.springframework.web.servlet.mvc.support.DefaultHandlerExceptionResolver
org.springframework.web.servlet.RequestToViewNameTranslator=org.springframework.web.servlet.view.DefaultRequestToViewNameTranslator
org.springframework.web.servlet.ViewResolver=org.springframework.web.servlet.view.InternalResourceViewResolver
org.springframework.web.servlet.FlashMapManager=org.springframework.web.servlet.support.SessionFlashMapManager


看到这里面定义了不同的组件类型,一共定义了8个组件,处理上传的组件没有定义。因为不是每个应用都需要上传功能。有的组件HandlerMapping ,HandlerAdapter,HandlerExceptionResolver配置了多个。
这里需要注意的是:首先默认配置不是最优配置,这是在没有配置的时候有一个默认值而已。另外一点是默认配置只会在没有配置的情况下才会使用。

主要分析了一下springmvc自身创建过程,springmvc中一共又三个层次,分别是HttpServletBean,FrameworkServlet和DispatcherServlet。HttpServletBean直接继承HttpServlet,其作用是将设置到Servlet中的属性设置到对应的属性,FrameworkServlet初始化了WebApplicationContext,DispatcherServlet初始化了自身的9个组件。
参考资料:看透springmvc源码

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值