package cn.com.usky.iot.auth; import cn.com.usky.iot.controller.login.LoginService; import cn.com.usky.utils.DESUtils; import cn.com.usky.utils.ListUtil; import cn.com.usky.utils.MapUtils; import com.alibaba.fastjson.JSONException; import com.alibaba.fastjson.JSONObject; import org.apache.commons.codec.binary.Base64; import org.apache.commons.lang3.StringUtils; import org.apache.log4j.Logger; import org.joda.time.DateTime; import org.springframework.orm.hibernate3.HibernateTemplate; import javax.servlet.http.Cookie; import javax.servlet.http.HttpServletRequest; import java.util.Collections; import java.util.HashMap; import java.util.List; import java.util.Map; public final class TokenAuthService { private LoginService loginService; public LoginService getLoginService() { return loginService; } public void setLoginService(LoginService loginService) { this.loginService = loginService; } private HibernateTemplate hibernateTemplate; public HibernateTemplate getHibernateTemplate() { return hibernateTemplate; } public void setHibernateTemplate(HibernateTemplate hibernateTemplate) { this.hibernateTemplate = hibernateTemplate; } private static Logger LOGGER = Logger.getLogger(TokenAuthService.class); /** * token 用户Id **/ public static String TOKEN_USERID = "userId"; /** * token有效期开始时间[登录时间] **/ public static String TOKEN_LOGIN_TIME = "loginTime"; /** * token有效期结束时间[截止时间] **/ public static String TOKEN_END_TIME = "endTime"; /** * token **/ public static String TOKEN = "token"; /** * @param token 认证字符 * @return TokenAuthEnum 认证result枚举 * @author laowo 验证Token **/ public TokenAuthBO verifyToken(String token) { if (StringUtils.isBlank(token)) { LOGGER.warn("token认证开始[end], token is null~"); return new TokenAuthBO(TokenAuthEnum.FAIL_ISNULL, Collections.emptyMap()); } JSONObject tokenJson = null; try { String base64Token = new String(Base64.decodeBase64(token)); String decrypt = DESUtils.decrypt(base64Token); tokenJson = JSONObject.parseObject(decrypt); if (MapUtils.isBlank(tokenJson) || tokenJson.isEmpty()) { throw new SecurityException("tokenJson is NULL"); } tokenJson.put(TOKEN, token); } catch (SecurityException | JSONException ex) { LOGGER.error("token 解析解密异常,message: " + ex.getMessage()); return new TokenAuthBO(TokenAuthEnum.FAIL, Collections.emptyMap()); } if (MapUtils.isEmptyMap(tokenJson, new String[]{TOKEN_USERID, TOKEN_LOGIN_TIME, TOKEN_END_TIME})) { LOGGER.warn("token缺失数据~"); return new TokenAuthBO(TokenAuthEnum.FAIL_DATA_ERROR, tokenJson); } if (!StringUtils.isNumeric(tokenJson.getString(TOKEN_USERID)) || !StringUtils.isNumeric(tokenJson.getString(TOKEN_LOGIN_TIME)) || !StringUtils.isNumeric(tokenJson.getString(TOKEN_END_TIME))) { LOGGER.warn("token数据格式有误~"); return new TokenAuthBO(TokenAuthEnum.FAIL_DATA_ERROR, tokenJson); } Integer loginTime = Integer.parseInt(tokenJson.getString(TOKEN_LOGIN_TIME)); Integer endTime = Integer.parseInt(tokenJson.getString(TOKEN_END_TIME)); // 判断token时间有效性 long thisTime = System.currentTimeMillis() / 1000; if (!(thisTime >= loginTime && thisTime <= endTime)) { LOGGER.warn("token timeOut, token解析后的数据,tokenJson: " + tokenJson + ", thisTime: " + thisTime); return new TokenAuthBO(TokenAuthEnum.FAIL_TIMEOUT, tokenJson); } // 判断userId有效性 String userId = tokenJson.getString(TOKEN_USERID); List userInfo = loginService.getObjectByUserId(userId); if (ListUtil.isBlank(userInfo)) { LOGGER.warn("认证失败,非有效用户~"); return new TokenAuthBO(TokenAuthEnum.FAIL, tokenJson); } LOGGER.info("token认证成功 \n" + "token=" + token + "\n" + "tokenInfo=" + tokenJson); return new TokenAuthBO(TokenAuthEnum.SUCCESS, tokenJson); } /** * @param userId 用户Id, loginTime登录时间, changePwdTime密码修改时间 * @return TokenAuthEnum 认证result枚举 * @author laowo 创建Token **/ public String createToken(String userId, Long loginTime) { LOGGER.info("创建Token[start], userId: " + userId + ", loginTime: " + loginTime + ""); JSONObject tokenJson = new JSONObject(); tokenJson.put(TOKEN_USERID, userId); tokenJson.put(TOKEN_LOGIN_TIME, loginTime); DateTime time = new DateTime(loginTime * 1000); time = time.plusMonths(1); long endTime = time.getMillis() / 1000; tokenJson.put(TOKEN_END_TIME, endTime); String encryptToken = DESUtils.encrypt(tokenJson.toJSONString()); String token = Base64.encodeBase64URLSafeString(encryptToken.getBytes()); LOGGER.info("创建Token[end], token: " + token); return token; } /** * 登录验证: code: 1,用户登录成功,获取用户userid;2,用户未登录;3,token失效 * * @param request * @return * @author shaoxiaowen 2019/6/18 */ public Map loginChek(HttpServletRequest request) { LOGGER.info("登录验证"); Map map = new HashMap(); Cookie[] cookies = request.getCookies(); if (cookies == null) { map.put("code", "2"); return map; } else { for (Cookie cookie : cookies) { if (cookie.getName().equals("authToken")) { String loginInfo = cookie.getValue(); TokenAuthBO tokenBo = verifyToken(loginInfo); if (!tokenBo.isAuthState()) { map.put("code", "3"); return map; } else { String userId = tokenBo.getData().getString("userId"); map.put("code", "1"); map.put("userId", userId); return map; } } } return map; } } public static void main(String[] args) { String token = "TC1Yakh3TE45cWtyNXI0S3pXZW53Yms1RXQzSmVMQVFkTDQtek9lMGIxRG13NXVSZ1prRU1SallwOEF1NjRFMWVvV01qeUtJXzI1ZzFaeUFHVTg5bzNIaExZV093Q1o2ZmEzMko5Ulp4aFdpR1BYWm1Bdk4zUQ"; String base64Token = new String(Base64.decodeBase64(token)); String decrypt = DESUtils.decrypt(base64Token); System.out.println(decrypt); } }