目录
Spring Boot异常处理
介绍
拦截器VS 过滤器
自定义异常页面
自定义异常页面
代码实战
需求
代码实现
创建MyErrorController类来模拟异常错误
完成测试
全局异常
说明
全局异常-应用实例
创建GlobalExceptionHandler.java
创建对应的视图地址global.html
完成测试
自定义异常
说明
应用实例
创建AccessException.java
修改MyErrorController.java
完成测试
Spring Boot异常处理
介绍
1. 默认情况下,Spring Boot 提供/error 处理所有错误的映射
2. 对于机器客户端,它将生成JSON 响应,其中包含错误,HTTP 状态和异常消息的详细信息。对于浏览器客户端,响应一个"whitelabel"错误视图,以HTML 格式呈现相同的数据
拦截器VS 过滤器
1、使用范围不同
1) 过滤器实现的是javax.servlet.Filter 接口,而这个接口是在Servlet 规范中定义的,也就是说过滤器Filter 的使用要依赖于Tomcat 等容器,Filter 只能在web 程序中使用
2) 拦截器(Interceptor) 它是一个Spring 组件,并由Spring 容器管理,并不依赖Tomcat 等容器,是可以单独使用的。不仅能应用在web 程序中,也可以用于Application 等程序中
2、过滤器和拦截器的触发时机也不同,看下边这张图
1) 过滤器Filter 是在请求进入容器后, 但在进入servlet 之前进行预处理, 请求结束是在servlet 处理完以后
2) 拦截器Interceptor 是在请求进入servlet 后, 在进入Controller 之前进行预处理的,Controller 中渲染了对应的视图之后请求结束
不理解的 请javaweb filter , 和springmvc 的interceptor 和springmvc 的执行流程的博客在我的专栏里面有
3、说明: 过滤器不会处理请求转发, 拦截器会处理请求转发
4、至于过滤器和拦截器的原理和机制, 已经在博客详细讲解过了, 过滤器在JavaWeb , 拦
截器在SpringMVC 讲过, 忘了在我的专栏里面有
自定义异常页面
文档:
https://docs.spring.io/spring-boot/docs/current/reference/html/features.html#features.develo
ping-web-applications.spring-mvc.error-handling.error-pages
自定义异常页面说明
1、如何找到这个文档位置, 看下面一步步的指引
https://docs.spring.io/spring-boot/docs/current/reference/html/index.html
说明 先点击上面的链接 打开文档 然后按下面的步骤一步一步的来 最后到截图位置
- a single pagehtml
- 8.web
- servlet web application
- The "Spring Web MVC Framework"
- Error Handling
- Custom Error Pages
自定义异常页面
代码实战
需求
自定义404.html 500.html 4xx.html 5xx.html 当发生相应错误时,显示自定义的页面信息
代码实现
创建4 个页面, 这几个页面拷贝即可
创建MyErrorController类来模拟异常错误
@Controller
public class MyErrorController {
//模拟一个服务器内部错误500
@GetMapping("/err")
public String err() {
int i = 10 / 0; //算术异常
return "manage";
}
//这里我们配置的是Post方式请求 /err2
@PostMapping("/err2")
public String err2() {
//..
return "manage";
}
}
完成测试
● 需要先登录,再进行测试,否则会被拦截器打回登录页面
● 对于/err2 , 使用get 方式去请求,就会生成400 错误, 可以看到4xx.html
因为这个页面在上一篇博客已经完成了这里在展示就太繁杂了 这篇主要演示异常的原理和机制 有兴趣可以去看 链接
测试链接
http://localhost:8080/xx
http://localhost:8080/err2http://localhost:8080/err
全局异常
说明
1. @ControllerAdvice+@ExceptionHandler 处理全局异常
2. 底层是ExceptionHandlerExceptionResolver 支持的
全局异常-应用实例
需求: 演示全局异常使用, 当发生ArithmeticException、NullPointerException 时
不使用默认异常机制匹配的xxx.html , 而是显示全局异常机制指定的错误页面
创建GlobalExceptionHandler.java
1、编写方法,处理指定异常, 比如我们处理算术异常和空指针异常, 可以指定多个异常
2. 这里要处理的异常,由程序员来指定
3. Exception e : 表示异常发生后,传递的异常对象
4. Model model: 可以将我们的异常信息,放入model,并传递给显示页面
5.如何获取到异常发生的方法
6.@Slf4j 这个注解的作用是显示日志 方便程序员查看
/**
* @ControllerAdvice: 使用它可以标识一个全局异常处理器/对象
* 会注入到spring容器
*/
@Slf4j
@ControllerAdvice
public class GlobalExceptionHandler {
//1、编写方法,处理指定异常, 比如我们处理算术异常和空指针异常, 可以指定多个异常
//2. 这里要处理的异常,由程序员来指定
//3. Exception e : 表示异常发生后,传递的异常对象
//4. Model model: 可以将我们的异常信息,放入model,并传递给显示页面
//5.如何获取到异常发生的方法
@ExceptionHandler({ArithmeticException.class, NullPointerException.class,AccessException.class})
public String handleAritException(Exception e, Model model, HandlerMethod handlerMethod) {
log.info("异常信息={}", e.getMessage());
//这里将发生的异常信息放入到model,可以再错误页面取出显示
model.addAttribute("msg", e.getMessage());
//得到异常发生的方法是哪个
log.info("异常发生的方法是={}", handlerMethod.getMethod());
return "/error/global"; //视图地址
}
}
创建对应的视图地址global.html
注意这个html页面要在静态资源下的erro文件不然无法识别
templates 是使用Thymeleaf解析指定的文件
只要静态资源放在类路径下: /static 、/public 、/resources 、/META-INF/resources可以被直接访问- 对应文件 这个如果不知道可以看一下 (6条消息) Spring boot之WEB 开发-静态资源访问---Rest 风格请求处理--接收参数相关注解--复杂参数--自定义对象参数-自动封装--自定义转换器--处理JSON-- 内容协商_尘觉的博客-CSDN博客
<html lang="en" xmlns:th="http://www.thymeleaf.org">
<head>
<meta charset="UTF-8">
<title>全局异常-显示页面</title>
</head>
<body bgcolor="#CED3FE">
<img src="images/1.GIF"/>
<hr/>
<div style="text-align: center">
<h1>全局异常/错误 发生了:)</h1><br/>
异常/错误信息: <h1 th:text="${msg}"></h1><br/>
<a href='#' th:href="@{/}">返回主页面</a>
</div>
<hr/>
<img src="images/logo.png"/>
</body>
</html>
完成测试
浏览器http://localhost:8080/err
自定义异常
说明
1. 如果Spring Boot 提供的异常不能满足开发需求,程序员也可以自定义异常.
2. @ResponseStatus+自定义异常
3. 底层是ResponseStatusExceptionResolver
底层调用response.sendError(statusCode,resolvedReason);
4. 当抛出自定义异常后,仍然会根据状态码,去匹配使用x.html 显示..
应用实例
需求:自定义一个异常AccessException, 当用户访问某个无权访问的路径时,抛出该异常,显示
自定义异常状态码..
创建AccessException.java
/**
* AccessException : 我们自定义的一个异常
* 关于自定义异常, 我们在java基础中的博客忘记了的小伙伴可以去看看在专栏EE
* value = HttpStatus.FORBIDDEN: 表示发生AccessException异常,我们通过http协议返回的状态码 403
* 这个状态码和自定义异常的对应关系是由程序员来决定[尽量合理来设置]
*/
@ResponseStatus(value = HttpStatus.FORBIDDEN)
public class AccessException extends RuntimeException {
//提供一个构造器,可以指定信息
public AccessException(String message) {
super(message);
}
//显示的定义一下无参构造器
public AccessException() {
}
}
修改MyErrorController.java
//编写方法,模拟一个AccessException
@GetMapping("/err3")
public String err3(String name) {
//如果用户不是tom,我们就认为,无权访问-模拟
if(!"tom".equals(name)) {
//throw new AccessException();
throw new AccessException("老韩自定义的AccessException..");
}
return "manage";//视图地址, 请求转发
//return "redirect:/manage.html";
}
完成测试
浏览器http://localhost:8080/err3