diff --git a/src/main/java/com/kwan/springbootkwan/annotation/RedisLock.java b/src/main/java/com/kwan/springbootkwan/annotation/RedisLock.java new file mode 100644 index 0000000000000000000000000000000000000000..fcc78928ea47b97998b187bd6ba44661465c3a5b --- /dev/null +++ b/src/main/java/com/kwan/springbootkwan/annotation/RedisLock.java @@ -0,0 +1,26 @@ +package com.kwan.springbootkwan.annotation; + +import org.springframework.core.annotation.AliasFor; +import org.springframework.stereotype.Component; + +import java.lang.annotation.*; + +@Target({ElementType.METHOD}) +@Retention(RetentionPolicy.RUNTIME) +@Documented +@Component +public @interface RedisLock { + String value() default ""; + + @AliasFor("key") + String name() default ""; + + @AliasFor("name") + String key() default ""; + + long expire() default 30000; // 默认锁的过期时间,单位毫秒 + + long timeout() default 0; // 默认获取锁的超时时间,单位毫秒 + + boolean fair() default false; // 是否使用公平锁 +} diff --git a/src/main/java/com/kwan/springbootkwan/aop/RedisLockAspect.java b/src/main/java/com/kwan/springbootkwan/aop/RedisLockAspect.java new file mode 100644 index 0000000000000000000000000000000000000000..13c9017f2de02299f25e6f5da073cb4ecd226a32 --- /dev/null +++ b/src/main/java/com/kwan/springbootkwan/aop/RedisLockAspect.java @@ -0,0 +1,62 @@ +package com.kwan.springbootkwan.aop; + +import com.kwan.springbootkwan.annotation.RedisLock; +import org.aspectj.lang.ProceedingJoinPoint; +import org.aspectj.lang.annotation.Around; +import org.aspectj.lang.annotation.Aspect; +import org.springframework.core.annotation.Order; +import org.springframework.data.redis.core.StringRedisTemplate; +import org.springframework.stereotype.Component; +import org.springframework.util.StringUtils; + +import java.util.concurrent.TimeUnit; +import java.util.concurrent.locks.Lock; +import java.util.concurrent.locks.ReentrantLock; + + +@Aspect +@Component +@Order(1) // 设置切面优先级 +public class RedisLockAspect { + + private final StringRedisTemplate redisTemplate; + + public RedisLockAspect(StringRedisTemplate redisTemplate) { + this.redisTemplate = redisTemplate; + } + + @Around("@annotation(redisLock)") + public Object doWithLock(ProceedingJoinPoint joinPoint, RedisLock redisLock) throws Throwable { + String lockKey = getLockKey(redisLock); + Lock lock = new ReentrantLock(redisLock.fair()); + boolean locked = false; + + try { + locked = lock.tryLock(redisLock.timeout(), TimeUnit.MILLISECONDS); + if (locked) { + if (StringUtils.hasText(lockKey)) { + redisTemplate.opsForValue().set(lockKey, "locked", redisLock.expire(), TimeUnit.MILLISECONDS); + } + return joinPoint.proceed(); + } else { + throw new RuntimeException("Failed to acquire lock."); + } + } finally { + if (locked) { + lock.unlock(); + if (StringUtils.hasText(lockKey)) { + redisTemplate.delete(lockKey); + } + } + } + } + + private String getLockKey(RedisLock redisLock) { + String lockKey = redisLock.key(); + if (!StringUtils.hasText(lockKey)) { + lockKey = redisLock.name(); + } + return lockKey; + } +} + diff --git a/src/main/java/com/kwan/springbootkwan/controller/ChatbotController.java b/src/main/java/com/kwan/springbootkwan/controller/ChatbotController.java index 76e0e70a78f7fa77238cc79062e11413b1c18382..eb45b42cc1dc24f47fdb8bb83253abac883845a8 100644 --- a/src/main/java/com/kwan/springbootkwan/controller/ChatbotController.java +++ b/src/main/java/com/kwan/springbootkwan/controller/ChatbotController.java @@ -8,7 +8,6 @@ import com.kwan.springbootkwan.entity.Result; import com.kwan.springbootkwan.entity.dto.ChatbotDTO; import com.kwan.springbootkwan.service.ChatbotService; import org.apache.commons.lang3.StringUtils; -import org.springframework.cache.annotation.Cacheable; import org.springframework.web.bind.annotation.DeleteMapping; import org.springframework.web.bind.annotation.GetMapping; import org.springframework.web.bind.annotation.PathVariable; @@ -57,11 +56,11 @@ public class ChatbotController { /** - * 分页查询所有数据 + * 分页查询所有数据,本地缓存的使用 * * @return 所有数据 */ - @Cacheable("chatbot-cache") +// @Cacheable("chatbot-cache") @GetMapping("/page") public Result selectAll(@RequestParam Integer page , @RequestParam Integer pageSize diff --git a/src/main/java/com/kwan/springbootkwan/controller/DepartmentController.java b/src/main/java/com/kwan/springbootkwan/controller/DepartmentController.java index e7184925c2900d934b686aab8de59789a2e37a88..77773aa6e9472b59329707d96d9bf66906f739e8 100644 --- a/src/main/java/com/kwan/springbootkwan/controller/DepartmentController.java +++ b/src/main/java/com/kwan/springbootkwan/controller/DepartmentController.java @@ -1,11 +1,18 @@ package com.kwan.springbootkwan.controller; +import com.kwan.springbootkwan.annotation.RedisLock; import com.kwan.springbootkwan.entity.Department; import com.kwan.springbootkwan.service.DepartmentService; import org.springframework.data.domain.Page; import org.springframework.data.domain.PageRequest; import org.springframework.http.ResponseEntity; -import org.springframework.web.bind.annotation.*; +import org.springframework.web.bind.annotation.DeleteMapping; +import org.springframework.web.bind.annotation.GetMapping; +import org.springframework.web.bind.annotation.PathVariable; +import org.springframework.web.bind.annotation.PostMapping; +import org.springframework.web.bind.annotation.PutMapping; +import org.springframework.web.bind.annotation.RequestMapping; +import org.springframework.web.bind.annotation.RestController; import javax.annotation.Resource; import java.util.List; @@ -63,6 +70,8 @@ public class DepartmentController { @GetMapping("/all") + @RedisLock(key = "myLock_queryTreeAll", expire = 5000, timeout = 3000) +// @RedisLock(key = "myLock_queryTreeAll", timeout = 10000) public ResponseEntity> queryTreeAll() { return ResponseEntity.ok(this.departmentService.queryTreeAll()); } diff --git a/src/main/java/com/kwan/springbootkwan/filter/TimeFilter.java b/src/main/java/com/kwan/springbootkwan/filter/TimeFilter.java index 98dff4a99dabf9d75fd3e3116c76f6b35835d772..f3844d9e6f0f41364c24d5fe37bd873f3c816f5d 100644 --- a/src/main/java/com/kwan/springbootkwan/filter/TimeFilter.java +++ b/src/main/java/com/kwan/springbootkwan/filter/TimeFilter.java @@ -18,7 +18,6 @@ public class TimeFilter implements Filter { @Override public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException { -// log.info("先执行:接口执行时间"); chain.doFilter(request, response); } }