Donald_Draper 阅读(832) 评论(0)
我们来看DispatcherServlet的handlerAdapters初始化所做的事情
public class DispatcherServlet extends FrameworkServlet
{
 public DispatcherServlet(WebApplicationContext webApplicationContext)
    {
        super(webApplicationContext);
        detectAllHandlerMappings = true;
        detectAllHandlerAdapters = true;
        detectAllHandlerExceptionResolvers = true;
        detectAllViewResolvers = true;
        throwExceptionIfNoHandlerFound = false;
        cleanupAfterInclude = true;
    }
   
    //初始化控制器映射
     private void initHandlerMappings(ApplicationContext context)
    {
        handlerMappings = null;
        if(detectAllHandlerMappings)
        {
            Map matchingBeans = BeanFactoryUtils.beansOfTypeIncludingAncestors(context, org/springframework/web/servlet/HandlerMapping, true, false);
            if(!matchingBeans.isEmpty())
            {
	       //List<HashMap<String,HandlerMapping>>,Key为beanName,value值为HandlerMapping实例
                handlerMappings = new ArrayList(matchingBeans.values());
                OrderComparator.sort(handlerMappings);
            }
        } 
    }
    //初始化控制器方法适配器
      private void initHandlerAdapters(ApplicationContext context)
    {
        handlerAdapters = null;
        if(detectAllHandlerAdapters)
        {
            Map matchingBeans = BeanFactoryUtils.beansOfTypeIncludingAncestors(context, org/springframework/web/servlet/HandlerAdapter, true, false);
            if(!matchingBeans.isEmpty())
            {
	        //List<HashMap<String,HandlerAdapter>>,Key为beanName,value值为HandlerAdapter实例
                handlerAdapters = new ArrayList(matchingBeans.values());
                OrderComparator.sort(handlerAdapters);
            }
        }
    }

    private List handlerMappings;//List<HashMap<String,HandlerMapping>>,Key为beanName,value值为HandlerMapping实例
    private List handlerAdapters;//List<HashMap<String,HandlerAdapter>>,Key为beanName,value值为HandlerAdapter实例
    private List handlerExceptionResolvers;
    private List viewResolvers;

    static 
    {
        try
        {
	    //加载默认配置文件
            ClassPathResource resource = new ClassPathResource("DispatcherServlet.properties", org/springframework/web/servlet/DispatcherServlet);
            defaultStrategies = PropertiesLoaderUtils.loadProperties(resource);
        }
    }
}

//Spring日志追踪我们可以发现,DispatcherServletd的处理适配器
org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerAdapter
org.springframework.web.servlet.mvc.SimpleControllerHandlerAdapter

