全局异常处理

原创 2018年04月16日 13:43:52

Spring 统一异常处理有 3 种方式,分别为:

1.使用 @ ExceptionHandler 注解

2.实现 HandlerExceptionResolver 接口

3.使用 @controlleradvice 注解

我们知道,系统中异常包括:编译时异常和运行时异常RuntimeException,前者通过捕获异常从而获取异常信息,后者主要通过规范代码开发、测试通过手段减少运行时异常的发生。在开发中,不管是dao层、service层还是controller层,都有可能抛出异常,在springmvc中,能将所有类型的异常处理从各处理过程解耦出来,既保证了相关处理过程的功能较单一,也实现了异常信息的统一处理和维护。

处理思路

如上图所示,系统的dao、service、controller出现异常都通过throws Exception向上抛出,最后由springmvc前端控制器交由异常处理器进行异常处理。springmvc提供全局异常处理器(一个系统只有一个异常处理器)进行统一异常处理。

全局异常处理器
整个系统只有一个,
使用方法:
1)需要实现一个接口
HandlerExceptionResolver
2)需要在springmvc中配置。

处理逻辑:
捕获整个系统中发生的异常。
1、异常写入日志文件
2、及时通知开发人员。发邮件、短信。
展示一个错误页面,例如:您的网络故障,请重试。

====================项目中的应用================


我们进行处理:

public class GlobalExceptionResolver implements HandlerExceptionResolver {
	public static final Logger logger= LoggerFactory.getLogger(GlobalExceptionResolver.class);
	@Override
	public ModelAndView resolveException(HttpServletRequest request, HttpServletResponse response, Object handler,
			Exception ex) {
		//1.打印控制台
		ex.printStackTrace();
		//2.写日志
		logger.error("系统发生异常",ex);
		//3.发邮件,发短信
		//使用jmail工具包
		//4.给用户展示友好界面
		ModelAndView modelandView = new ModelAndView();
		modelandView.setViewName("error/exception");
		return modelandView;
	}
}
<!-- 全局异常处理器 -->
<bean class="cn.e3mall.search.controller.GlobalExceptionResolver"/>


日志文件记录:

