1:定义一个注解,例如:
@Documented
@Retention(RetentionPolicy.RUNTIME)
@Target(ElementType.METHOD)
public @interface RedisLock {
// 60s
int timeOut() default 60;
}
:2:将该注解使用到需要考虑分布式的方法上
3:切面
/**
* 环绕通知:灵活自由的在目标方法中切入代码
*/
@Around("aspect()")
public void around(ProceedingJoinPoint joinPoint) throws Throwable {
String methodName = joinPoint.getSignature().getName();
Class<?> targetClass = joinPoint.getTarget().getClass();
Class<?>[] parameterTypes = ((MethodSignature) joinPoint.getSignature()).getParameterTypes();
Method objMethod = targetClass.getMethod(methodName, parameterTypes);
RedisLock annotation = objMethod.getDeclaredAnnotation(RedisLock.class);
String key = targetClass.getName() + "-" + methodName;
Boolean result = redisTemplate.opsForValue().setIfAbsent(key, UUID.randomUUID().toString().replaceAll("-", ""), annotation.timeOut(), TimeUnit.SECONDS);
if (null == result || !result ) {
log.info(key + " get lock fail return");
return;
}
try {
Date beginTime = new Date();
log.info("准备执行任务:{},开始时间为:{}", methodName, beginTime);
joinPoint.proceed();
Date endTime = new Date();
log.info("结束执行任务:{},结束时间为:{},总共用时{}", methodName, endTime, (endTime.getTime() - beginTime.getTime()) / 1000 + "秒");
} catch (Exception e) {
log.info(key + " Exception:{}", e);
} finally {
redisTemplate.delete(key);
}
}
4 注意:最后finally 中 一定要吧key删掉