下面我们来看一下RequestMappingHandlerAdapter
public class RequestMappingHandlerAdapter extends AbstractHandlerMethodAdapter
    implements BeanFactoryAware, InitializingBean
{
  //待bean属性初始化完,初始化一些ArgumentResolvers
public void afterPropertiesSet()
    {
        if(argumentResolvers == null)
        {
            List resolvers = getDefaultArgumentResolvers();
            argumentResolvers = (new HandlerMethodArgumentResolverComposite()).addResolvers(resolvers);
        }
        if(initBinderArgumentResolvers == null)
        {
            List resolvers = getDefaultInitBinderArgumentResolvers();
            initBinderArgumentResolvers = (new HandlerMethodArgumentResolverComposite()).addResolvers(resolvers);
        }
        if(returnValueHandlers == null)
        {
            List handlers = getDefaultReturnValueHandlers();
            returnValueHandlers = (new HandlerMethodReturnValueHandlerComposite()).addHandlers(handlers);
        }
	//初始化控制器增强处理,包括方法
        initControllerAdviceCache();
    }
    //获取默认的ArgumentResolvers
    private List getDefaultArgumentResolvers()
    {
        List resolvers = new ArrayList();
	//@RequestParam
        resolvers.add(new RequestParamMethodArgumentResolver(getBeanFactory(), false));
        resolvers.add(new RequestParamMapMethodArgumentResolver());
	//@PathVariable
        resolvers.add(new PathVariableMethodArgumentResolver());
        resolvers.add(new PathVariableMapMethodArgumentResolver());
	//@MatrixVariable
        resolvers.add(new MatrixVariableMethodArgumentResolver());
        resolvers.add(new MatrixVariableMapMethodArgumentResolver());
	//@ModelAttribute
        resolvers.add(new ServletModelAttributeMethodProcessor(false));
	//@ResponseBody
        resolvers.add(new RequestResponseBodyMethodProcessor(getMessageConverters()));
	//@RequestPart
        resolvers.add(new RequestPartMethodArgumentResolver(getMessageConverters()));
        //@RequestHeader
        resolvers.add(new RequestHeaderMethodArgumentResolver(getBeanFactory()));
        resolvers.add(new RequestHeaderMapMethodArgumentResolver());
        //@CookieValue
        resolvers.add(new ServletCookieValueMethodArgumentResolver(getBeanFactory()));
	//@Value
        resolvers.add(new ExpressionValueMethodArgumentResolver(getBeanFactory()));
        resolvers.add(new ServletRequestMethodArgumentResolver());
        resolvers.add(new ServletResponseMethodArgumentResolver());
        resolvers.add(new HttpEntityMethodProcessor(getMessageConverters()));
        resolvers.add(new RedirectAttributesMethodArgumentResolver());
        resolvers.add(new ModelMethodProcessor());
        resolvers.add(new MapMethodProcessor());
        resolvers.add(new ErrorsMethodArgumentResolver());
        resolvers.add(new SessionStatusMethodArgumentResolver());
        resolvers.add(new UriComponentsBuilderMethodArgumentResolver());
        if(getCustomArgumentResolvers() != null)
            resolvers.addAll(getCustomArgumentResolvers());
        resolvers.add(new RequestParamMethodArgumentResolver(getBeanFactory(), true));
        resolvers.add(new ServletModelAttributeMethodProcessor(true));
        return resolvers;
    }
     //获取默认的InitBinderArgumentResolvers
    private List getDefaultInitBinderArgumentResolvers()
    {
        List resolvers = new ArrayList();
        resolvers.add(new RequestParamMethodArgumentResolver(getBeanFactory(), false));
        resolvers.add(new RequestParamMapMethodArgumentResolver());
        resolvers.add(new PathVariableMethodArgumentResolver());
        resolvers.add(new PathVariableMapMethodArgumentResolver());
        resolvers.add(new MatrixVariableMethodArgumentResolver());
        resolvers.add(new MatrixVariableMapMethodArgumentResolver());
        resolvers.add(new ExpressionValueMethodArgumentResolver(getBeanFactory()));
        resolvers.add(new ServletRequestMethodArgumentResolver());
        resolvers.add(new ServletResponseMethodArgumentResolver());
        if(getCustomArgumentResolvers() != null)
            resolvers.addAll(getCustomArgumentResolvers());
        resolvers.add(new RequestParamMethodArgumentResolver(getBeanFactory(), true));
        return resolvers;
    }
    //获取默认的ReturnValueHandlers
    private List getDefaultReturnValueHandlers()
    {
        List handlers = new ArrayList();
        handlers.add(new ModelAndViewMethodReturnValueHandler());
        handlers.add(new ModelMethodProcessor());
        handlers.add(new ViewMethodReturnValueHandler());
        handlers.add(new HttpEntityMethodProcessor(getMessageConverters(), contentNegotiationManager));
        handlers.add(new HttpHeadersReturnValueHandler());
        handlers.add(new CallableMethodReturnValueHandler());
        handlers.add(new DeferredResultMethodReturnValueHandler());
        handlers.add(new AsyncTaskMethodReturnValueHandler(beanFactory));
        handlers.add(new ModelAttributeMethodProcessor(false));
        handlers.add(new RequestResponseBodyMethodProcessor(getMessageConverters(), contentNegotiationManager));
        handlers.add(new ViewNameMethodReturnValueHandler());
        handlers.add(new MapMethodProcessor());
        if(getCustomReturnValueHandlers() != null)
            handlers.addAll(getCustomReturnValueHandlers());
        if(!CollectionUtils.isEmpty(getModelAndViewResolvers()))
            handlers.add(new ModelAndViewResolverMethodReturnValueHandler(getModelAndViewResolvers()));
        else
            handlers.add(new ModelAttributeMethodProcessor(true));
        return handlers;
    }
     private List customArgumentResolvers;
    private HandlerMethodArgumentResolverComposite argumentResolvers;
    private HandlerMethodArgumentResolverComposite initBinderArgumentResolvers;
    private List customReturnValueHandlers;
    private HandlerMethodReturnValueHandlerComposite returnValueHandlers;
    private List modelAndViewResolvers;
    private ContentNegotiationManager contentNegotiationManager;
    private List messageConverters;
    private WebBindingInitializer webBindingInitializer;
    private AsyncTaskExecutor taskExecutor;
    private Long asyncRequestTimeout;
    private CallableProcessingInterceptor callableInterceptors[];
    private DeferredResultProcessingInterceptor deferredResultInterceptors[];
    private boolean ignoreDefaultModelOnRedirect;
    private int cacheSecondsForSessionAttributeHandlers;
    private boolean synchronizeOnSession;
    private SessionAttributeStore sessionAttributeStore;
    private ParameterNameDiscoverer parameterNameDiscoverer;
    private ConfigurableBeanFactory beanFactory;
    private final Map sessionAttributesHandlerCache = new ConcurrentHashMap(64);
    private final Map initBinderCache = new ConcurrentHashMap(64);
    private final Map initBinderAdviceCache = new LinkedHashMap();
    private final Map modelAttributeCache = new ConcurrentHashMap(64);
    private final Map modelAttributeAdviceCache = new LinkedHashMap();
    public static final org.springframework.util.ReflectionUtils.MethodFilter INIT_BINDER_METHODS = 
    new org.springframework.util.ReflectionUtils.MethodFilter() {
        //查看method是否带有@InitBinder
        public boolean matches(Method method)
        {
            return AnnotationUtils.findAnnotation(method, org/springframework/web/bind/annotation/InitBinder) != null;
        }

    };
    public static final org.springframework.util.ReflectionUtils.MethodFilter MODEL_ATTRIBUTE_METHODS = new org.springframework.util.ReflectionUtils.MethodFilter() {
        //查看method是否带有@RequestMapping和@ModelAttribute
        public boolean matches(Method method)
        {
            return AnnotationUtils.findAnnotation(method, org/springframework/web/bind/annotation/RequestMapping) == null && AnnotationUtils.findAnnotation(method, org/springframework/web/bind/annotation/ModelAttribute) != null;
        }

    };
}