[INFO ] 2018-04-16 13:55:47,280 org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerAdapter     - Looking for @ControllerAdvice: WebApplicationContext for namespace 'e3-search-web-servlet': startup date [Mon Apr 16 13:55:42 CST 2018]; root of context hierarchy
 [INFO ] 2018-04-16 13:55:47,358 org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerAdapter     - Looking for @ControllerAdvice: WebApplicationContext for namespace 'e3-search-web-servlet': startup date [Mon Apr 16 13:55:42 CST 2018]; root of context hierarchy
 [INFO ] 2018-04-16 13:55:47,562 org.springframework.web.servlet.DispatcherServlet     - FrameworkServlet 'e3-search-web': initialization completed in 4986 ms
 [ERROR] 2018-04-16 13:56:57,774 cn.e3mall.search.controller.GlobalExceptionResolver     - 系统发生异常
 java.lang.ArithmeticException: / by zero
	at cn.e3mall.search.controller.SearchController.searchItemList(SearchController.java:42)
	at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
	at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
	at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
	at java.lang.reflect.Method.invoke(Method.java:498)
	at org.springframework.web.method.support.InvocableHandlerMethod.doInvoke(InvocableHandlerMethod.java:222)
	at org.springframework.web.method.support.InvocableHandlerMethod.invokeForRequest(InvocableHandlerMethod.java:137)
	at org.springframework.web.servlet.mvc.method.annotation.ServletInvocableHandlerMethod.invokeAndHandle(ServletInvocableHandlerMethod.java:110)
	at org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerAdapter.invokeHandlerMethod(RequestMappingHandlerAdapter.java:814)
	at org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerAdapter.handleInternal(RequestMappingHandlerAdapter.java:737)
	at org.springframework.web.servlet.mvc.method.AbstractHandlerMethodAdapter.handle(AbstractHandlerMethodAdapter.java:85)
	at org.springframework.web.servlet.DispatcherServlet.doDispatch(DispatcherServlet.java:959)
	at org.springframework.web.servlet.DispatcherServlet.doService(DispatcherServlet.java:893)
	at org.springframework.web.servlet.FrameworkServlet.processRequest(FrameworkServlet.java:969)
	at org.springframework.web.servlet.FrameworkServlet.doGet(FrameworkServlet.java:860)
	at javax.servlet.http.HttpServlet.service(HttpServlet.java:621)
	at org.springframework.web.servlet.FrameworkServlet.service(FrameworkServlet.java:845)
	at javax.servlet.http.HttpServlet.service(HttpServlet.java:728)
	at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:305)
	at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:210)
	at org.apache.tomcat.websocket.server.WsFilter.doFilter(WsFilter.java:51)
	at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:243)
	at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:210)
	at org.springframework.web.filter.CharacterEncodingFilter.doFilterInternal(CharacterEncodingFilter.java:121)
	at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:107)
	at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:243)
	at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:210)
	at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:222)
	at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:123)
	at org.apache.catalina.authenticator.AuthenticatorBase.invoke(AuthenticatorBase.java:502)
	at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:171)
	at org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:100)
	at org.apache.catalina.valves.AccessLogValve.invoke(AccessLogValve.java:953)
	at org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:118)
	at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:408)
	at org.apache.coyote.http11.AbstractHttp11Processor.process(AbstractHttp11Processor.java:1041)
	at org.apache.coyote.AbstractProtocol$AbstractConnectionHandler.process(AbstractProtocol.java:603)
	at org.apache.tomcat.util.net.JIoEndpoint$SocketProcessor.run(JIoEndpoint.java:310)
	at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1149)
	at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:624)
	at java.lang.Thread.run(Thread.java:748)

 springmvc中自带了一个异常处理器叫SimpleMappingExceptionResolver,该处理器实现了HandlerExceptionResolver 接口,全局异常处理器都需要实现该接口。我们要使用这个自带的异常处理器,首先得在springmvc.xml文件中配置该处理器:

<!-- springmvc提供的简单异常处理器 -->
<bean class="org.springframework.web.servlet.handler.SimpleMappingExceptionResolver">
     <!-- 定义默认的异常处理页面 -->
    <property name="defaultErrorView" value="/WEB-INF/jsp/error.jsp"/>
    <!-- 定义异常处理页面用来获取异常信息的变量名,也可不定义,默认名为exception --> 
    <property name="exceptionAttribute" value="ex"/>
    <!-- 定义需要特殊处理的异常,这是重要点 --> 
    <property name="exceptionMappings">
        <props>
            <prop key="ssm.exception.CustomException">/WEB-INF/jsp/custom_error.jsp</prop>
        </props>
        <!-- 还可以定义其他的自定义异常 -->
    </property>
</bean>
从上面的配置来看,最重要的是要配置特殊处理的异常,这些异常一般都是我们自定义的,根据实际情况来自定义的异常,然后也会跳转到不同的错误显示页面显示不同的错误信息。这里就用一个自定义异常CustomException来说明问题,定义如下:
//定义一个简单的异常类
public class CustomException extends Exception {
    //异常信息
    public String message;

    public CustomException(String message) {
        super(message);
        this.message = message;
    }
    public String getMessage() {
        return message;
    }
    public void setMessage(String message) {
        this.message = message;
    }
}
接下来就是写测试程序了,还是使用查询的例子,如下: 

异常

 @ExceptionHandler注解实现异常处理

  还有一种是使用注解的方法,我大概说一下思路,因为这种方法对代码的入侵性比较大,我不太喜欢用这种方法。 
  首先写个BaseController类,并在类中使用@ExceptionHandler注解声明异常处理的方法,如:

 

