Java使用注解實(shí)現(xiàn)防止重復(fù)提交實(shí)例
重復(fù)提交的場(chǎng)景:
- 用于用戶誤操作,多次點(diǎn)擊表單提交按鈕
- 由于網(wǎng)速等原因造成頁(yè)面卡頓,用戶重復(fù)刷新提交頁(yè)面
- 惡用戶如利用postman等工具重復(fù)惡意提交表單
為了防止以上情況的出現(xiàn)需要自定義一個(gè)注解來(lái)完成防止重復(fù)提交操作
實(shí)現(xiàn)
1.創(chuàng)建一個(gè)注解
/** * 自定義注解防止表單重復(fù)提交 */ @Documented @Target({ElementType.TYPE,ElementType.METHOD}) @Retention(RetentionPolicy.RUNTIME) public @interface NoRepeatSubmit { int lockTime() default 5; }
注解參數(shù)不懂的小伙伴可以移步這篇文章:java自定義注解_crazyK.的博客-CSDN博客
2.創(chuàng)建Http請(qǐng)求工具類,用于在切面時(shí)獲取token使用
public class HttpContextUtils { public static HttpServletRequest httpServletRequest(){ return ((ServletRequestAttributes) Objects.requireNonNull(RequestContextHolder.getRequestAttributes())).getRequest(); } }
3.項(xiàng)目中加入SpringAop依賴
<dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-aop</artifactId> </dependency>
4.創(chuàng)建切面
將切點(diǎn)注冊(cè)為自定義的注解,唯一表示采用接口url+token的形式,戶每發(fā)起第一次添加請(qǐng)求,會(huì)經(jīng)過(guò)界面,在切面獲取信息后組裝起來(lái)存入Redis,當(dāng)用戶后續(xù)發(fā)起請(qǐng)求時(shí),首先判斷Redis中是否緩存了這個(gè)key,如果緩存了,則證明已經(jīng)提交,于是反饋給前端,如果不存在,證明沒(méi)有提交,則存入Redis。
@Component @Aspect public class NoRepeatSubmitAspect { @Autowired private RedisTemplate<String,Object> redisTemplate; @Pointcut("@annotation(repeatSubmit)") public void pointcutNoRepeat(NoRepeatSubmit repeatSubmit){}; @Around("pointcutNoRepeat(noRepeatSubmit)") public Object doNoRepeat(ProceedingJoinPoint point, NoRepeatSubmit noRepeatSubmit) throws Throwable { int i=noRepeatSubmit.lockTime(); HttpServletRequest httpServletRequest = HttpContextUtils.httpServletRequest(); String token = httpServletRequest.getHeader("token"); String url = httpServletRequest.getRequestURL().toString(); String sign = url+"/"+token; Boolean key=redisTemplate.hasKey(sign); if (key){ throw new Exception("請(qǐng)勿重復(fù)提交"); } redisTemplate.opsForValue().set(sign,sign,i, TimeUnit.SECONDS); return point.proceed(); } }
測(cè)試
將我們自定義的注解加到對(duì)應(yīng)方法上
先向redis中插入一條key為crazyk,value為csdn的數(shù)據(jù)
提交成功,然后在向redis中存入相同的數(shù)據(jù)后端會(huì)拋出我們?cè)谇忻孀远x的異常
到此這篇關(guān)于Java使用注解實(shí)現(xiàn)防止重復(fù)提交實(shí)例的文章就介紹到這了,更多相關(guān)Java注解防止重復(fù)提交內(nèi)容請(qǐng)搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!
相關(guān)文章
JavaWeb購(gòu)物車項(xiàng)目開(kāi)發(fā)實(shí)戰(zhàn)指南
之前沒(méi)有接觸過(guò)購(gòu)物車的東東,也不知道購(gòu)物車應(yīng)該怎么做,所以在查詢了很多資料,總結(jié)一下購(gòu)物車的功能實(shí)現(xiàn),下面這篇文章主要給大家介紹了關(guān)于JavaWeb購(gòu)物車項(xiàng)目開(kāi)發(fā)的相關(guān)資料,需要的朋友可以參考下2022-06-06spring中WebClient如何設(shè)置連接超時(shí)時(shí)間以及讀取超時(shí)時(shí)間
這篇文章主要給大家介紹了關(guān)于spring中WebClient如何設(shè)置連接超時(shí)時(shí)間以及讀取超時(shí)時(shí)間的相關(guān)資料,WebClient是Spring框架5.0引入的基于響應(yīng)式編程模型的HTTP客戶端,它提供一種簡(jiǎn)便的方式來(lái)處理HTTP請(qǐng)求和響應(yīng),需要的朋友可以參考下2024-08-08springboot中websocket簡(jiǎn)單實(shí)現(xiàn)
本文主要介紹了springboot中websocket簡(jiǎn)單實(shí)現(xiàn),文中通過(guò)示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來(lái)一起學(xué)習(xí)學(xué)習(xí)吧2023-01-01Maven打包jar包沒(méi)有主屬性問(wèn)題解決方案
這篇文章主要介紹了Maven打包jar包沒(méi)有主屬性問(wèn)題解決方案,文中通過(guò)示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友可以參考下2020-07-07Java使用JavaMail API發(fā)送和接收郵件的代碼示例
JavaMail是Oracle甲骨文開(kāi)發(fā)的Java郵件類API,支持多種郵件協(xié)議,這里我們就來(lái)看一下Java使用JavaMail API發(fā)送和接收郵件的代碼示例2016-06-06