代码内可以通过try/catch捕获已知异常(checked exception),但未知异常(unchecked exception)却不同时机以不同形式随机出现。异常抛出时系统需要特殊处理捕获异常友好提示,而不是把服务器端异常信息发动到客户端。并且记录异常发生的各项指标信息以方便开发人员调试代码。
可以通过以下方式实现共通的全局处理:
- ServletRequestListener :请求的开始和结束时执行,Spring的RequestContextListener等
- Filter :Servlet的开始和结束时执行,Spring的CharacterEncodingFilter、HiddenHttpMethodFilter等
- HandlerInterceptor :Controller方法的开始和结束时执行,Spring的LocaleChangeInterceptor等
- Spring AOP(AspectJ) :面向切面,任意注入处理。
这里只介绍 Spring MVC 内置的异常处理机制:
- @ResponseStatus
- @ExceptionHandler
- @ControllerAdvice
- HandlerExceptionResolver
(1)Controller内的异常捕获
通过注解@ExceptionHandler来实现异常的捕获处理。
@Controller
public class FooController {
@ExceptionHandler
@ResponseStatus(NOT_FOUND)
public void notFound(ResourceNotFoundException ex) {
// N/A
}
}
也可以通过实现HandlerExceptionResolver来实现异常的捕获处理。
@Controller
public class FooController implements HandlerExceptionResolver {
@Override
public ModelAndView resolveException(HttpServletRequest req, HttpServletResponse res, Object handler, Exception ex) {
// N/A
}
}
(2)被@ResponseStatus注解标记的异常
会被 ResponseStatusExceptionResolver 自动处理。
@ResponseStatus(value = NOT_FOUND, reason = "Resource is not found.")
public class ResourceNotFoundException extends RuntimeException {
// ...
}
(3)全局异常捕获
@ControllerAdvice
public class GlobalExceptionHandler {
@ExceptionHandler
@RespnseStatus(NOT_FOUND)
public void notFound(ResourceNotFoundException ex) {
// N/A
}
}
@ControllerAdvice
public class GlobalExceptionHandler extends ResponseEntityExceptionHandler {
@ExceptionHandler(RuntimeException.class)
public ResponseEntity<Error> handle(RuntimeException ex, HttpServletResponse res){
// N/A
res.setStatus(HttpStatus.INTERNAL_SERVER_ERROR.value());
}
}
API和页面共存的时候,全局异常捕获可以通过再次forward来返回不同的内容。
@ControllerAdvice
public class GlobalExceptionHandler extends ResponseEntityExceptionHandler {
@ExceptionHandler(Exception.class)
public String error(HttpServletRequest req, Exception ex){
// N/A
String baseUrl = getBaseUrl(req);
return "forward:" + baseUrl + "/error";
}
}
@Controller
public class GeneralErrorHandlerController {
@RequestMapping("/admin/error")
public String screenError(HttpServletRequest req, Model model) {
// N/A
return "screen/admin/error";
}
@RequestMapping(value = "/api/internal/error")
@ResponseBody
public ErrorResponse apiError(HttpServletRequest req) {
// N/A
return ErrorResponse.build(e);
}
}
***** 不能自动设置status code,需要自己设置
***** 不能捕获所有异常,比如表示层,404错误等
@ControllerAdvice注解内的@ExceptionHandler、@InitBinder、@ModelAttribute方法会被应用到所有的@RequestMapping注解的方法。上边@ExceptionHandler是最常见的,而@InitBinder也会用到,比如:
1)默认SpringMVC对空字段设置值为空字符串而不是null。通过以下定义可以将空字符串设置成null,并且会对字符串进行自动trim处理。
还可以传入需要过滤的字符:StringTrimmerEditor(String charsToDelete, boolean emptyAsNull)
@ControllerAdvice
public class NullValidAdvice {
@InitBinder
public void initBinder(WebDataBinder binder) {
binder.registerCustomEditor(String.class, new StringTrimmerEditor(true));
}
}
2)设置JSONP的返回参数
@ControllerAdvice
public class JsonpAdvice extends AbstractJsonpResponseBodyAdvice {
public JsonpAdvice() {
super("callback");
}
}
(4)web.xml中的error-page
这部分本身不归Spring处理,是ServletContainer处理范围。
把所有未能捕获的异常再次跳转到一个指定mapping。
<error-page>
<location>/error</location>
</error-page>
@Controller
class GeneralErrorHandlerController {
@RequestMapping("error")
public String otherError(HttpServletRequest req, Model model) {
// N/A
}
}
(5)自定义404相应
设置throwExceptionIfNoHandlerFound为true
<servlet>
<servlet-name>rest-dispatcher</servlet-name>
<servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
<init-param>
<param-name>throwExceptionIfNoHandlerFound</param-name>
<param-value>true</param-value>
</init-param>
</servlet>
@ControllerAdvice
public class GlobalExceptionHandler {
@ExceptionHandler(NoHandlerFoundException.class)
public ResponseEntity<Error> handle(NoHandlerFoundException ex){
// N/A
}
}
(6)自定义错误页面
定制将异常映射为视图 SimpleMappingExceptionResolver
@Bean
public SimpleMappingExceptionResolver exceptionResolver(){
SimpleMappingExceptionResolver resolver = new SimpleMappingExceptionResolver();
Properties exceptions = new Properties();
exceptions.put(ArithmeticException.class, "error");
resolver.setExceptionMappings(exceptions);
return resolver;
}
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html>
<head>
<title>Spring MVC Exception Handling</title>
</head>
<body>
<h1>Spring MVC Exception Handling</h1>
${exception.message}
</body>
</html>
***** 测试开发环境可以在页面打印出异常堆栈,方便调试。
Spring MVC 异常处理顺序:
ExceptionHandlerExceptionResolver :被@ExceptionHandler注解标记的异常
->
ResponseStatusExceptionResolver :被@ResponseStatus注解标记的异常
->
DefaultHandlerExceptionResolver :Spring的标准异常处理
->
自定义的Resolver
标准异常处理 DefaultHandlerExceptionResolver
引用
BindException 400 (Bad Request)
ConversionNotSupportedException 500 (Internal Server Error)
HttpMediaTypeNotAcceptableException 406 (Not Acceptable)
HttpMediaTypeNotSupportedException 415 (Unsupported Media Type)
HttpMessageNotReadableException 400 (Bad Request)
HttpMessageNotWritableException 500 (Internal Server Error)
HttpRequestMethodNotSupportedException 405 (Method Not Allowed)
MethodArgumentNotValidException 400 (Bad Request)
MissingPathVariableException 500 (Internal Server Error)
MissingServletRequestParameterException 400 (Bad Request)
MissingServletRequestPartException 400 (Bad Request)
NoHandlerFoundException 404 (Not Found)
NoSuchRequestHandlingMethodException 404 (Not Found)
TypeMismatchException 400 (Bad Request)
参考:
http://docs.spring.io/spring/docs/current/spring-framework-reference/html/mvc.html#mvc-exceptionhandlers
https://spring.io/blog/2013/11/01/exception-handling-in-spring-mvc
http://memorynotfound.com/spring-mvc-exception-handling/
http://www.journaldev.com/2651/spring-mvc-exception-handling-controlleradvice-exceptionhandler-handlerexceptionresolver
http://www.roytuts.com/exception-handling-best-practices-in-java/
https://speakerdeck.com/sinsengumi/spring-boot-application-infrastructure
https://github.com/jirutka/spring-rest-exception-handler
http://qiita.com/kazuki43zoo/items/757b557c05f548c6c5db
http://cgs1999.iteye.com/blog/1547197
http://www.cnblogs.com/xinzhao/p/4934247.html
- 大小: 154.1 KB
分享到:
相关推荐
01. 采用后台及前台的 Spring + ... 通过自定义处理器 ExceptionIntercept 实现 Spring mvc的全局异常捕获 10. 系统中包含了企业中采用的开发工具类的集合 11. AbstractDao 父类实现了Dao中针对单个对象的常用操作
本篇文章主要介绍了Spring MVC全局异常处理和单元测试,具有一定的参考价值,感兴趣的小伙伴们可以参考一下
由于SpringSecurity的异常处理和mvc的异常处理是不一样的,认证类异常和权限异常了,并不会被全局异常捕获,而是SpringSecurity内部自己做了处理逻辑。 思路分析 我已经将本次请求的url添加到忽略名单里面了,起始...
简单性 ...异常处理是Java中使得程序更稳健的另一个特征。异常是某种类似于错误的异常条件出现的信号。使用try/catch/finally语句,程序员可以找到出错的处理代码,这就简化了出错处理和恢复的任务。
springMvc中的自定义捕获异常 必须在spring.xml文件中注释mvc:default-servlet-handler / 在DispatcherServlet中重写noHandlerFound方法,将重定向到sx.java上的/ demo / notFound路径和定义找不到请求。 方法
Spring MVC AOP通过自定义注解方式拦截Controller等实现日志管理, springMVC里做添加AOP拦截,用于捕获异常。
培训时讲的springmvc,代码清晰易懂,初学者也容易学会,希望能帮助大家
返回相同的对象但是json字段不同参考JsonController和BookInfo类捕获Controller中的异常参考ExceptionController和ExceptionAdvice类增加数据校验和分组校验参考ValidationController,UserInfo, ExceptionAdvice...
Spring Data REST从那里开始使用Spring MVC来创建一个超媒体驱动的RESTful接口,该接口允许您创建,读取,更新和删除数据。 此示例应用程序演示了如何声明一个旨在存储图像数据的后端如何使上传图片然后转身显示在...
程序在编写时,对可能出现的异常进行了捕获,增加了程序的健壮性。本程序实现的功能比较简单,但其遵循了MVC的设计思想,Model层,View层,control层实现了很好的分离,大大减低了将来的维护难度。
* 增加事务测试样例,详见AdminController的save方法,此坑很深,爬了一天,由于没有对spring事务的深入了解,导致事务一直不成功,原因在于spring事务只能处理没有被捕获的异常信息,如果对方法增加了事务,请尽量...
“监视器”项目是一个用 Java 编写... Spring 核心和 Spring MVC 为这个应用程序实现 web 控制器和 web 服务。 JSP 和 JQuery 来实现浏览器界面。 Apache Tiles 可以重用常见的 JSP 并强制执行一致的页面布局Java Mail
这类异常没法要求程序员去一一捕获并抛出,一般异常是Java类库或程序员自己写的代码发生的错误,这类异常可以由我们去一一捕获并抛出。 多线程几种实现方法,同步? 答:多线程有两种实现方法,一种是继承Thread类...
微信小程序“消防隐患在线举报系统开发Ssm.zip”是一款基于Spring、Spring MVC和MyBatis(SSM)框架开发的小程序,旨在提高公众对消防安全隐患的关注并促进社区安全。该项目结合了微信小程序的广泛覆盖和便利性以及...
“监视器”项目是一个用 Java ... Spring 核心和 Spring MVC 为这个应用程序实现 web 控制器和 web 服务。 JSP 和 JQuery 来实现浏览器界面。 Apache Tiles 可以重用常见的 JSP 并强制执行一致的页面布局 Java Mail
Jquery Angular Bootstrap JS.SDK后台MVC:SpringMVCIoC:Spring数据库:Mysql工作流引擎:jBPM云平台:SAE类别技术前台基础jQuery、requireJS、JS.SDK前台MVCAngular前台UIBootstrap后台MVCSpringMVCIocSpring工作...
框架:Spring MVC 工具:Maven 要安装Maven依赖项,请键入mvn clean install 要启动Web应用程序,请键入命令mvn jetty:run 要运行测试用例,请运行命令mvn test REST Api端点 POST /village?village_name=...
1. 异常类的产生、捕获与处理 34 2. 抛出异常 36 二. Swing程序设计 38 (一) Swing概述 38 1. 布局管理器 39 2. 流布局管理器 39 3. 边界布局管理器 41 4. 网格布局管理器 42 5. 盒式布局管理器 43 (二) 面板及组件...
通过简单的小例子演示Spring MVC Web框架的功能 当当网开源的数据库中间件 hexo的插件,向你的Hexo里放上一只萌萌哒二次元看板娘! 介绍README.md文件中应该放什么徽章 浏览器兼容性列表,在前端代码中加入兼容性代码...