先了解一下springboot 正常情况下捕获异常的方式
1、添加以下配置
spring.resources.add-mappings=false
spring.mvc.throw-exception-if-no-handler-found=true
2、使用@RestControllerAdvice+@ExceptionHandler的方式捕获异常
*@RestControllerAdvice =@ResponseBody+@ControllerAdvice
@ExceptionHandler(value = { NoHandlerFoundException.class })
public ResponseData noHandlerFoundException(NoHandlerFoundException ex) {
ResponseData responseData = new ResponseData();
responseData.setApiCode(ApiErrorCodeEnum.CODE20000.getCode());
return responseData;
}
一、调试过程>发现问题>解决问题
产生异常的原因有
A、URL错误,controller中没有对应的路径(statuCode:400)
B、在controller内出现异常(statuCode:500)
AB两种方法很好区别 ,肉眼可见的区别,实在不行debug一下观察接口有没有到达Controller内即可
主要对A进行阐述,排查原因debug调试>直接进入DispatchServlet.class 如何进入 Ctrl+shift+N 搜索
一个不存在的URL会被SimpleUrlHandlerMapping的 /** 匹配到
匹配到会有什么影响呢?下图可见,程序进入不了noHandlerFound()方法里面
所以这个地方我们需要添加一个配置就是 spring.resources.add-mappings=false 关闭资源映射
这个时候问题出现了就是该配置没有生效,还是被SimpleUrlHandlerMapping的 /** 匹配到了
接下来仔细看了项目配置发现:
在mvc配置中添加了/**的mapping 所以我们将该处内容注释掉
接下来程序顺利的进入到了noHandlerFound方法里面 内容如下:
红框内的是重点 可以看到一个通过一个判定条件就会抛出异常,这个判定东西就是我们在配置中设置的一个东西:spring.mvc.throw-exception-if-no-handler-found=true
我在测试的时候发现这个配置没有生效:原因待查 初步估计是版本问题
所以在这个地方默认是false,抛不出异常,也就导致我们的异常捕捉不到
这个地方怎么处理呢?那就是重写noHandlerFound方法
import org.springframework.http.HttpHeaders;
import org.springframework.web.servlet.DispatcherServlet;
import org.springframework.web.servlet.NoHandlerFoundException;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
public class CustomizeDispatcherServlet extends DispatcherServlet {
@Override
protected void noHandlerFound(HttpServletRequest request, HttpServletResponse response) throws Exception {
throw new NoHandlerFoundException(request.getMethod(), request.getRequestURL().toString(), new HttpHeaders());
}
}
很简单就是直接创建一个类继承DispatcherServlet 重写他的noHandlerFound方法直接抛出异常
然后将新写的CustomizeDispatcherServlet 配置到mvc中
@Bean
public ServletRegistrationBean apiMvc() {
CustomizeDispatcherServlet dispatcherServlet = new CustomizeDispatcherServlet();
AnnotationConfigWebApplicationContext applicationContext = new AnnotationConfigWebApplicationContext();
applicationContext.register(ApiConfig.class);
dispatcherServlet.setApplicationContext(applicationContext);
ServletRegistrationBean servletRegistrationBean = new ServletRegistrationBean(dispatcherServlet, "/api/*");
servletRegistrationBean.setName("apiMvc");
return servletRegistrationBean;
}
再来启动项目调试 成功解决400白页