zoukankan      html  css  js  c++  java
  • 基于SpringMVC的全局异常处理器介绍(转)

    近几天又温习了一下SpringMVC的运行机制以及原理

    我理解的springmvc,是设计模式MVC中C层,也就是Controller(控制)层,常用的注解有@Controller、@RequestMapping、@Autowared、@Component,今天呢,我所要写的是SpringMVC的全局异常处理器,关联的接口有HandlerExceptionResolver(Eclipse用户可以按Ctrl+Shift+T进行搜索该接口),什么是全局异常处理器?为什么要用它呢?

    在企业开发中,各种的Runtime异常可能会让我们崩溃,但是还有一部分异常在此之外,因此我们就要捕获它,然后进行操作提示(将错误提示返回到ModelAndView)

    下来呢,我贴一部分代码

    首先呢,创建一个自定义的异常类

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    /**
     * @Title: ExceptionCustom.java
     * @Description: 本地异常
     * @author ChoviWu
     * @version V1.0
     */
    public class ExceptionCustom extends Exception{
     
     /**
     * @Fields serialVersionUID :
     */
     private static final long serialVersionUID = 1L;
     private String message;
     
     /**
      * @return the message
      */
     public String getMessage() {
      return message;
     }
     
     /**
      * @param message the message to set
      */
     public void setMessage(String message) {
      this.message = message;
     }
     
     public ExceptionCustom() {
      super();
      // TODO Auto-generated constructor stub
     }
     
     public ExceptionCustom(String message) {
      super(message);
      this.message = message;
     }
    }

    创建一个全局异常处理器的类,让它实现HandlerExceptionResolver 接口。相信,基础好一点的同学可以看出来我代码的意思(注释)

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    import javax.servlet.http.HttpServletRequest;
    import javax.servlet.http.HttpServletResponse;
     
    import org.apache.log4j.Logger;
    org.springframework.web.servlet.HandlerExceptionResolver;
    import org.springframework.web.servlet.ModelAndView;
     
    /**
     * @Title: SimpleException.java
     * @Description:全局异常处理器
     * @author ChoviWu
     * @version V1.0
     */
    public class SimpleExceptionResolver implements HandlerExceptionResolver {
     
     // 异常对象
     ExceptionCustom exceptionCustom = null;
     
     private Logger logger = Logger.getLogger(SimpleExceptionResolver.class
       .getSimpleName());
     
     /**
      * 全局处理异常
      */
     public ModelAndView resolveException(HttpServletRequest request,
       HttpServletResponse response, Object handler, Exception ex) {
      //转化为自定义异常
      exceptionCustom = (ExceptionCustom) ex;
      //判断是否是本地异常
      if (ex instanceof ExceptionCustom) {
       logger.info(ex.getMessage());
      } else {
       …抛出错误
      }
      //获取异常信息
      String message = exceptionCustom.getMessage();
      ModelAndView mv = new ModelAndView();
      //将异常返回到Model
      mv.addObject("xx", message);
      // 指向错误页面
      mv.setViewName("error");
      return null;
     }
     
    }

    解释一下,在判断一个异常是否是其他异常的时候,先看它是否属于本地异常(Exception)的exceptionCustom ,如果是本地异常,则抛出本地异常信息

    1
    2
    3
    4
    5
    if (ex instanceof ExceptionCustom) {
       logger.info(ex.getMessage());
      } else {
       …抛出错误
      }

    如果不是本地异常,则抛出未知异常

    然后从异常里面获取异常信息,将异常信息返回到MV中,最后转至页面,当然严谨一点的,会将异常信息添加到数据库中,方便查看

    由于本文章只是一个Demo,所以没有考虑到很多因素

    下来,说说配置文件

    配置文件,先贴上代码,然后再做解释

    1
    2
    <!-- 全局异常处理器 -->
    <bean id="handlerExceptionResolver" class = "xxxx(包名).SimpleExceptionResolver"/>

    注意:首先,这个bean将配置在自己的web层.xml(spring-web.xml),当启动tomcat,加载web.xml后需加载spring-web.xml

    之前注入的bean的id我随便写了一个名称,然后spring解析的时候报错了,

    之后看了源码的时候,才知道原来是这么回事

    1
    2
    1SpringMVC 在org.springframework.web.servlet.DispatcherServlet类中声明了
    public static final String HANDLER_EXCEPTION_RESOLVER_BEAN_NAME = "handlerExceptionResolver";
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    private void initHandlerExceptionResolvers(ApplicationContext context) {
      this.handlerExceptionResolvers = null;
     
      if (this.detectAllHandlerExceptionResolvers) {
       // Find all HandlerExceptionResolvers in the ApplicationContext, including ancestor contexts.
       Map<String, HandlerExceptionResolver> matchingBeans = BeanFactoryUtils
         .beansOfTypeIncludingAncestors(context, HandlerExceptionResolver.class, true, false);
       if (!matchingBeans.isEmpty()) {
        this.handlerExceptionResolvers = new ArrayList<HandlerExceptionResolver>(matchingBeans.values());
        // We keep HandlerExceptionResolvers in sorted order.
        OrderComparator.sort(this.handlerExceptionResolvers);
       }
      }
      else {
       try {
        HandlerExceptionResolver her =
          context.getBean(HANDLER_EXCEPTION_RESOLVER_BEAN_NAME, HandlerExceptionResolver.class);
        this.handlerExceptionResolvers = Collections.singletonList(her);
       }
       catch (NoSuchBeanDefinitionException ex) {
        // Ignore, no HandlerExceptionResolver is fine too.
       }
      }

    看完这段代码的同学应该就知道为什么把bean 的id 设置成handlerExceptionResolver了吧

    1
    HandlerExceptionResolver her =context.getBean(HANDLER_EXCEPTION_RESOLVER_BEAN_NAME, HandlerExceptionResolver.class);

    所以说,全局异常处理器的bean的id不能随便的设置。

    原文链接:https://www.jb51.net/article/119042.htm

  • 相关阅读:
    第四十三课:jQuery插件化
    js模块化开发
    第四十二课:基于CSS的动画引擎
    第四十一课:CSS3 animation详解
    第四十课:CSS3 transition详解
    第三十九课:requestAnimationFrame详解
    几种排序
    图与搜索
    数组
    链表
  • 原文地址:https://www.cnblogs.com/muxi0407/p/11607743.html
Copyright © 2011-2022 走看看