Next, we will focus on how to use uniform exception handling in SpringBoot applications.How do I reuse exception data with normal business data and return it as a json?
Why uniform exception handling
Currently, our project architecture is basically a separate front-end and back-end model: developed using Restful interface protocol, the foreground simply accepts sending data regardless of any business logic.But if there are exceptions in the background, such as database exceptions, permission issues, Redis cache exceptions, business processing errors, etc., the front end usually displays a very ugly error page.This is very unfriendly to users and affects the normal operation of the business.So we need to unify the various system exceptions and return the results we want.
How to implement
There are two main ways Spring Boot implements uniform exception handling:
First: use the @ControllerAdvice and @ExceptionHandler annotations
The second is implemented using the ErrorController class.
The way to use ErrorController is relatively simple, and is not covered here.Today we will focus on how to use the @ControllerAdvice and @ExceptionHandler annotations to achieve uniform exception handling.
1. Unified exception handling class
package com.weiz.exception; import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpServletResponse; import org.springframework.web.bind.annotation.ControllerAdvice; import org.springframework.web.bind.annotation.ExceptionHandler; import org.springframework.web.servlet.ModelAndView; import com.weiz.utils.JSONResult; @ControllerAdvice public class GlobalExceptionHandler { public static final String ERROR_VIEW = "error"; @ExceptionHandler(value = Exception.class) public Object errorHandler(HttpServletRequest reqest, HttpServletResponse response, Exception e) throws Exception { e.printStackTrace(); // Is an ajax request if (isAjax(reqest)) { return JSONResult.errorException(e.getMessage()); } else { ModelAndView mav = new ModelAndView(); mav.addObject("exception", e); mav.addObject("url", reqest.getRequestURL()); mav.setViewName(ERROR_VIEW); return mav; } } public static boolean isAjax(HttpServletRequest httpRequest){ return (httpRequest.getHeader("X-Requested-With") != null && "XMLHttpRequest" .equals( httpRequest.getHeader("X-Requested-With")) ); } }
Explain:
1. The comment @ControllerAdvice indicates that this is a controller enhancement class and will be intercepted by this interceptor when a controller exception occurs.
2. Note @ExceptionHandler defines intercepted exception classes to get thrown exception information.Here you can define multiple interception methods, intercept different exception classes, and get thrown exception information with greater freedom.
2. Error Page
<!DOCTYPE html> <html> <head lang="en"> <meta charset="UTF-8" /> <title>Catch global exceptions</title> </head> <body> <h1 style="color: red">An error occurred:</h1> <div th:text="${url}"></div> <div th:text="${exception.message}"></div> </body> </html>
Description: The thymeleaf template is used here, as described earlier:'Introduction to SpringBoot Series (4) Integrated Template Engine Thymeleaf'
3. Test Address
Create a controller for the test exception
package com.weiz.controller; import com.weiz.utils.JSONResult; import org.springframework.stereotype.Controller; import org.springframework.web.bind.annotation.RequestMapping; import org.springframework.web.bind.annotation.ResponseBody; @Controller @RequestMapping("err") public class ErrorController { @RequestMapping("/error") public String error() { int a = 1 / 0; return "thymeleaf/error"; } @RequestMapping("/ajaxerror") public String ajaxerror() { return "thymeleaf/ajaxerror"; } @RequestMapping("/getAjaxerror") @ResponseBody public JSONResult getAjaxerror() { int a = 1 / 0; return JSONResult.ok(); } }
test
Enter in the browser: http://localhost:8088/err/error
Last
Above, I've finished handling Spring Boot uniform exceptions.This section only describes how to use the @ControllerAdvice annotation for exception handling and how to implement ErrorController, which you can learn about.
Note @ControllerAdvice only handles exceptions thrown by the controller, while ErrorController-like methods handle all exceptions, including errors that do not enter the controller, such as 404,401.