下面在来看一下
RequestMappingHandlerAdapter如何处理请求的
在DispatcherServlet的请求处理函数
protected void doDispatch(HttpServletRequest request, HttpServletResponse response)  
        throws Exception  
{ 
 mv = ha.handle(processedRequest, response, mappedHandler.getHandler()); 
 }

上面的handle函数实际上是调用的AbstractHandlerMethodAdapter的方法handle
public abstract class AbstractHandlerMethodAdapter extends WebContentGenerator
    implements HandlerAdapter, Ordered
{
   //处理请求
public final ModelAndView handle(HttpServletRequest request, HttpServletResponse response, Object handler)
        throws Exception
    {
         //委托给handleInternal
        return handleInternal(request, response, (HandlerMethod)handler);
    }
    //请求内部处理,留个子类RequestMappingHandlerAdapter扩展
    protected abstract ModelAndView handleInternal(HttpServletRequest httpservletrequest, HttpServletResponse httpservletresponse, HandlerMethod handlermethod)
        throws Exception;
}

回到RequestMappingHandlerAdapter
public class RequestMappingHandlerAdapter extends AbstractHandlerMethodAdapter
    implements BeanFactoryAware, InitializingBean
{
  //请求内部处理
 protected final ModelAndView handleInternal(HttpServletRequest request, HttpServletResponse response, HandlerMethod handlerMethod)
        throws Exception
    {
        HttpSession session;
	//获取handlerMethod的会话属性,并检查请求方法是否支持
        if(getSessionAttributesHandler(handlerMethod).hasSessionAttributes())
            checkAndPrepare(request, response, cacheSecondsForSessionAttributeHandlers, true);
        else
            checkAndPrepare(request, response, true);
        if(!synchronizeOnSession)
            break MISSING_BLOCK_LABEL_85;
        session = request.getSession(false);
        if(session == null)
            break MISSING_BLOCK_LABEL_85;
        Object mutex = WebUtils.getSessionMutex(session);
        Object obj = mutex;
        JVM INSTR monitorenter ;
	//委托给invokeHandleMethod
        return invokeHandleMethod(request, response, handlerMethod);
    }
     private ModelAndView invokeHandleMethod(HttpServletRequest request, HttpServletResponse response, HandlerMethod handlerMethod)
        throws Exception
    {
       //包装request, response
        ServletWebRequest webRequest = new ServletWebRequest(request, response);
	//获取DataBinderFactory
        WebDataBinderFactory binderFactory = getDataBinderFactory(handlerMethod);
	//获取模型属性工厂
        ModelFactory modelFactory = getModelFactory(handlerMethod, binderFactory);
	//创建请求处理handler
        ServletInvocableHandlerMethod requestMappingMethod = createRequestMappingMethod(handlerMethod, binderFactory);
        //创建视图模型容器
	ModelAndViewContainer mavContainer = new ModelAndViewContainer();
        mavContainer.addAllAttributes(RequestContextUtils.getInputFlashMap(request));
        modelFactory.initModel(webRequest, mavContainer, requestMappingMethod);
        mavContainer.setIgnoreDefaultModelOnRedirect(ignoreDefaultModelOnRedirect);
	//异步请求处理
        AsyncWebRequest asyncWebRequest = WebAsyncUtils.createAsyncWebRequest(request, response);
        asyncWebRequest.setTimeout(asyncRequestTimeout);
        WebAsyncManager asyncManager = WebAsyncUtils.getAsyncManager(request);
        asyncManager.setTaskExecutor(taskExecutor);
        asyncManager.setAsyncWebRequest(asyncWebRequest);
        asyncManager.registerCallableInterceptors(callableInterceptors);
        asyncManager.registerDeferredResultInterceptors(deferredResultInterceptors);
        if(asyncManager.hasConcurrentResult())
        {
            Object result = asyncManager.getConcurrentResult();
            mavContainer = (ModelAndViewContainer)asyncManager.getConcurrentResultContext()[0];
            asyncManager.clearConcurrentResult();
            if(logger.isDebugEnabled())
                logger.debug((new StringBuilder()).append("Found concurrent result value [").append(result).append("]").toString());
            requestMappingMethod = requestMappingMethod.wrapConcurrentResult(result);
        }
	//关键在这,处理请求
        requestMappingMethod.invokeAndHandle(webRequest, mavContainer, new Object[0]);
        if(asyncManager.isConcurrentHandlingStarted())
            return null;
        else
	   //返回视图
            return getModelAndView(mavContainer, modelFactory, webRequest);
    }
    //渲染组装视图
     private ModelAndView getModelAndView(ModelAndViewContainer mavContainer, ModelFactory modelFactory, NativeWebRequest webRequest)
        throws Exception
    {
        modelFactory.updateModel(webRequest, mavContainer);
        if(mavContainer.isRequestHandled())
            return null;
        ModelMap model = mavContainer.getModel();
        ModelAndView mav = new ModelAndView(mavContainer.getViewName(), model);
        if(!mavContainer.isViewReference())
            mav.setView((View)mavContainer.getView());
        if(model instanceof RedirectAttributes)
        {
            Map flashAttributes = ((RedirectAttributes)model).getFlashAttributes();
            HttpServletRequest request = (HttpServletRequest)webRequest.getNativeRequest(javax/servlet/http/HttpServletRequest);
            RequestContextUtils.getOutputFlashMap(request).putAll(flashAttributes);
        }
        return mav;
    }
}

