SpringBoot自定义注解 + AOP+分布式Redis 防止重复提交
要实现基于Spring Boot的自定义注解、AOP和分布式Redis防止重复提交,你可以按照以下步骤操作:
- 创建自定义注解:
@Target(ElementType.METHOD)
@Retention(RetentionPolicy.RUNTIME)
public @interface PreventDuplicateSubmit {
// 可以定义注解属性,例如超时时间等
}
- 创建一个AOP切面来处理注解:
@Aspect
@Component
public class PreventDuplicateSubmitAspect {
@Autowired
private StringRedisTemplate stringRedisTemplate;
@Around("@annotation(PreventDuplicateSubmit)")
public Object around(ProceedingJoinPoint joinPoint, PreventDuplicateSubmit annotation) throws Throwable {
MethodSignature signature = (MethodSignature) joinPoint.getSignature();
Method method = signature.getMethod();
// 获取注解属性或者默认值
// int timeout = annotation.timeout();
// 获取请求的唯一标识,可以根据实际情况生成,例如用户ID、请求参数等
String key = generateKey(method, joinPoint.getArgs());
// 使用Redis的set命令,如果返回true则执行方法,否则返回提示信息
if (stringRedisTemplate.opsForValue().setIfAbsent(key, "lock", 10, TimeUnit.SECONDS)) {
try {
return joinPoint.proceed();
} finally {
// 方法执行完毕后删除key,以便后续请求可以正常提交
stringRedisTemplate.delete(key);
}
} else {
// 如果操作失败,返回提示信息,可以是自定义的ResponseEntity或其他格式
return ResponseEntity.status(HttpStatus.CONFLICT).body("Operation is in progress.");
}
}
private String generateKey(Method method, Object[] args) {
// 根据方法名和参数生成唯一的key
// 例如: method.getName() + "_" + Arrays.toString(args)
return "prevent_duplicate_submit_" + UUID.randomUUID().toString();
}
}
- 在需要防止重复提交的方法上使用
@PreventDuplicateSubmit
注解:
@RestController
public class MyController {
@PreventDuplicateSubmit
@PostMapping("/submit")
public ResponseEntity<?> submit() {
// 方法逻辑
return ResponseEntity.ok("Operation completed.");
}
}
确保你的Spring Boot项目已经包含了spring-boot-starter-data-redis
依赖,以便使用StringRedisTemplate
。
以上代码提供了一个基本的示例,你可能需要根据实际情况调整generateKey
方法,以确保生成的key能够唯一地标识每个请求。同时,超时时间(例如10秒)可以根据实际需求进行调整,以满足需求。
评论已关闭