An interceptor is a component in Spring MVC that can do something before entering a request method, or after requesting a method and rendering a view.

Welcome to pay attention to my B station account

B station account

If the content helps you, welcome everyone to like, favorites + attention

Learning exchange group

Definition of interceptor

SpringMVC interceptors only need to implement the HandlerInterceptor interface and configure it. The HandlerInterceptor interface is defined as follows:

public interface HandlerInterceptor {
    default boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
        return true;
    }

    default void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, @Nullable ModelAndView modelAndView) throws Exception {
    }

    default void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, @Nullable Exception ex) throws Exception {
    }
}
Copy the code

There are three methods in the HandlerInterceptor, each of which has the following meanings:

PreHandler: executed before entering the request method;

PostHandler: Request method execution after completion;

AfterCompletion: Executed after the view is rendered.

The execution flow of interceptors

In the case of the preHandle method, its return value is of Boolean type, and its return value affects the execution of the request method, as well as postHandle and afterCompletion. Details are as follows.

That is, if false is returned in the preHandle, subsequent processes will not be executed, which is probably why the interceptor is named.

Test interceptor

Write a simple interceptor as follows:

@Slf4j public class TestInterceptor implements HandlerInterceptor { @Override public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception { log.info("preHandler"); return true; } @Override public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView) throws Exception { log.info("postHandler"); } @Override public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) throws Exception { log.info("afterCompletion"); } } @Override public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView) throws Exception { log.info("postHandler"); } @Override public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) throws Exception { log.info("afterCompletion"); }}Copy the code

TestInterceptor listener class, which implements all the interfaces of the HandlerInterceptor. TestInterceptor also needs to be registered. The code is as follows: @Configuration public class InterceptorConfig implements WebMvcConfigurer { @Override public void addInterceptors(InterceptorRegistry registry) { registry.addInterceptor(testInterceptor()); }Copy the code

Write a simple request method as follows:

@GetMapping("test")
public String test()
{
    return "test";
}
Copy the code

To launch our project and access, the console output is as follows:

The 2021-05-05 16:02:08. 88509-110 the INFO [nio - 8081 - exec - 6] com. Example. Demo. TestInterceptor: PreHandler 16:02:08 2021-05-05. 88509-111 the INFO [nio - 8081 - exec - 6] com. Example. Demo. TestInterceptor: PostHandler 16:02:08 2021-05-05. 88509-111 the INFO [nio - 8081 - exec - 6] com. Example. Demo. TestInterceptor: afterCompletionCopy the code

Execution order of multiple interceptors

Let’s write multiple identical listeners: TestInterceptor, TestInterceptor2, and TestInterceptor3. Then we register with the following registration code:

@Override
public void addInterceptors(InterceptorRegistry registry) {
    registry.addInterceptor(testInterceptor());
    registry.addInterceptor(testInterceptor2());
    registry.addInterceptor(testInterceptor3());
}
Copy the code

Request our method, output is as follows:

The 2021-05-05 16:09:57. 88572-735 the INFO [nio - 8081 - exec - 1] com. Example. Demo. TestInterceptor: PreHandler 16:09:57 2021-05-05. 88572-736 the INFO [nio - 8081 - exec - 1] com. Example. Demo. TestInterceptor2: PreHandler2 16:09:57 2021-05-05. 88572-736 the INFO [nio - 8081 - exec - 1] com. Example. Demo. TestInterceptor3: PreHandler3 16:09:57 2021-05-05. 88572-755 the INFO [nio - 8081 - exec - 1] com. Example. Demo. TestInterceptor3: PostHandler3 16:09:57 2021-05-05. 88572-755 the INFO [nio - 8081 - exec - 1] com. Example. Demo. TestInterceptor2: PostHandler2 16:09:57 2021-05-05. 88572-755 the INFO [nio - 8081 - exec - 1] com. Example. Demo. TestInterceptor: PostHandler 16:09:57 2021-05-05. 88572-755 the INFO [nio - 8081 - exec - 1] com. Example. Demo. TestInterceptor3: AfterCompletion3 16:09:57 2021-05-05. 88572-755 the INFO [nio - 8081 - exec - 1] com. Example. Demo. TestInterceptor2: AfterCompletion2 16:09:57 2021-05-05. 88572-755 the INFO [nio - 8081 - exec - 1] com. Example. Demo. TestInterceptor: afterCompletionCopy the code

Notice the order of output. The preHandle method is executed in the order in which it was registered, while postHandle and afterCompletion are executed in reverse.

Let preHandle intercept

Let’s return false from the TestInterceptor2 preHandle and take a look at the output.

The 2021-05-05 16:14:00. 88582-997 the INFO [nio - 8081 - exec - 1] com. Example. Demo. TestInterceptor: PreHandler 16:14:00 2021-05-05. 88582-998 the INFO [nio - 8081 - exec - 1] com. Example. Demo. TestInterceptor2: PreHandler2 16:14:00 2021-05-05. 88582-998 the INFO [nio - 8081 - exec - 1] com. Example. Demo. TestInterceptor: afterCompletionCopy the code

If the TestInterceptor2 preHandle returns false, the TestInterceptor2 preHandle process does not continue.

Let’s adjust the order of registration, the code is as follows:

@Override
public void addInterceptors(InterceptorRegistry registry) {
    registry.addInterceptor(testInterceptor2());
    registry.addInterceptor(testInterceptor());
    registry.addInterceptor(testInterceptor3());
}
Copy the code

The following output is displayed after the sequence is changed:

The 2021-05-05 16:17:23. 88589-956 the INFO [nio - 8081 - exec - 1] com. Example. Demo. TestInterceptor2: preHandler2Copy the code

You can see that the flow after it is blocked and has no chance to execute.

conclusion

Interceptors are saved using a List. We can add multiple interceptors in the project to complete different functions, such as Token verification, permission acquisition and so on. We can put them in different interceptors to do this.