The SpringBoot interceptor implements the interception of errors such as 404 and 500

  • 2020-06-23 00:12:55
  • OfStack

Today I will introduce the use of interceptors in SpringBoot. Compared to the interceptors in Struts2, the interceptors in SpringBoot are more convenient and simple.

Just writing a few implementation classes makes it easy to implement the interceptor without configuring any extra information, which is a boon to programmers.

Without further ado, let's start with the implementation of the interceptor:

Step 1: Create our own interceptor class and implement the HandlerInterceptor interface.


package example.Interceptor; 
import javax.servlet.http.HttpServletRequest; 
import javax.servlet.http.HttpServletResponse; 
import org.springframework.stereotype.Controller; 
import org.springframework.web.bind.annotation.RequestMapping; 
import org.springframework.web.servlet.HandlerInterceptor; 
import org.springframework.web.servlet.ModelAndView; 
 
/** 
 *  Custom interceptors 1 
 * 
 * @author   Zhi-qiang Lin (208017534) 
 * @create  2016 years 9 month 20 day  
 */ 
@Controller 
public class ErrorInterceptor implements HandlerInterceptor { 
 
  /** 
   * preHandle Method is used for processor interception. As the name implies, this method will be used in Controller Call before processing, SpringMVC In the Interceptor Interceptors are chained and can exist simultaneously  
   *  multiple Interceptor And then SpringMVC It depends on the order of the declaration 1 after 1 The execution of, and all of Interceptor In the preHandle The methods will be there  
   * Controller Call before a method call. SpringMVC This kind of Interceptor The chain structure can also be interrupted in the form of let preHandle The return of  
   *  Back to the value of false when preHandle The return value of false "The whole request is over.  
   */  
  @Override 
  public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) 
      throws Exception { 
    System.out.println(">>>MyInterceptor1>>>>>>> Call before the request is processed ( Controller Before the method call) "); 
    return true;//  Only the return true It's going to go down and return false Cancel current request  
  } 
 
  /** 
   *  This method is only going to be in the current one Interceptor the preHandle Method returns a value of true Will only be implemented when. postHandle Is used for processor interception, and its execution time is processed in the processor  
   *  After, that is, in Controller Is executed after a method call to the DispatcherServlet Execute before rendering the view, that is, in this method you can do the right thing ModelAndView To fuck  
   *  Make it. The chain structure of this method is in the opposite direction of normal access, that is, declared first Interceptor The interceptor instead calls the method after it follows Struts2 The execution of the interceptor inside is a little bit like,  
   *  just Struts2 The inside of the intercept Method to be called manually ActionInvocation the invoke Method, Struts2 In the call ActionInvocation the invoke The method is called 1 a Interceptor 
   *  Or call action And then you have to be in Interceptor The contents of the previous call are written in the call invoke Before, before Interceptor Everything that is called after that is written in the call invoke Method.  
   */  
  @Override 
  public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, 
              ModelAndView modelAndView) throws Exception { 
    System.out.println(">>>MyInterceptor1>>>>>>> Called after the request is processed, but before the view is rendered ( Controller After the method call) "); 
    if(response.getStatus()==500){ 
      modelAndView.setViewName("/errorpage/500"); 
    }else if(response.getStatus()==404){ 
      modelAndView.setViewName("/errorpage/404"); 
    } 
  } 
 
  /** 
   *  The method also needs the current corresponding Interceptor the preHandle The return value of the true Will be executed when. This method will be completed after the entire request, i.e DispatcherServlet Rendering the view execution,  
   *  The main purpose of this method is to clean up resources, but this method can only be used in the current one Interceptor the preHandle The return value of the true Will be executed when.  
   */  
  @Override 
  public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) 
      throws Exception { 
    System.out.println(">>>MyInterceptor1>>>>>>> Is called at the end of the entire request DispatcherServlet  Execute after rendering the corresponding view (mainly for resource cleaning) "); 
  } 
} 

The purpose of several functions in the interceptor implementation class, and the order in which they are called, is clear, and I won't go into more detail here.

Part 2: Create an Java class that inherits WebMvcConfigurerAdapter and overwrites the addInterceptors method. Instantiate our custom interceptor, and then manually add the image to the interceptor chain (in the addInterceptors method).


package example.configuration; 
import example.Interceptor.ErrorInterceptor; 
import example.Interceptor.MyInterceptor2; 
import org.springframework.context.annotation.Configuration; 
import org.springframework.web.servlet.config.annotation.InterceptorRegistry; 
import org.springframework.web.servlet.config.annotation.WebMvcConfigurerAdapter; 
@Configuration 
public class MyWebAppConfigurer extends WebMvcConfigurerAdapter { 
  @Override 
  public void addInterceptors(InterceptorRegistry registry) { 
    //  Multiple interceptors 1 Three interceptor chains  
    // addPathPatterns  Used to add intercepting rules  
    // excludePathPatterns  User exclusion interception  
    registry.addInterceptor(new ErrorInterceptor()).addPathPatterns("/**"); 
    super.addInterceptors(registry); 
  } 
 
} 

At this point interceptors are basically implemented, and in the examples I've given above I can intercept 404 or 500.

It is important to note, however, that such intercepts can sometimes be particularly problematic. For example, if you need to load a lot of images or js file resources in a web page, but you just don't have the resources, that is, you can't find so many resources to report a heap of 404 errors. The null pointer exception will occur if the interception is used alone.

In this case, I studied a method to solve such a similar problem.

The solution is to create a class and implement the ErrorController interface so that the class can handle the problem above.

Here is the code:


package example.controller; 
import org.springframework.boot.autoconfigure.web.ErrorController; 
import org.springframework.stereotype.Controller; 
import org.springframework.web.bind.annotation.RequestMapping; 
@Controller 
public class MainsiteErrorController implements ErrorController { 
  private static final String ERROR_PATH = "/error"; 
  @RequestMapping(value=ERROR_PATH) 
  public String handleError(){ 
    return "errorpage/error"; 
  } 
  @Override 
  public String getErrorPath() { 
    return ERROR_PATH; 
  } 
} 

This can achieve the interception of 404,500 and other error messages, and will not occur in the case of null pointer exception, is not particularly convenient ah!


Related articles: