本篇介紹如何在Spring Boot應用程式中設定Inteceptor攔截器,其可攔截傳入Controller的Request及攔截從Controller回傳給Client的Response。
不過Interceptor無法修改response的內容,也就是無法取得及修改response body。若要修改response的內容則使用ResponseBodyAdvice
來修改。
範例環境:
- Windows 64 Bit
- JDK 1.8.0_171
- Eclipse 2019-03 (4.11.0)
- Spring Boot 2.1.6.RELEASE
首先建立一個Spring Boot專案,參考使用Eclipse STS建立Spring Boot應用程式專案。
例如Spring Boot現在有一個MessageController
如下,其getMessage()
用來處理
http://<domain>/<contextPath>/message
的請求。
例如在本機為http://localhost:8080/MySpringBoot/message
。
MessageController
package idv.matt.springboot.controller;
import org.springframework.http.MediaType;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
@RestController
@RequestMapping
public class MessageController {
@GetMapping(value="/message", produces=MediaType.APPLICATION_JSON_UTF8_VALUE)
public String getMessage() {
String message = "お前はもう死んでいる";
System.out.println("MessageController.getMessage():" + message);
return message;
}
}
現在針對這個url請求進行攔截,定義一個攔截器MessageInterceptor
類別如下。攔截器類別要實作HandlerInterceptor
介面,並記得加上@Component
才能被SpringBoot掃描並註冊為Bean。
MessageInterceptor
package idv.matt.springboot.interceptor;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import org.springframework.lang.Nullable;
import org.springframework.stereotype.Component;
import org.springframework.web.servlet.HandlerInterceptor;
import org.springframework.web.servlet.ModelAndView;
@Component
public class MessageInterceptor implements HandlerInterceptor {
@Override
public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler)
throws Exception {
System.out.println("MessageInterceptor.preHandle():北 斗 殘 悔 拳");
return true;
}
@Override
public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler,
@Nullable ModelAndView modelAndView) throws Exception {
System.out.println("MessageInterceptor.postHandle():なに!?");
}
@Override
public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler,
@Nullable Exception ex) throws Exception {
System.out.println("MessageInterceptor.afterCompletion:たわば!!");
}
}
實作HandlerInterceptor
介面可覆寫(override)其三個方法,preHandle()
、postHandle()
及afterCompletion()
。
三個方法的執行時機為:
preHandle()
:請求送到Controller前執行,回傳一個布林值,如果是true
通過攔截器,反之則否。postHandle()
:Controller處理完後執行。afterCompletion()
:整個請求及回應結束後執行。
然後要將此攔截器註冊到Web MVC的配置,定義一個類別InterceptorWebMvcConfig
並實作WebMvcConfigurer
介面。
package idv.matt.springboot.config;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Configuration;
import org.springframework.web.servlet.config.annotation.EnableWebMvc;
import org.springframework.web.servlet.config.annotation.InterceptorRegistry;
import org.springframework.web.servlet.config.annotation.WebMvcConfigurer;
import idv.matt.springboot.interceptor.MessageInterceptor;
@Configuration
@EnableWebMvc
public class InterceptorWebMvcConfig implements WebMvcConfigurer {
@Autowired
private MessageInterceptor messageInterceptor;
@Override
public void addInterceptors(InterceptorRegistry registry) {
registry.addInterceptor(messageInterceptor).addPathPatterns("/message/**");
}
}
此類別名稱前要加上@Configuration
及@EnableWebMvc
annotation表示為Web MVC的配置類別;覆寫addInterceptors(InterceptorRegistry registry)
方法,
並調用InterceptorRegistry.addInterceptor()
來註冊MessageInterceptor
攔截器;最後調用InterceptorRegistration.addPathPatterns()
來套用要攔截的url請求路徑。
設定完以上後啟動專案,然後在瀏覽器位址輸入http://localhost:8080/MySpringBoot/message
。
輸入後在Eclipse的console會印出以下訊息。
MessageInterceptor.preHandle():北 斗 殘 悔 拳
MessageController.getMessage():お前はもう死んでいる
MessageInterceptor.postHandle():なに!?
MessageInterceptor.afterCompletion:たわば!!
以上就是在Spring Boot應用程式加上攔截器的簡單範例。
範例完成後的專案目錄結構如下。
沒有留言:
張貼留言