复制代码
public class BaseController { 
    @ExceptionHandler  
    public String exp(HttpServletRequest request, Exception ex) { 
    //异常处理
    //......
    }
}
复制代码

 

然后将所有需要异常处理的Controller都继承这个BaseController,虽然从执行来看,不需要配置什么东西,但是代码有侵入性,需要异常处理的Controller都要继承它才行。 

整个思路就是这样子的,你可以继续完善。。。。


版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/m0_37499059/article/details/79959531

14.SpringMVC 异常处理 - HandlerExceptionResolver

基本概念这里讲的异常处理,具体来说是控制器(controller)请求处方法的异常。在 springmvc 中可能存在着多个控制器,各个控制器又存在着众多请求处理方法。若在每个方法上都进行异常处理,那...
  • u012420654
  • u012420654
  • 2016-08-07 11:20:35
  • 8795

SpringMVC 异常处理 - HandlerExceptionResolver

今天用到SpringMVC中的异常处理,所以决定写下来,以后也会用的着。Spring MVC提供了一个HandlerExceptionResolver接口,可用于统一异常处理。代码如下...
  • wuqiwei521
  • wuqiwei521
  • 2017-05-05 10:03:02
  • 1722

springmvc全局异常处理

对于springmvc全局异常处理有三种方式, 1.使用SimpleMappingExceptionResolver实现异常处理 2.实现HandlerExceptionResolver 接口自...
  • Petershusheng
  • Petershusheng
  • 2016-09-01 11:13:43
  • 2469

spring mvc配置全局异常处理器

spring mvc配置全局异常处理器spring mvc配置全局异常处理器 概述 方法概述异常分为两种,一种是我们能够通过规范代码的书写、条件的判断就能够完成的,另外一种是在运行过程中发生的,这种异...
  • jpzhu16
  • jpzhu16
  • 2016-12-21 15:47:41
  • 1139

springMVC源码分析--异常处理机制HandlerExceptionResolver执行原理(二)

上一篇博客springMVC源码分析--异常处理机制HandlerExceptionResolver简单示例(一)中我们简单地实现了一个异常处理实例,接下来我们要介绍一下HandlerExceptio...
  • qq924862077
  • qq924862077
  • 2016-12-17 20:27:45
  • 1939

自定义异常处理 HandlerExceptionResolver

需求:     需要将项目里自定义的拦截器中抛出的错误信息按照一定的规则返回到不同界面进行展示。 分析:    自定义的拦截器属于HandlerInterceptor组件,用于拦截HandlerA...
  • yu8196378
  • yu8196378
  • 2017-07-21 18:42:12
  • 138

Spring Boot 系列教程6-全局异常处理

  • 2016年11月30日 19:41
  • 80KB
  • 下载

【SpringMVC整合MyBatis】springmvc异常处理-全局异常处理器开发

异常处理 1.异常处理思路 系统中异常包括两类:预期异常和运行时异常RuntimeException,前者通过捕获异常从而获取异常信息,后者主要通过规范代码开发、测试通过手段减少运行时异常的发生。 ...
  • u013517797
  • u013517797
  • 2015-08-13 08:54:18
  • 11113

HandlerExceptionResolver统一捕获系统异常做处理

转载 http://fancyboy2050.iteye.com/blog/1300037 最近使用spring mvc开发一个web系统,发现在controller里发生未捕获异常时不出日志。...
  • mawming
  • mawming
  • 2016-08-03 14:15:34
  • 2218

自定义异常处理 HandlerExceptionResolver

需求:     需要将项目里自定义的拦截器中抛出的错误信息按照一定的规则返回到不同界面进行展示。 分析:    自定义的拦截器属于HandlerInterceptor组件,用于拦截HandlerA...
  • yu8196378
  • yu8196378
  • 2017-07-21 18:42:12
  • 138
收藏助手
不良信息举报
您举报文章:全局异常处理
举报原因:
原因补充:

(最多只允许输入30个字)