HandlerMapping的作用
HandlerMapping的主要作用是注冊(cè)Handler和獲取Handler延曙。
注冊(cè)Handler
HandleMapping注冊(cè)Handler發(fā)生在SpringMVC容器啟動(dòng)的過程中,在注冊(cè)Handler的同時(shí)也初始化攔截器田度。
注冊(cè)Handle源碼走讀
//AbstractDetectingUrlHandlerMapping類中initApplicationContext()方法
public void initApplicationContext() throws ApplicationContextException {
//初始化攔截器
super.initApplicationContext();
//注冊(cè)處理器
detectHandlers();
}
//AbstractHandlerMapping類中initApplicationContext()實(shí)現(xiàn)
protected void initApplicationContext() throws BeansException {
extendInterceptors(this.interceptors);
detectMappedInterceptors(this.mappedInterceptors);
initInterceptors();
}
//AbstractDetectingUrlHandlerMapping類中detectHandlers()實(shí)現(xiàn)
protected void detectHandlers() throws BeansException {
if (logger.isDebugEnabled()) {
logger.debug("Looking for URL mappings in application context: " + getApplicationContext());
}
String[] beanNames = (this.detectHandlersInAncestorContexts ?
BeanFactoryUtils.beanNamesForTypeIncludingAncestors(getApplicationContext(), Object.class) :
getApplicationContext().getBeanNamesForType(Object.class));
// Take any bean name that we can determine URLs for.
for (String beanName : beanNames) {
String[] urls = determineUrlsForHandler(beanName);
if (!ObjectUtils.isEmpty(urls)) {
// URL paths found: Let's consider it a handler.
registerHandler(urls, beanName);
}
else {
if (logger.isDebugEnabled()) {
logger.debug("Rejected bean name '" + beanName + "': no URL paths identified");
}
}
}
}
//BeanNameUrlHandlerMapping類中determineUrlsForHandler()實(shí)現(xiàn)
//獲取以"/"開頭的beanName
protected String[] determineUrlsForHandler(String beanName) {
List<String> urls = new ArrayList<String>();
if (beanName.startsWith("/")) {
urls.add(beanName);
}
String[] aliases = getApplicationContext().getAliases(beanName);
for (String alias : aliases) {
if (alias.startsWith("/")) {
urls.add(alias);
}
}
return StringUtils.toStringArray(urls);
}
//AbstractUrlHandlerMapping類中實(shí)現(xiàn)
protected void registerHandler(String[] urlPaths, String beanName) throws BeansException, IllegalStateException {
Assert.notNull(urlPaths, "URL path array must not be null");
for (String urlPath : urlPaths) {
//注冊(cè)處理器
registerHandler(urlPath, beanName);
}
}
//AbstractUrlHandlerMapping類中registerHandler()實(shí)現(xiàn)
protected void registerHandler(String urlPath, Object handler) throws BeansException, IllegalStateException {
Assert.notNull(urlPath, "URL path must not be null");
Assert.notNull(handler, "Handler object must not be null");
Object resolvedHandler = handler;
// Eagerly resolve handler if referencing singleton via name.
if (!this.lazyInitHandlers && handler instanceof String) {
String handlerName = (String) handler;
if (getApplicationContext().isSingleton(handlerName)) {
resolvedHandler = getApplicationContext().getBean(handlerName);
}
}
//mappedHandler為保存處理器的map,key值為請(qǐng)求地址(/hello)
Object mappedHandler = this.handlerMap.get(urlPath);
if (mappedHandler != null) {
if (mappedHandler != resolvedHandler) {
throw new IllegalStateException(
"Cannot map " + getHandlerDescription(handler) + " to URL path [" + urlPath +
"]: There is already " + getHandlerDescription(mappedHandler) + " mapped.");
}
}
else {
if (urlPath.equals("/")) {
if (logger.isInfoEnabled()) {
logger.info("Root mapping to " + getHandlerDescription(handler));
}
setRootHandler(resolvedHandler);
}
else if (urlPath.equals("/*")) {
if (logger.isInfoEnabled()) {
logger.info("Default mapping to " + getHandlerDescription(handler));
}
setDefaultHandler(resolvedHandler);
}
else {
this.handlerMap.put(urlPath, resolvedHandler);
if (logger.isInfoEnabled()) {
logger.info("Mapped URL path [" + urlPath + "] onto " + getHandlerDescription(handler));
}
}
}
}
獲取Handler
獲取Handler其實(shí)獲取的是HandlerExecutionChain湾宙,HandlerExecutionChain包括一個(gè)Handler和一組攔截器樟氢。
獲取Handle源碼走讀
//AbstractHandlerMapping類中g(shù)etHandler()實(shí)現(xiàn)
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 = getApplicationContext().getBean(handlerName);
}
//獲取HandlerExecutionChain
return getHandlerExecutionChain(handler, request);
}
//AbstractHandlerMapping類中g(shù)etHandlerExecutionChain()實(shí)現(xiàn)
protected HandlerExecutionChain getHandlerExecutionChain(Object handler, HttpServletRequest request) {
HandlerExecutionChain chain = (handler instanceof HandlerExecutionChain ?
(HandlerExecutionChain) handler : new HandlerExecutionChain(handler));
//將<bean <property>>配置的攔截器添加到對(duì)應(yīng)的攔截器List中
chain.addInterceptors(getAdaptedInterceptors());
String lookupPath = this.urlPathHelper.getLookupPathForRequest(request);
for (MappedInterceptor mappedInterceptor : this.mappedInterceptors) {
if (mappedInterceptor.matches(lookupPath, this.pathMatcher)) {
//<mvc:interceptors>都會(huì)被解析成MappedInterceptor
chain.addInterceptor(mappedInterceptor.getInterceptor());
}
}
return chain;
}