|
@@ -9,11 +9,16 @@ import javax.servlet.http.HttpServletRequest;
|
|
|
import javax.servlet.http.HttpServletResponse;
|
|
|
|
|
|
import com.jiayue.ssi.constant.CacheConstants;
|
|
|
+import com.jiayue.ssi.constant.Constants;
|
|
|
+import com.jiayue.ssi.constant.LoginConstants;
|
|
|
import com.jiayue.ssi.entity.SysUser;
|
|
|
+import com.jiayue.ssi.factory.LoginFactory;
|
|
|
import com.jiayue.ssi.service.SysUserService;
|
|
|
import com.jiayue.ssi.service.impl.UserServiceImpl;
|
|
|
import com.jiayue.ssi.util.DateUtils;
|
|
|
import com.jiayue.ssi.util.ResponseInfo;
|
|
|
+import io.jsonwebtoken.Claims;
|
|
|
+import io.jsonwebtoken.ExpiredJwtException;
|
|
|
import lombok.RequiredArgsConstructor;
|
|
|
import lombok.extern.slf4j.Slf4j;
|
|
|
import org.springframework.core.annotation.Order;
|
|
@@ -40,11 +45,13 @@ public class JwtAuthenticationTokenFilter extends OncePerRequestFilter {
|
|
|
UserServiceImpl userServiceImpl;
|
|
|
JwtTokenUtil jwtTokenUtil;
|
|
|
SysUserService sysUserService;
|
|
|
+ int bfhhs;
|
|
|
|
|
|
- public JwtAuthenticationTokenFilter(UserServiceImpl userServiceImpl, JwtTokenUtil jwtTokenUtil,SysUserService sysUserService) {
|
|
|
+ public JwtAuthenticationTokenFilter(UserServiceImpl userServiceImpl, JwtTokenUtil jwtTokenUtil,SysUserService sysUserService,int bfhhs) {
|
|
|
this.userServiceImpl = userServiceImpl;
|
|
|
this.jwtTokenUtil = jwtTokenUtil;
|
|
|
this.sysUserService = sysUserService;
|
|
|
+ this.bfhhs = bfhhs;
|
|
|
}
|
|
|
|
|
|
@Override
|
|
@@ -53,63 +60,96 @@ public class JwtAuthenticationTokenFilter extends OncePerRequestFilter {
|
|
|
SecurityContextHolder.getContext().getAuthentication();
|
|
|
String token = request.getHeader("Authorization");
|
|
|
if (!StringUtils.isEmpty(token)) {
|
|
|
- String username = jwtTokenUtil.getUsernameFromToken(token);
|
|
|
- if (username != null) {
|
|
|
- if (CacheConstants.LOGIN_TOKEN_MAP.get(username) == null) {
|
|
|
+ try {
|
|
|
+ Claims claims = jwtTokenUtil.getClaimsFromToken(token);
|
|
|
+ if (claims==null){
|
|
|
+ // 无效token
|
|
|
ResponseInfo.doResponse(response, "令牌无效,请重新登录!", 403);
|
|
|
return;
|
|
|
- } else {
|
|
|
- String cacheToken = CacheConstants.LOGIN_TOKEN_MAP.get(username);
|
|
|
- //内存token和当前token一致 说明是当前登陆用户访问
|
|
|
- if (!token.equals(cacheToken)) {
|
|
|
- ResponseInfo.doResponse(response, "账号已在另一台机器登录,请重新登录!", 403);
|
|
|
+ }
|
|
|
+
|
|
|
+ String username = claims.getSubject();
|
|
|
+ if (username != null) {
|
|
|
+ if (CacheConstants.LOGIN_TOKEN_MAP.get(username) == null) {
|
|
|
+ ResponseInfo.doResponse(response, "令牌无效,请重新登录!", 403);
|
|
|
return;
|
|
|
+ } else {
|
|
|
+ String cacheToken = CacheConstants.LOGIN_TOKEN_MAP.get(username);
|
|
|
+ //内存token和当前token一致 说明是当前登陆用户访问
|
|
|
+ if (!token.equals(cacheToken)) {
|
|
|
+ ResponseInfo.doResponse(response, "账号已在另一台机器登录,请重新登录!", 403);
|
|
|
+ return;
|
|
|
+ }
|
|
|
}
|
|
|
}
|
|
|
- }
|
|
|
|
|
|
- if (username != null && SecurityContextHolder.getContext().getAuthentication() == null) {
|
|
|
- UserDetails userDetails = userServiceImpl.loadUserByUsername(username);
|
|
|
- SysUser user = (SysUser) userDetails;
|
|
|
- if (user.getStatus().equals("2")){
|
|
|
- ResponseInfo.doResponse(response, "账号已注销,不能登录!", 403);
|
|
|
- return;
|
|
|
- }
|
|
|
- if (user.getExpDate() != null) {
|
|
|
- // 判断账号截止日期
|
|
|
- Date lastDate = DateUtils.getDayLastTime(user.getExpDate());
|
|
|
- if (new Date().after(lastDate)) {
|
|
|
- if ("0".equals(user.getStatus())){
|
|
|
- // 将正常状态变为锁定
|
|
|
+ if (username != null && SecurityContextHolder.getContext().getAuthentication() == null) {
|
|
|
+ UserDetails userDetails = userServiceImpl.loadUserByUsername(username);
|
|
|
+ SysUser user = (SysUser) userDetails;
|
|
|
+ if (user.getStatus().equals("2")){
|
|
|
+ ResponseInfo.doResponse(response, "账号已注销,不能登录!", 403);
|
|
|
+ return;
|
|
|
+ }
|
|
|
+ if (user.getExpDate() != null) {
|
|
|
+ // 判断账号截止日期
|
|
|
+ Date lastDate = DateUtils.getDayLastTime(user.getExpDate());
|
|
|
+ if (new Date().after(lastDate)) {
|
|
|
+ if ("0".equals(user.getStatus())){
|
|
|
+ // 将正常状态变为锁定
|
|
|
// user.setLockTime(System.currentTimeMillis());
|
|
|
- user.setStatus("1");
|
|
|
- Boolean bo = sysUserService.updateUser(user);
|
|
|
- if (!bo){
|
|
|
- log.info(user.getUsername()+"账号已过有效期被锁定失败");
|
|
|
- }
|
|
|
- else{
|
|
|
- log.info(user.getUsername()+"账号已过有效期被锁定成功");
|
|
|
+ user.setStatus("1");
|
|
|
+ Boolean bo = sysUserService.updateUser(user);
|
|
|
+ if (!bo){
|
|
|
+ log.info(user.getUsername()+"账号已过有效期被锁定失败");
|
|
|
+ }
|
|
|
+ else{
|
|
|
+ log.info(user.getUsername()+"账号已过有效期被锁定成功");
|
|
|
+ }
|
|
|
}
|
|
|
+ ResponseInfo.doResponse(response, "账号已过有效期被锁定,请联系管理员!", 403);
|
|
|
+ return;
|
|
|
}
|
|
|
- ResponseInfo.doResponse(response, "账号已过有效期被锁定,请联系管理员!", 403);
|
|
|
+ }
|
|
|
+ if ("1".equals(user.getStatus()) && user.getLockTime()==0){
|
|
|
+ ResponseInfo.doResponse(response, "账号已被锁定,请联系管理员!", 403);
|
|
|
return;
|
|
|
}
|
|
|
+ if (jwtTokenUtil.validateToken(token, userDetails)) {
|
|
|
+ // 将用户信息存入 authentication,方便后续校验
|
|
|
+ UsernamePasswordAuthenticationToken
|
|
|
+ authentication = new UsernamePasswordAuthenticationToken(userDetails, null, userDetails.getAuthorities());
|
|
|
+ authentication.setDetails(new WebAuthenticationDetailsSource().buildDetails(request));
|
|
|
+ // 将 authentication 存入 ThreadLocal,方便后续获取用户信息
|
|
|
+ SecurityContextHolder.getContext().setAuthentication(authentication);
|
|
|
+ }
|
|
|
}
|
|
|
- if ("1".equals(user.getStatus()) && user.getLockTime()==0){
|
|
|
- ResponseInfo.doResponse(response, "账号已被锁定,请联系管理员!", 403);
|
|
|
+ }
|
|
|
+ catch (ExpiredJwtException expiredJwtException){
|
|
|
+ Claims claims = expiredJwtException.getClaims();
|
|
|
+ String username = claims.getSubject();
|
|
|
+ String cacheToken = CacheConstants.LOGIN_TOKEN_MAP.get(username);
|
|
|
+ //内存token和当前token一致 说明是当前登陆用户访问
|
|
|
+ if (cacheToken!=null && !token.equals(cacheToken)) {
|
|
|
+ ResponseInfo.doResponse(response, "账号已在另一台机器登录,请重新登录!", 403);
|
|
|
return;
|
|
|
}
|
|
|
- if (jwtTokenUtil.validateToken(token, userDetails)) {
|
|
|
- // 将用户信息存入 authentication,方便后续校验
|
|
|
- UsernamePasswordAuthenticationToken
|
|
|
- authentication = new UsernamePasswordAuthenticationToken(userDetails, null, userDetails.getAuthorities());
|
|
|
- authentication.setDetails(new WebAuthenticationDetailsSource().buildDetails(request));
|
|
|
- // 将 authentication 存入 ThreadLocal,方便后续获取用户信息
|
|
|
- SecurityContextHolder.getContext().setAuthentication(authentication);
|
|
|
+ else{
|
|
|
+ // 登录连接超时,保存审计
|
|
|
+ LoginFactory.recordLogininfor(claims.getSubject(), Constants.LOGIN_FAIL, "连接超时");
|
|
|
+ // 将token存储内存中,便于重复登录比对
|
|
|
+ CacheConstants.LOGIN_TOKEN_MAP.remove(claims.getSubject());
|
|
|
+ LoginConstants.sessionMap.remove(claims.getSubject());
|
|
|
+ ResponseInfo.doResponse(response, "令牌无效,请重新登录!", 403);
|
|
|
+ return;
|
|
|
}
|
|
|
}
|
|
|
} else {
|
|
|
if ("POST".equalsIgnoreCase(request.getMethod()) && defaultFilterProcessUrl.equals(request.getServletPath())) {
|
|
|
+ // 判断并发会话数是否满足
|
|
|
+ if (LoginConstants.sessionMap.size()+1>bfhhs){
|
|
|
+ ResponseInfo.doResponse(response, "系统会话数已满,不能登录!", 401);
|
|
|
+ return;
|
|
|
+ }
|
|
|
// 用户名密码登录提交,判断账号有效期
|
|
|
try {
|
|
|
UserDetails userDetails = userServiceImpl.loadUserByUsername(request.getParameter("username"));
|