public class ServletInvocableHandlerMethod extends InvocableHandlerMethod
{
 public final transient void invokeAndHandle(ServletWebRequest webRequest, ModelAndViewContainer mavContainer, Object providedArgs[])
        throws Exception
    {
        Object returnValue = invokeForRequest(webRequest, mavContainer, providedArgs);
        setResponseStatus(webRequest);
        if(returnValue == null)
        {
            if(isRequestNotModified(webRequest) || hasResponseStatus() || mavContainer.isRequestHandled())
            {
                mavContainer.setRequestHandled(true);
                return;
            }
        } else
        if(StringUtils.hasText(responseReason))
        {
            mavContainer.setRequestHandled(true);
            return;
        }
        mavContainer.setRequestHandled(false);
        try
        {
            returnValueHandlers.handleReturnValue(returnValue, getReturnValueType(returnValue), mavContainer, webRequest);
        }
    }

    private HttpStatus responseStatus;
    private String responseReason;
    private HandlerMethodReturnValueHandlerComposite returnValueHandlers;

}

//InvocableHandlerMethod
public class InvocableHandlerMethod extends HandlerMethod
{
   //
public final transient Object invokeForRequest(NativeWebRequest request, ModelAndViewContainer mavContainer, Object providedArgs[])
        throws Exception
    {
        //获取方法参数
        Object args[] = getMethodArgumentValues(request, mavContainer, providedArgs);
        if(logger.isTraceEnabled())
        {
            StringBuilder sb = new StringBuilder("Invoking [");
            sb.append(getBeanType().getSimpleName()).append(".");
            sb.append(getMethod().getName()).append("] method with arguments ");
            sb.append(Arrays.asList(args));
            logger.trace(sb.toString());
        }
	//invoke处理请求对应的Controller的Method.invoke()
        Object returnValue = invoke(args);
        if(logger.isTraceEnabled())
            logger.trace((new StringBuilder()).append("Method [").append(getMethod().getName()).append("] returned [").append(returnValue).append("]").toString());
        return returnValue;
    }
    //获取方法参数
    private transient Object[] getMethodArgumentValues(NativeWebRequest request, ModelAndViewContainer mavContainer, Object providedArgs[])
        throws Exception
    {
        MethodParameter parameters[] = getMethodParameters();
        Object args[] = new Object[parameters.length];
        for(int i = 0; i < parameters.length; i++)
        {
            MethodParameter parameter = parameters[i];
            parameter.initParameterNameDiscovery(parameterNameDiscoverer);
            GenericTypeResolver.resolveParameterType(parameter, getBean().getClass());
            args[i] = resolveProvidedArgument(parameter, providedArgs);
            if(args[i] != null)
                continue;
            if(argumentResolvers.supportsParameter(parameter))
                try
                {
                    args[i] = argumentResolvers.resolveArgument(parameter, mavContainer, request, dataBinderFactory);
                    continue;
                }
        }
        return args;
    }
   //
     private transient Object invoke(Object args[])
        throws Exception
    {
        //获取权限
        ReflectionUtils.makeAccessible(getBridgedMethod());
	//触发处理方法,返回结果
        return getBridgedMethod().invoke(getBean(), args);
    }
    private WebDataBinderFactory dataBinderFactory;
    private HandlerMethodArgumentResolverComposite argumentResolvers;
    private ParameterNameDiscoverer parameterNameDiscoverer;
}

