SpringMVC中为什么要用装饰者模式来处理Handler

1、前言

在SpringMVC中,我们都知道有HandlerAdapter组件的存在,虽然在我们的日常使用中并不会感知到它的存在,不过有些人也可能遇到过如下bug:

No adapter for handler [xxx]: The DispatcherServlet configuration
 needs to include a HandlerAdapter that supports this handler

今天我们就来聊聊,关于SpringMVC中HandlerAdapter组件的作用以及为什么要使用装饰者模式。

2、为什么要使用装饰者模式

SpringMVC在DispatchServlet的doDispatch方法中,对HandlerMapping接口获取到的Handler使用装饰者模式进行了处理,使其变成了HandlerAdapter类型:

// Determine handler for the current request.
mappedHandler = getHandler(processedRequest);
if (mappedHandler == null || mappedHandler.getHandler() == null) {
	noHandlerFound(processedRequest, response);
	return;
}
// Determine handler adapter for the current request.
HandlerAdapter ha = getHandlerAdapter(mappedHandler.getHandler());

在此之前有一点需要说一下,handler实际上就是真正处理业务逻辑的方法,比如下面的例子中,hello方法就是我们的handler:

@GetMapping("/hello")
public String hello(){
	//……doSomething
}

从源码中我们可以看到,SpringMVC在getHandlerInternal方法中,得到的其实是一个object类型。

在这里插入图片描述
虽然getHandler方法最终给我们返回的是HandlerExecutionChain,但这只是因为封装了拦截器链,并不影响handler是object类型的实质。

但是在最终我们是需要通过反射来调用handler实现业务的调用,object类型很明显没办法实现这个效果。

如果handler有统一接口的话倒还好说,但是handler不仅没有统一接口,而且实现类还不止一个:

  1. Controller接口
  2. HttpRequestHandler 接口
  3. HttpServlet 接口
  4. @RequestMapping方法注解

当dispatchServlet获取当对应的Handler之后如何调用呢?调用其哪个方法?
这里有两种解决办法:
一是用instanceof 判断Handler 类型然后调用相关方法 。
二是通过引入适配器实现,每个适配器实现对指定Handler的调用。

SpringMVC采用的是后者。

3、HandlerAdapter简述

HandlerAdapter的实现类除去废弃和抽象之外,实现类有如下四个,分别对应上述的四个

在这里插入图片描述
关于SpringMVC是怎么通过HandlerAdapter来解决上面问题的,有兴趣的读者可以自己去看看源码,这里不作描述。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值