SpringMVC中的ConversionServiceExposingInterceptor工具类解析
作者:安迪源文
概述
ConversionServiceExposingInterceptor是Spring MVC的一个HandlerInterceptor,用于向请求添加一个属性,属性名称为ConversionService.class.getName(),值是Spring MVC配置定义的一个类型转换服务。该类型转换服务会在请求处理过程中用于请求参数或者返回值的类型转换。
缺省情况下,Spring MVC配置机制会主动构建一个ConversionServiceExposingInterceptor应用于所有的请求。
关于应用
1. 引入
缺省被WebMvcConfigurationSupport启用:
// WebMvcConfigurationSupport 代码片段 // /** * Provide access to the shared handler interceptors used to configure * {@link HandlerMapping} instances with. * <p>This method cannot be overridden; use {@link #addInterceptors} instead. */ protected final Object[] getInterceptors() { if (this.interceptors == null) { InterceptorRegistry registry = new InterceptorRegistry(); addInterceptors(registry); registry.addInterceptor(new ConversionServiceExposingInterceptor(mvcConversionService())); registry.addInterceptor(new ResourceUrlProviderExposingInterceptor(mvcResourceUrlProvider())); this.interceptors = registry.getInterceptors(); } return this.interceptors.toArray(); } // requestMappingHandlerMapping() bean 定义中使用所有 getInterceptors() 定义的通用拦截器 // mapping.setInterceptors(getInterceptors()); // viewControllerHandlerMapping() bean 定义中使用所有 getInterceptors() 定义的通用拦截器 // handlerMapping.setInterceptors(getInterceptors()); // beanNameHandlerMapping() bean 定义中使用所有 getInterceptors() 定义的通用拦截器 // mapping.setInterceptors(getInterceptors()); // resourceHandlerMapping() bean 定义中使用所有 getInterceptors() 定义的通用拦截器 // handlerMapping.setInterceptors(getInterceptors());
2. 使用
DispatcherServlet#doDispatch请求处理主流程会先找到能处理该请求的Handler,以HandlerExecutionChain形式包装存在。这些HandlerExecutionChain来自某个HandlerMapping,而这些HandlerMapping就是Spring MVC配置中定义的那些HandlerMapping,它们在DispatcherServlet初始化阶段#initHandlerMappings执行时被从容器中获取。
DispatcherServlet#doDispatch得到HandlerExecutionChain之后,会调用其方法applyPreHandle以应用各个HandlerInterceptor对请求的前置处理逻辑。这其中就有ConversionServiceExposingInterceptor。
// HandlerExecutionChain 代码片段 /** * Apply preHandle methods of registered interceptors. * @return {@code true} if the execution chain should proceed with the * next interceptor or the handler itself. Else, DispatcherServlet assumes * that this interceptor has already dealt with the response itself. */ boolean applyPreHandle(HttpServletRequest request, HttpServletResponse response) throws Exception { HandlerInterceptor[] interceptors = getInterceptors(); if (!ObjectUtils.isEmpty(interceptors)) { for (int i = 0; i < interceptors.length; i++) { HandlerInterceptor interceptor = interceptors[i]; if (!interceptor.preHandle(request, response, this.handler)) { triggerAfterCompletion(request, response, null); return false; } this.interceptorIndex = i; } } return true; }
源代码解析
源代码版本 : spring-webmvc-5.1.5.RELEASE
package org.springframework.web.servlet.handler; import java.io.IOException; import javax.servlet.ServletException; import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpServletResponse; import org.springframework.core.convert.ConversionService; import org.springframework.util.Assert; /** * Interceptor that places the configured {@link ConversionService} in request scope * so it's available during request processing. The request attribute name is * "org.springframework.core.convert.ConversionService", the value of * {@code ConversionService.class.getName()}. * * <p>Mainly for use within JSP tags such as the spring:eval tag. * * @author Keith Donald * @since 3.0.1 */ public class ConversionServiceExposingInterceptor extends HandlerInterceptorAdapter { private final ConversionService conversionService; /** * Creates a new {@link ConversionServiceExposingInterceptor}. * @param conversionService the conversion service to export to request scope when this interceptor is invoked */ public ConversionServiceExposingInterceptor(ConversionService conversionService) { Assert.notNull(conversionService, "The ConversionService may not be null"); this.conversionService = conversionService; } @Override public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws ServletException, IOException { // 请求处理前向请求添加属性 // 属性名称使用 ConversionService.class.getName() request.setAttribute(ConversionService.class.getName(), this.conversionService); return true; } }
到此这篇关于SpringMVC中的ConversionServiceExposingInterceptor工具类解析的文章就介绍到这了,更多相关ConversionServiceExposingInterceptor工具类内容请搜索脚本之家以前的文章或继续浏览下面的相关文章希望大家以后多多支持脚本之家!