問題描述:
使用springMVC的時候,有些時候會需要擷取請求或者響應對象,例如在身份驗證的時候,需要擷取請求頭中的token,在做登入系統的時候需要使用response對象向用戶端添加cookie,一個有效的做法是在controller的方法中添加對應參數如下所示:
@RestController
public class Test2Contrller {
@RequestMapping("/test")
public void test(HttpServletRequest req, HttpServletResponse res) {
// todo
}
}
這樣做有一個問題,就是如果這個系統是作為接口并希望被遠端調用的,那麼額外的參數的存在便會破壞原本的接口定義,造成麻煩,下面介紹兩種不需要在方法中增加額外參數就能擷取request和response的方式
第一種方式:通過RequestContextHolder類的方法擷取requestAttributes,再從中擷取請求和響應對象;
@RestController
public class Test2Contrller {
@RequestMapping("/testreq")
public void test() {
// 獲得request對象,response對象
ServletRequestAttributes attributes = (ServletRequestAttributes) RequestContextHolder.getRequestAttributes();
HttpServletRequest request = attributes.getRequest();
HttpServletResponse response = attributes.getResponse();
try {
response.getWriter().write("hello");
} catch (IOException e) {
e.printStackTrace();
}
Enumeration<String> headerNames = request.getHeaderNames();
while (headerNames.hasMoreElements()) {
String name = headerNames.nextElement();
String value = request.getHeader(name);
System.out.println(name + "===========" + value);
}
}
}
第二種方式:可以将請求和響應對象抽取出來放在一個超類中,需要使用這兩個對象的controller繼承這個類,直接使用即可,代碼如下:
超類:
public class BaseController {
// 這些對象何以直接被子類使用
protected HttpServletRequest request;
protected HttpServletResponse response;
protected HttpSession session;
@ModelAttribute
public void setReqAndRes(HttpServletRequest req, HttpServletResponse res) {
this.request = req;
this.response = res;
this.session = req.getSession();
}
}
@RestController
public class Test3Contrller extends BaseController{
@RequestMapping("/testreq2")
public void test() {
try {
response.getWriter().write("hello");
} catch (IOException e) {
e.printStackTrace();
}
Enumeration<String> headerNames = request.getHeaderNames();
while (headerNames.hasMoreElements()) {
String name = headerNames.nextElement();
String value = request.getHeader(name);
System.out.println(name + "===========" + value);
}
}
}