| | |
| | | package com.sandu.common.security; |
| | | |
| | | import cn.hutool.core.util.StrUtil; |
| | | import cn.hutool.json.JSONUtil; |
| | | import com.sandu.common.enums.ResponseStatusEnums; |
| | | import com.sandu.common.redis.online.OnlineUser; |
| | | import com.sandu.common.redis.online.OnlineUserService; |
| | | import com.sandu.common.security.config.SecurityProperties; |
| | | import com.sandu.common.security.jwt.JwtTokenProvider; |
| | | import com.sandu.common.security.token.TokenProvider; |
| | | import com.sandu.common.util.ResponseUtil; |
| | | import com.sandu.common.util.SpringContextHolder; |
| | | import io.jsonwebtoken.ExpiredJwtException; |
| | | import org.springframework.beans.factory.annotation.Autowired; |
| | | import org.springframework.security.core.AuthenticationException; |
| | | import org.springframework.security.web.AuthenticationEntryPoint; |
| | | import org.springframework.stereotype.Component; |
| | | import org.springframework.util.StringUtils; |
| | | |
| | | import javax.annotation.Resource; |
| | | import javax.servlet.http.HttpServletRequest; |
| | | import javax.servlet.http.HttpServletResponse; |
| | | import java.io.IOException; |
| | |
| | | @Component |
| | | public class JwtAuthenticationEntryPoint implements AuthenticationEntryPoint { |
| | | |
| | | @Autowired |
| | | private JwtTokenProvider tokenProvider; |
| | | @Resource |
| | | private TokenProvider tokenProvider; |
| | | @Resource |
| | | private SecurityProperties properties; |
| | | |
| | | @Override |
| | | public void commence(HttpServletRequest request, |
| | | HttpServletResponse response, |
| | | AuthenticationException authException) throws IOException { |
| | | |
| | | String token = tokenProvider.getToken(request); |
| | | SecurityProperties properties = SpringContextHolder.getBean(SecurityProperties.class); |
| | | String token = request.getHeader(properties.getHeader()); |
| | | |
| | | if (!StringUtils.hasText(token)) { |
| | | writeResponse(response, ResponseUtil.error(ResponseStatusEnums.TOKEN_NONE.getCode(), ResponseStatusEnums.TOKEN_NONE.getMessage())); |
| | | return; |
| | | } |
| | | |
| | | LoginUserInfo loginUserInfo = tokenProvider.validateToken(token); |
| | | |
| | | Throwable exception = tokenProvider.getException(token); |
| | | |
| | | // jwt过期 替换新的jwt |
| | | if (exception instanceof ExpiredJwtException) { |
| | | String usernameForce = tokenProvider.getSubjectForce(token); |
| | | if (properties.isCacheOnline()) { |
| | | OnlineUserService onlineUserService = SpringContextHolder.getBean(OnlineUserService.class); |
| | | OnlineUser onlineUser = onlineUserService.getOne(properties.getOnlineKey() + usernameForce); |
| | | if (onlineUser == null || !token.equals(onlineUser.getToken())) { |
| | | // redis上没有 或者不是当前用户的token 返回失效 |
| | | writeResponse(response, ResponseUtil.error(ResponseStatusEnums.TOKEN_INVALID.getCode(), ResponseStatusEnums.TOKEN_INVALID.getMessage())); |
| | | } else { |
| | | // 返回过期,携带新的token |
| | | String refreshToken = tokenProvider.refreshToken(token); |
| | | onlineUser.setToken(refreshToken); |
| | | onlineUserService.updateOne(onlineUser); |
| | | writeResponse(response, ResponseUtil.error(ResponseStatusEnums.TOKEN_EXPIRED.getCode(), ResponseStatusEnums.TOKEN_EXPIRED.getMessage(), properties.getTokenStartWith() + refreshToken)); |
| | | } |
| | | } else { |
| | | // 返回过期,携带新的token |
| | | String refreshToken = properties.getTokenStartWith() + tokenProvider.refreshToken(token); |
| | | writeResponse(response, ResponseUtil.error(ResponseStatusEnums.TOKEN_EXPIRED.getCode(), ResponseStatusEnums.TOKEN_EXPIRED.getMessage(), null)); |
| | | } |
| | | if (loginUserInfo == null) { |
| | | writeResponse(response, ResponseUtil.error(ResponseStatusEnums.TOKEN_INVALID.getCode(), ResponseStatusEnums.TOKEN_INVALID.getMessage())); |
| | | return; |
| | | } |
| | | |
| | | // 其他jwt解析异常 |
| | | if (exception != null) { |
| | | writeResponse(response, ResponseUtil.error(ResponseStatusEnums.TOKEN_INVALID.getCode(), ResponseStatusEnums.TOKEN_INVALID.getMessage())); |
| | | } else { |
| | | //jwt解析正常 看看是不是redis的问题 |
| | | if (properties.isCacheOnline()) { |
| | | String usernameForce = tokenProvider.getSubjectForce(token); |
| | | OnlineUserService onlineUserService = SpringContextHolder.getBean(OnlineUserService.class); |
| | | OnlineUser onlineUser = onlineUserService.getOne(properties.getOnlineKey() + usernameForce); |
| | | if (onlineUser != null && !token.equals(onlineUser.getToken())) { |
| | | // 和服务器保存的token不一样,说明在其他地方登录 |
| | | writeResponse(response, ResponseUtil.error(ResponseStatusEnums.SINGLE_LOGIN.getCode(), ResponseStatusEnums.SINGLE_LOGIN.getMessage())); |
| | | } else { |
| | | // 服务器没有在线用户token或者token不一致 都返回token失效 |
| | | writeResponse(response, ResponseUtil.error(ResponseStatusEnums.TOKEN_INVALID.getCode(), ResponseStatusEnums.TOKEN_INVALID.getMessage())); |
| | | } |
| | | } else { |
| | | writeResponse(response, ResponseUtil.error(ResponseStatusEnums.FAIL.getCode(), "认证出错")); |
| | | } |
| | | if (!StrUtil.equals(loginUserInfo.getToken(), token)) { |
| | | writeResponse(response, ResponseUtil.error(ResponseStatusEnums.SINGLE_LOGIN.getCode(), ResponseStatusEnums.SINGLE_LOGIN.getMessage())); |
| | | } |
| | | return; |
| | | |
| | | |
| | | // String token = tokenProvider.getToken(request); |
| | | // SecurityProperties properties = SpringContextHolder.getBean(SecurityProperties.class); |
| | | // |
| | | // if (!StringUtils.hasText(token)) { |
| | | // writeResponse(response, ResponseUtil.error(ResponseStatusEnums.TOKEN_INVALID.getCode(), ResponseStatusEnums.TOKEN_INVALID.getMessage())); |
| | | // return; |
| | | // } |
| | | // |
| | | // |
| | | // Throwable exception = tokenProvider.getException(token); |
| | | // |
| | | // // jwt过期 替换新的jwt |
| | | // if (exception instanceof ExpiredJwtException) { |
| | | // String usernameForce = tokenProvider.getSubjectForce(token); |
| | | // if (properties.isCacheOnline()) { |
| | | // OnlineUserService onlineUserService = SpringContextHolder.getBean(OnlineUserService.class); |
| | | // OnlineUser onlineUser = onlineUserService.getOne(properties.getOnlineKey() + usernameForce); |
| | | // if (onlineUser == null || !token.equals(onlineUser.getToken())) { |
| | | // // redis上没有 或者不是当前用户的token 返回失效 |
| | | // writeResponse(response, ResponseUtil.error(ResponseStatusEnums.TOKEN_INVALID.getCode(), ResponseStatusEnums.TOKEN_INVALID.getMessage())); |
| | | // } else { |
| | | // // 返回过期,携带新的token |
| | | // String refreshToken = tokenProvider.refreshToken(token); |
| | | // onlineUser.setToken(refreshToken); |
| | | // onlineUserService.updateOne(onlineUser); |
| | | // writeResponse(response, ResponseUtil.error(ResponseStatusEnums.TOKEN_EXPIRED.getCode(), ResponseStatusEnums.TOKEN_EXPIRED.getMessage(), properties.getTokenStartWith() + refreshToken)); |
| | | // } |
| | | // } else { |
| | | // // 返回过期,携带新的token |
| | | // String refreshToken = properties.getTokenStartWith() + tokenProvider.refreshToken(token); |
| | | // writeResponse(response, ResponseUtil.error(ResponseStatusEnums.TOKEN_EXPIRED.getCode(), ResponseStatusEnums.TOKEN_EXPIRED.getMessage(), null)); |
| | | // } |
| | | // return; |
| | | // } |
| | | // |
| | | // // 其他jwt解析异常 |
| | | // if (exception != null) { |
| | | // writeResponse(response, ResponseUtil.error(ResponseStatusEnums.TOKEN_INVALID.getCode(), ResponseStatusEnums.TOKEN_INVALID.getMessage())); |
| | | // } else { |
| | | // //jwt解析正常 看看是不是redis的问题 |
| | | // if (properties.isCacheOnline()) { |
| | | // String usernameForce = tokenProvider.getSubjectForce(token); |
| | | // OnlineUserService onlineUserService = SpringContextHolder.getBean(OnlineUserService.class); |
| | | // OnlineUser onlineUser = onlineUserService.getOne(properties.getOnlineKey() + usernameForce); |
| | | // if (onlineUser != null && !token.equals(onlineUser.getToken())) { |
| | | // // 和服务器保存的token不一样,说明在其他地方登录 |
| | | // writeResponse(response, ResponseUtil.error(ResponseStatusEnums.SINGLE_LOGIN.getCode(), ResponseStatusEnums.SINGLE_LOGIN.getMessage())); |
| | | // } else { |
| | | // // 服务器没有在线用户token或者token不一致 都返回token失效 |
| | | // writeResponse(response, ResponseUtil.error(ResponseStatusEnums.TOKEN_INVALID.getCode(), ResponseStatusEnums.TOKEN_INVALID.getMessage())); |
| | | // } |
| | | // } else { |
| | | // writeResponse(response, ResponseUtil.error(ResponseStatusEnums.FAIL.getCode(), "认证出错")); |
| | | // } |
| | | // } |
| | | // return; |
| | | |
| | | } |
| | | |