我們可以先看一下為什么不能被捕獲?
很明顯JwtFilter的祖宗是Fliter,而我們自己定義的全局異常處理器@RestControllerAdvice
這個注解是 @ControllerAdvice 和 @ResponseBody的結合體。
主要是針對的我們controller控制器的。而過濾器是在這個之前進行處理的。我們在Filter里面進行拋出異常,那么該怎么做呢?
@RestControllerAdvice
public class GlobalExceptionHandler {
xxxxx
}
MyRealm域對象
@Override
protected AuthenticationInfo doGetAuthenticationInfo(AuthenticationToken authenticationToken) throws AuthenticationException {
//對傳入的token進行類型轉換
MyJsonWebToken myJsonWebToken = (MyJsonWebToken) authenticationToken;
String token = myJsonWebToken.getCredentials() + "";
//直接通過redis進行判斷
RbacManagerDTO rbacManagerDTO = (RbacManagerDTO) redisTemplate.opsForValue().get(token);
if (null != rbacManagerDTO) {
return new SimpleAuthenticationInfo(token, token, "myRealm");
} else {
throw new AuthenticationException("token已過期,請重新登錄");
}
}
Jwt驗證步驟
@SneakyThrows
@Override
protected boolean isAccessAllowed(ServletRequest request, ServletResponse response, Object mappedValue) {
//檢查認證請求,判斷請求頭中是否有token,有就執行登錄驗證
if (isLoginAttempt(request, response)) {
try {
//執行登錄
executeLogin(request, response);
//全局異常無法捕獲filter里的異常,這里就使用請求轉發給controller,返回給前端
} catch (AuthenticationException e) {
response401(request, response, e.getMessage());
} catch (Exception e) {
//如果沒有token,那么就請求轉發到到401請求,讓410controller返回前端一個請求
response401(request, response, "其他異常");
}
} else {
//沒有token
response401(request, response, "沒有token");
}
return true;
}
具體實現response401()方法
private void response401(ServletRequest request, ServletResponse response
, String msg) throws ServletException, IOException {
HttpServletRequest httpServletRequest = (HttpServletRequest) request;
HttpServletResponse httpServletResponse = (HttpServletResponse) response;
try {
// //請求轉發401controller
httpServletRequest.getRequestDispatcher("/rbacManager/401/" + msg).forward(request, response);
} catch (ServletException | IOException e) {
e.printStackTrace();
}
}
401專屬controller
@GetMapping("/401/{msg}")
public ResponseResult error (@PathVariable("msg") String msg){
return new ResponseResult(400,msg,null);
}
這樣前台就可以收到我們的狀態了。而我們的域對象的異常也算是成功返回給前端了。ヾ(✿゚▽゚)ノ
結果展示: