springmvc根据请求uri获取handlermapping源码
springmvc根据请求uri获取handlermapping源码
org.springframework.web.servlet.handler.AbstractHandlerMapping#getHandler
org.springframework.web.servlet.DispatcherServlet#getHandler
public final HandlerExecutionChain getHandler(HttpServletRequest request) throws Exception { Object handler = getHandlerInternal(request); if (handler == null) { handler = getDefaultHandler(); } if (handler == null) { return null; } // Bean name or resolved handler? if (handler instanceof String) { String handlerName = (String) handler; handler = obtainApplicationContext().getBean(handlerName); } HandlerExecutionChain executionChain = getHandlerExecutionChain(handler, request); if (logger.isTraceEnabled()) { logger.trace("Mapped to " + handler); } else if (logger.isDebugEnabled() && !request.getDispatcherType().equals(DispatcherType.ASYNC)) { logger.debug("Mapped to " + executionChain.getHandler()); } if (hasCorsConfigurationSource(handler) || CorsUtils.isPreFlightRequest(request)) { CorsConfiguration config = (this.corsConfigurationSource != null ? this.corsConfigurationSource.getCorsConfiguration(request) : null); CorsConfiguration handlerConfig = getCorsConfiguration(handler, request); config = (config != null ? config.combine(handlerConfig) : handlerConfig); executionChain = getCorsHandlerExecutionChain(request, executionChain, config); } return executionChain; }
此处定义个三个controller,分别采用springmvc实现controller的三种方式。如下所示。
@Component("/handlercontroller.do")
public class HandlerController implements HttpRequestHandler {
@Override
public void handleRequest(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
System.out.println("111");
}
}
@Component("/implController.do")
public class ImplController implements Controller {
@Override
public ModelAndView handleRequest(HttpServletRequest request, HttpServletResponse response) throws Exception {
System.out.println("实现Controller接口");
return new ModelAndView("index");
}
}
@Controller
public class TestController {
/**
* 访问普通的字符串,试图解析器会解析成对应的页面
* @return
*/
@RequestMapping("/str.do")
public Object Test(){
return "index";
}
/**
* 因为返回值是一个对象,所以如果不做特殊处理,则试图解析器无法解析
* 对象嵌套是一个难点
* @param name
* @param request
* @param response
* @return
*/
@RequestMapping("/model.do")
@ResponseBody
public Object modeltest(String name, HttpServletRequest request, HttpServletResponse response){
System.out.println("调用了modeltest");
String req_name = request.getParameter("name");
Map hashMap = new HashMap<>();
hashMap.put("key", "value");
return hashMap;
}
}
现在依次测试
断点:

先访问:http://localhost/model.do

从getHandlerInternal(request)已经获取到handler
第二次测试地址:http://localhost/handlercontroller.do
进行代码跟踪发现程序在遍历三个handleMappings,分别是:RequestMappingHandlerMapping、BeanNameUrlHandlerMapping、RouterFunctionMapping
此时RequestMappingHandlerMapping未空,所以遍历到BeanNameUrlHandlerMapping,因为这次访问的uri的定义方式是实现HttpRequestHandler接口。

此时已经找到了匹配的handler。
第三次访问地址:http://localhost/implController.do

可以看到,与第二次访问所获取handler的对象是同一个。

浙公网安备 33010602011771号