Api介面鑑權註解實現
阿新 • • 發佈:2021-10-08
定義註解
1 import java.lang.annotation.Documented; 2 import java.lang.annotation.ElementType; 3 import java.lang.annotation.Retention; 4 import java.lang.annotation.RetentionPolicy; 5 import java.lang.annotation.Target; 6 7 8 /** 9 * 驗簽註解 10 * @version 1.0 11 * @date 2021/9/30 12 */ 13 @Target(ElementType.METHOD)14 @Retention(RetentionPolicy.RUNTIME) 15 @Documented 16 public @interface ApiHeaderCheck { 17 }
定義切面
@Aspect
@Component
@Slf4j
public class ApiHeaderCheckAspect {
//30s超時
public static final int REQUEST_EXPIRE_TIME = 30000;
@Before("@annotation(apiHeaderCheck)")
public void checkAuth(ApiHeaderCheck apiHeaderCheck) {
HttpServletRequest request = currentRequest();
if (Objects.isNull(request)) {
return;
}
String timeStampStr = request.getHeader("x-ts");
String sign = request.getHeader("x-sign");
if (StringUtils.isEmpty(timeStampStr) || StringUtils.isEmpty(sign)) {
throw new BaseException(ApiAuthErrorEnum.UNAUTHORIZED);
}
String regex = "^\\d{13}$";
if (!Pattern.matches(regex, timeStampStr.trim())) {
throw new BaseException(ApiAuthErrorEnum.UNAUTHORIZED);
}
long requestTimestamp = Long.parseLong(timeStampStr);
if (System.currentTimeMillis() - requestTimestamp > REQUEST_EXPIRE_TIME) {
throw new BaseException(ApiAuthErrorEnum.REQUEST_EXPIRED);
}
//驗證RSA簽名
String targetTimestamp = RsaUtil.decrypt(sign);
if (!targetTimestamp.equals(timeStampStr)) {
throw new BaseException(ApiAuthErrorEnum.UNAUTHORIZED);
}
}
/**
* 獲取當前請求資訊
* @return Current request or null
*/
private HttpServletRequest currentRequest() {
ServletRequestAttributes servletRequestAttributes = (ServletRequestAttributes) RequestContextHolder.getRequestAttributes();
return Optional.ofNullable(servletRequestAttributes).map(ServletRequestAttributes::getRequest).orElse(null);
}
}
定義異常
1 public enum ApiAuthErrorEnum implements IErrorCode { 2 3 UNAUTHORIZED("10001", "Unauthorized"), 4 REQUEST_EXPIRED("10002", "Request Expired"), 5 ; 6 7 private final String errorCode; 8 private final String errorMessage; 9 private static final String ERROR_CODE_START = "Auth-";10 11 ApiAuthErrorEnum(String errorCode, String errorMessage) { 12 this.errorCode = errorCode; 13 this.errorMessage = errorMessage; 14 } 15 16 @Override 17 public String getErrorCode() { 18 return ERROR_CODE_START + errorCode; 19 } 20 21 @Override 22 public String getErrorMessage() { 23 return errorMessage; 24 } 25 }
使用方式
在方法上新增@ApiHeaderCheck 註解即可