//HandlerMethod
public class HandlerMethod
{
    private class ReturnValueMethodParameter extends HandlerMethodParameter
    {

        public Class getParameterType()
        {
            return returnValue == null ? super.getParameterType() : returnValue.getClass();
        }

        private final Object returnValue;
        final HandlerMethod this$0;

        public ReturnValueMethodParameter(Object returnValue)
        {
            this$0 = HandlerMethod.this;
            super(-1);
            this.returnValue = returnValue;
        }
    }

    private class HandlerMethodParameter extends MethodParameter
    {

        public Class getContainingClass()
        {
            return getBeanType();
        }

        public Annotation getMethodAnnotation(Class annotationType)
        {
            return HandlerMethod.this.getMethodAnnotation(annotationType);
        }

        final HandlerMethod this$0;

        public HandlerMethodParameter(int index)
        {
            this$0 = HandlerMethod.this;
            super(bridgedMethod, index);
        }
    }
    public HandlerMethod(Object bean, Method method)
    {
        this.bean = bean;
        beanFactory = null;
        this.method = method;
        bridgedMethod = BridgeMethodResolver.findBridgedMethod(method);
        parameters = initMethodParameters();
    }

    public transient HandlerMethod(Object bean, String methodName, Class parameterTypes[])
        throws NoSuchMethodException
    {
        this.bean = bean;
        beanFactory = null;
        method = bean.getClass().getMethod(methodName, parameterTypes);
        bridgedMethod = BridgeMethodResolver.findBridgedMethod(method);
        parameters = initMethodParameters();
    }

