spring源码适配器模式
在Spring框架中,使用了许多设计模式,其中适配器模式是比较常用的一种。以下是在 Spring 框架中使用适配器模式的几个典型代码片段:
HandlerAdapter
适配器接口及其实现类
这个适配器在 Spring MVC 框架中用于将不同类型的处理器适配为统一的处理器调用接口,其部分源码如下:
public interface HandlerAdapter {
boolean supports(Object handler);
ModelAndView handle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception;
}
public class SimpleControllerHandlerAdapter implements HandlerAdapter {
public boolean supports(Object handler) {
return (handler instanceof Controller);
}
public ModelAndView handle(HttpServletRequest request, HttpServletResponse response, Object handler)
throws Exception {
...//适配过程的具体实现
}
}
MessageListenerAdapter
适配器类
在使用 Spring 框架进行 JMS 消息监听时,需要将消息监听器适配为一个带有固定方法名的处理器。此时,可以使用 MessageListenerAdapter
适配器完成适配,其部分源码如下:
public class MessageListenerAdapter implements MessageListener {
...//省略其他代码
public void onMessage(Message message) {
try {
Object delegate = getDelegate();
if (!(delegate instanceof MessageListener)) {
throw new IllegalStateException("No 'delegate' specified - invoke 'setDelegate' before attempting any operations");
}
doInvoke((MessageListener) delegate, getSession(), message);
}
catch (JMSException ex) {
...//省略异常处理代码
}
}
private void doInvoke(MessageListener listener, Session session, Message message) throws JMSException {
Object result = null;
try {
result = getHandler().invoke(listener, new Object[] {message});
}
catch (InvocationTargetException ex) {
...//省略异常处理代码
}
}
...//省略其他代码
}
在使用时,只需要给 MessageListenerAdapter
适配器设置一个消息监听器对象作为其委托即可。
ServletRequestDataBinder
适配器类
在 Spring MVC 框架中,用户提交的表单数据需要进行类型转换、格式化等操作后才能进行进一步处理。ServletRequestDataBinder
就是用来完成这个过程的适配器类,其部分源码如下:
public class ServletRequestDataBinder extends WebDataBinder {
...//省略其他代码
protected void addBindValues(MutablePropertyValues mpvs, ServletRequest request) {
HttpServletRequest req = (HttpServletRequest) request;
HttpSession session = req.getSession(false);
Enumeration paramNames = req.getParameterNames();
while (paramNames.hasMoreElements()) {
String paramName = (String) paramNames.nextElement();
if (!isBindExceptionRequired(paramName)) {
continue;
}
String[] values = req.getParameterValues(paramName);
if (values.length == 0) {
// Do nothing, no values found at all.
}
else if (values.length > 1) {
addBindValue(mpvs, paramName, values);
}
else {
addBindValue(mpvs, paramName, values[0]);
}
}
...//省略其他代码
}
...//省略其他代码
}
在处理时,只需要将用户提交的表单数据和对应的 JavaBean 绑定到 ServletRequestDataBinder
适配器中,即可完成参数适配工作。
这些是 Spring 框架中使用适配器模式的几个典型例子,它们都在不同场景下完成了类型适配、方法适配等功能。