package cc.mrbird.febs.websocket; import cc.mrbird.febs.common.utils.AppContants; import cn.hutool.core.util.StrUtil; import cn.hutool.crypto.asymmetric.KeyType; import cn.hutool.crypto.asymmetric.RSA; import lombok.extern.slf4j.Slf4j; import org.springframework.http.server.ServerHttpRequest; import org.springframework.http.server.ServerHttpResponse; import org.springframework.stereotype.Component; import org.springframework.web.socket.WebSocketHandler; import org.springframework.web.socket.server.HandshakeInterceptor; import java.util.HashMap; import java.util.Map; /** * * @author XXX * @date 2020-09-01 **/ @Slf4j @Component public class WsAuthInterceptor implements HandshakeInterceptor { @Override public boolean beforeHandshake(ServerHttpRequest request, ServerHttpResponse response, WebSocketHandler webSocketHandler, Map map) throws Exception { // log.info("拦截器,握手前"); Map params = parseParameterMap(request.getURI().getQuery()); //invite_id_时间戳 例如:45656161_4554848489的加密 String token = params.get("token"); if (StrUtil.isNotBlank(token)) { String inviteId = token; // String inviteId = resolveToken(token); log.info("----->{}", inviteId); if (StrUtil.isBlank(inviteId) || AppContants.TIME_OUT.equals(inviteId)) { return false; } map.put("inviteId", inviteId); return true; } return false; } @Override public void afterHandshake(ServerHttpRequest request, ServerHttpResponse response, WebSocketHandler webSocketHandler, Exception e) { // log.info("握手后"); } private Map parseParameterMap(String queryString) { Map parameterMap = new HashMap<>(); String[] parameters = queryString.split("&"); for (String parameter : parameters) { String[] paramPair = parameter.split("="); if (paramPair.length == 2) { parameterMap.put(paramPair[0], paramPair[1]); } } return parameterMap; } private String resolveToken(String token) { try { RSA rsa = new RSA(AppContants.PRIVATE_KEY, null); String[] tokens = StrUtil.split(rsa.decryptStr(token, KeyType.PrivateKey), "_"); // log.info("websocket token : {}, timestemp : {}", tokens[0], tokens[1]); if (verifyTokenExpired(Long.parseLong(tokens[1]))) { return tokens[0]; } else { return AppContants.TIME_OUT; } } catch (Exception e) { log.error("#解析token异常#", e); return null; } } private Boolean verifyTokenExpired(Long time) { boolean isDebug = false; if (!isDebug) { long currentTime = System.currentTimeMillis(); return currentTime - time <= 10000; } return true; } }