    public HandlerMethod(String beanName, BeanFactory beanFactory, Method method)
    {
        bean = beanName;
        this.beanFactory = beanFactory;
        this.method = method;
        bridgedMethod = BridgeMethodResolver.findBridgedMethod(method);
        parameters = initMethodParameters();
    }

    private HandlerMethod(HandlerMethod handlerMethod, Object handler)
    {
        bean = handler;
        beanFactory = handlerMethod.beanFactory;
        method = handlerMethod.method;
        bridgedMethod = handlerMethod.bridgedMethod;
        parameters = handlerMethod.parameters;
    }
    //获取处理bean-Conroller
      public Object getBean()
    {
        return bean;
    }
    //获取处理方法
    protected Method getBridgedMethod()
    {
        return bridgedMethod;
    }
    //获取方法参数
    public MethodParameter[] getMethodParameters()
    {
        return parameters;
    }
    protected final Log logger;
    private final Object bean;
    private final BeanFactory beanFactory;
    private final Method method;
    private final Method bridgedMethod;
    private final MethodParameter parameters[];
}

//MethodParameter
public class MethodParameter
{

    public MethodParameter(Method method, int parameterIndex)
    {
        this(method, parameterIndex, 1);
    }

    public MethodParameter(Method method, int parameterIndex, int nestingLevel)
    {
        this.nestingLevel = 1;
        Assert.notNull(method, "Method must not be null");
        this.method = method;
        this.parameterIndex = parameterIndex;
        this.nestingLevel = nestingLevel;
        constructor = null;
    }

    public MethodParameter(Constructor constructor, int parameterIndex)
    {
        this(constructor, parameterIndex, 1);
    }

    public MethodParameter(Constructor constructor, int parameterIndex, int nestingLevel)
    {
        this.nestingLevel = 1;
        Assert.notNull(constructor, "Constructor must not be null");
        this.constructor = constructor;
        this.parameterIndex = parameterIndex;
        this.nestingLevel = nestingLevel;
        method = null;
    }
   private final Method method;
    private final Constructor constructor;
    private final int parameterIndex;
    private Class containingClass;
    private Class parameterType;
    private Type genericParameterType;
    private Annotation parameterAnnotations[];
    private ParameterNameDiscoverer parameterNameDiscoverer;
    private String parameterName;
    private int nestingLevel;
    Map typeIndexesPerLevel;
}