網站首頁 編程語言 正文
說明:實際開發中,我們在前端頁面上點擊了一個按鈕,訪問了一個接口,這時因為網絡波動或者其他原因,頁面上沒有反應,用戶可能會在短時間內再次點擊一次或者用戶以為沒有點到,很快的又點了一次。導致短時間內發送了兩個請求到后臺,可能會導致數據重復添加。
為了避免短時間內對一個接口訪問,我們可以通過AOP+自定義注解+Redis的方式,在接口上加一個自定義注解,然后通過AOP的前置通知,在Redis中存入一個有效期的值,當訪問接口時這個值還未過期,則拋出異常,以此來避免短時間內對接口的方法。
實現
第一步:創建一個自定義注解,設置兩個屬性,一個是key,一個是這個key在Redis中的有效時間;
import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
/**
* 自定義注解
*/
@Target(ElementType.METHOD)
@Retention(RetentionPolicy.RUNTIME)
public @interface LimitAccess {
/**
* 限制訪問的key
* @return
*/
String key();
/**
* 限制訪問時間
* @return
*/
int times();
}
第二步:創建對應的Aspect;
import com.hezy.annotation.LimitAccess;
import org.aspectj.lang.ProceedingJoinPoint;
import org.aspectj.lang.Signature;
import org.aspectj.lang.annotation.Around;
import org.aspectj.lang.annotation.Aspect;
import org.aspectj.lang.annotation.Pointcut;
import org.aspectj.lang.reflect.MethodSignature;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.stereotype.Component;
import java.util.concurrent.TimeUnit;
/**
* AOP類(通知類)
*/
@Component
@Aspect
public class LimitAspect {
@Autowired
private RedisTemplate redisTemplate;
@Pointcut("@annotation(com.hezy.annotation.LimitAccess)")
public void pt(){};
@Around("pt()")
public Object aopAround(ProceedingJoinPoint pjp) throws Throwable {
// 獲取切入點上面的自定義注解
Signature signature = pjp.getSignature();
MethodSignature methodSignature = (MethodSignature) signature;
// 獲取方法上面的注解
LimitAccess limitAccess = methodSignature.getMethod().getAnnotation(LimitAccess.class);
// 獲取注解上面的屬性
int limit = limitAccess.times();
String key = limitAccess.key();
// 根據key去找Redis中的值
Object o = redisTemplate.opsForValue().get(key);
// 如果不存在,說明是首次訪問,存入Redis,過期時間為limitAccess中的time
if (o == null) {
redisTemplate.opsForValue().set(key, "", limit, TimeUnit.SECONDS);
// 執行切入點的方法
return pjp.proceed();
} else {
// 如果存在,說明不是首次訪問,拋出異常
throw new RuntimeException("訪問過于頻繁");
}
}
}
第三步:在需要限制的接口上,加上這個注解,并設置key和限制訪問時間,如下這個這個接口,設置key為set,實際開發中可以設置一個隨機值,或者按照規則自定義設置,times為限制訪問時間;
@GetMapping("/limit")
@LimitAccess(key = "limit", times = 10)
public String limit() {
return "success";
}
演示
啟動項目,訪問該接口;
(首次訪問,沒得問題,同時在Redis中存入值)
(短時間內,連續訪問,因為Redis中值未過期)
(10秒之后再訪問,又可以了,Redis中的值過期了)
以上就是使用Redis實現接口防抖,避免短時間內連續訪問接口。實際開發中,可以將異常設置為自定義異常。
原文鏈接:https://blog.csdn.net/qq_42108331/article/details/134691925
- 上一篇:沒有了
- 下一篇:沒有了
相關推薦
- 2021-11-08 C++繼承模式詳解_C 語言
- 2022-11-08 C/C++實現遍歷文件夾最全方法總結_C 語言
- 2022-08-25 利用Android實現光影流動特效的方法詳解_Android
- 2023-06-19 C++開放封閉原則示例解析_C 語言
- 2022-05-05 Python學習之流程控制與條件判斷總結_python
- 2022-10-26 Python?Pyinstaller庫安裝步驟以及使用方法_python
- 2022-09-05 Linux系統下創建守護進程
- 2022-11-21 基于C++實現一個日期計算器_C 語言
- 欄目分類
-
- 最近更新
-
- window11 系統安裝 yarn
- 超詳細win安裝深度學習環境2025年最新版(
- Linux 中運行的top命令 怎么退出?
- MySQL 中decimal 的用法? 存儲小
- get 、set 、toString 方法的使
- @Resource和 @Autowired注解
- Java基礎操作-- 運算符,流程控制 Flo
- 1. Int 和Integer 的區別,Jav
- spring @retryable不生效的一種
- Spring Security之認證信息的處理
- Spring Security之認證過濾器
- Spring Security概述快速入門
- Spring Security之配置體系
- 【SpringBoot】SpringCache
- Spring Security之基于方法配置權
- redisson分布式鎖中waittime的設
- maven:解決release錯誤:Artif
- restTemplate使用總結
- Spring Security之安全異常處理
- MybatisPlus優雅實現加密?
- Spring ioc容器與Bean的生命周期。
- 【探索SpringCloud】服務發現-Nac
- Spring Security之基于HttpR
- Redis 底層數據結構-簡單動態字符串(SD
- arthas操作spring被代理目標對象命令
- Spring中的單例模式應用詳解
- 聊聊消息隊列,發送消息的4種方式
- bootspring第三方資源配置管理
- GIT同步修改后的遠程分支