• SpringMVC(四):什么是HandlerAdapter


    一、什么是HandlerAdapter

    Note that a handler can be of type Object. This is to enable handlers from other frameworks to be integrated with this framework without custom coding.

    boolean supports(Object handler)


    Given a handler instance, return whether or not this HandlerAdapter can support it.

     HandlerAdapter 接口实现类:

    1. HttpRequestHandlerAdapter : 要求handler实现HttpRequestHandler接口

    public class HttpRequestHandlerAdapter implements HandlerAdapter {
    
        @Override
        public boolean supports(Object handler) {
            return (handler instanceof HttpRequestHandler);
        }
    
        @Override
        public ModelAndView handle(HttpServletRequest request, HttpServletResponse response, Object handler)
                throws Exception {
    
            ((HttpRequestHandler) handler).handleRequest(request, response);
            return null;
        }
    
        @Override
        public long getLastModified(HttpServletRequest request, Object handler) {
            if (handler instanceof LastModified) {
                return ((LastModified) handler).getLastModified(request);
            }
            return -1L;
        }
    
    }


    2. SimpleControllerHandlerAdapter:要求handler实现Controller接口,该接口的方法参数为ModelAndView 

    public class SimpleControllerHandlerAdapter implements HandlerAdapter {
    
        @Override
        public boolean supports(Object handler) {
            return (handler instanceof Controller);
        }
    
        @Override
        public ModelAndView handle(HttpServletRequest request, HttpServletResponse response, Object handler)
                throws Exception {
    
            return ((Controller) handler).handleRequest(request, response);
        }
    
        @Override
        public long getLastModified(HttpServletRequest request, Object handler) {
            if (handler instanceof LastModified) {
                return ((LastModified) handler).getLastModified(request);
            }
            return -1L;
        }
    
    }


    3. AbstracthandlerMethodAdapter的handle()使用模板方法,调用子类handleInternal()实现

        @Override
        public final boolean supports(Object handler) {
            return (handler instanceof HandlerMethod && supportsInternal((HandlerMethod) handler));
        }
    
        protected abstract boolean supportsInternal(HandlerMethod handlerMethod);
    
    
        @Override
        public final ModelAndView handle(HttpServletRequest request, HttpServletResponse response, Object handler)
                throws Exception {
    
            return handleInternal(request, response, (HandlerMethod) handler);
        }
    
    
        protected abstract ModelAndView handleInternal(HttpServletRequest request,
                HttpServletResponse response, HandlerMethod handlerMethod) throws Exception;


    AbstracthandlerMethodAdapter及其子类RequestMappingHandlerAdapter的supportsInternal()方法

        /**
         * Always return {@code true} since any method argument and return value
         * type will be processed in some way. A method argument not recognized
         * by any HandlerMethodArgumentResolver is interpreted as a request parameter
         * if it is a simple type, or as a model attribute otherwise. A return value
         * not recognized by any HandlerMethodReturnValueHandler will be interpreted
         * as a model attribute.
         */
        @Override
        protected boolean supportsInternal(HandlerMethod handlerMethod) {
            return true;
        }

     二、什么是HandlerMethod:封装了请求处理方法的参数和返回值,及该方法上的注解

    Encapsulates information about a handler method consisting of a method and a bean. Provides convenient access to method parameters, the method return value, method annotations, etc.

    The class may be created with a bean instance or with a bean name (e.g. lazy-init bean, prototype bean).

    Use createWithResolvedBean() to obtain a HandlerMethod instance with a bean instance resolved through the associated BeanFactory.

    三、什么时候使用HandlerAdapter

    1. DispatchServlet protected void doDispatch()方法会获取相应的HandlerAdapter

                    // Determine handler adapter for the current request.
                    HandlerAdapter ha = getHandlerAdapter(mappedHandler.getHandler());
                    mv = ha.handle(processedRequest, response, mappedHandler.getHandler());

    在以前的文章中,已经说过RequestMappingHandlerAdapter是处理输入输出的关键点,也是spring根据相应的路径查找对应的处理器的关键点

    RequestMappingHandlerAdapter的handleInternal()会调用invokeHandlerMethod()

        protected ModelAndView invokeHandlerMethod(HttpServletRequest request,
                HttpServletResponse response, HandlerMethod handlerMethod) throws Exception {
    
            ServletWebRequest webRequest = new ServletWebRequest(request, response);
            try {
                WebDataBinderFactory binderFactory = getDataBinderFactory(handlerMethod);
                ModelFactory modelFactory = getModelFactory(handlerMethod, binderFactory);
            //创建ServletInvocableHandlerMethod
                ServletInvocableHandlerMethod invocableMethod = createInvocableHandlerMethod(handlerMethod);
                invocableMethod.setHandlerMethodArgumentResolvers(this.argumentResolvers);
                invocableMethod.setHandlerMethodReturnValueHandlers(this.returnValueHandlers);
                invocableMethod.setDataBinderFactory(binderFactory);
                invocableMethod.setParameterNameDiscoverer(this.parameterNameDiscoverer);
    
                ModelAndViewContainer mavContainer = new ModelAndViewContainer();
                mavContainer.addAllAttributes(RequestContextUtils.getInputFlashMap(request));
                modelFactory.initModel(webRequest, mavContainer, invocableMethod);
                mavContainer.setIgnoreDefaultModelOnRedirect(this.ignoreDefaultModelOnRedirect);
    
                AsyncWebRequest asyncWebRequest = WebAsyncUtils.createAsyncWebRequest(request, response);
                asyncWebRequest.setTimeout(this.asyncRequestTimeout);
    
                WebAsyncManager asyncManager = WebAsyncUtils.getAsyncManager(request);
                asyncManager.setTaskExecutor(this.taskExecutor);
                asyncManager.setAsyncWebRequest(asyncWebRequest);
                asyncManager.registerCallableInterceptors(this.callableInterceptors);
                asyncManager.registerDeferredResultInterceptors(this.deferredResultInterceptors);
    
                if (asyncManager.hasConcurrentResult()) {
                    Object result = asyncManager.getConcurrentResult();
                    mavContainer = (ModelAndViewContainer) asyncManager.getConcurrentResultContext()[0];
                    asyncManager.clearConcurrentResult();
                    if (logger.isDebugEnabled()) {
                        logger.debug("Found concurrent result value [" + result + "]");
                    }
                    invocableMethod = invocableMethod.wrapConcurrentResult(result);
                }
                //调用
                invocableMethod.invokeAndHandle(webRequest, mavContainer);
                if (asyncManager.isConcurrentHandlingStarted()) {
                    return null;
                }
    
                return getModelAndView(mavContainer, modelFactory, webRequest);
            }
            finally {
                webRequest.requestCompleted();
            }
        }

    3.一个请求过来时,InvocableHandlerMethod的执行变量

    从上面的分析看到,处理请求时,会调用invokeAndHandle(),最终是doInvoke执行 

    4.  疑问:这些HandlerMethond是什么时候载入系统的

    解答:系统启动的时候执行registerHandlerMethod()方法,创建HandlerMethod实例

    三、HandlerMapping VS HandlerAdapter

    The strategy interface HandlerAdapter takes the role of invoking handler methods selected by some HandlerMapping.

  • 相关阅读:
    求职方法论
    测试经验与教训_学习笔记
    测试架构师修炼之道_学习笔记
    Jmeter测试oracle
    Jmeter 非UI界面jmx脚本不能正常退出
    Jmeter参数化的理解
    jmeter 测试并发
    Jmeter测试数据库
    pytorch runtime error: CUDNN_STATUS_MAPPING_ERROR
    Python/pytorch 切换国内源/AttributeError: module 'torch.jit' has no attribute 'unused'/not a trusted or secure host
  • 原文地址:https://www.cnblogs.com/yuyutianxia/p/8622923.html
Copyright © 2020-2023  润新知