springboot通过注解实现拦截器的效果

需求:每一个请求都需要签名认证,即在外部请求的过程中需要在URI末尾?后加上key=value形式的参数Query Param

Query Param : timestamp,nonce_str,sign(timestamp:时间戳;noce_str:随机字符串;sign:appid×tamp&nonce_str&appsecret通过sha256加密获得字符串)

例:https://生产环境/test?timestamp=nonce_str=sign=

@Documented
@Target({ElementType.METHOD,ElementType.TYPE})
@Retention(RetentionPolicy.RUNTIME)
public @interface RequireSignature {
}
@Component
public class ExternalServiceInterceptor extends HandlerInterceptorAdapter {

    private Logger logger = LoggerFactory.getLogger(getClass());

    private static final String appid = "1646464644654646";

    private static final String appsecret = "ajgddqndqkdqbdqn";

    @Override
    public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
        Method method = ((HandlerMethod) handler).getMethod();
        if (AnnotatedElementUtils.isAnnotated(method, RequireSignature.class)) {
            long now = System.currentTimeMillis();
            String timestamp = request.getParameter("timestamp");
            Long timestampGain = Long.parseLong(timestamp);
            if (Math.abs(now - timestampGain) > 3_000_000) {
                logger.error("签名时间[" + timestampGain + "]已经过期,请重试!");
                throw new BadRequestException("签名已经过期,请重试!");
            }
            String nonce_str = request.getParameter("nonce_str");
            String signGain = request.getParameter("sign");
            if (nonce_str.isEmpty() || signGain.isEmpty()) {
                logger.error("签名不存在,请稍后重试!");
                throw new BadRequestException("签名不存在,请稍后重试!");
            }
            String sign = DigestUtils.sha256Hex(appid + "&"+ timestamp + "&" + nonce_str + "&" + appsecret).toLowerCase();
            if (!signGain.equals(sign)) {
                logger.error("签名sign [ " + signGain + " ] 错误!");
                throw new BadRequestException("签名sign [ " + signGain + " ] 错误!");
            }
        }
        return super.preHandle(request, response, handler);
    }
}

在需要签名验证的请求接口上加上@RequireSignature注解即可

@RequireSignature
    @RequestMapping(value = "test",method = RequestMethod.GET)
    public JSONObject getKey(){
        return testService.getKey();
    }
}

你可能感兴趣的:(springboot通过注解实现拦截器的效果)