欧美bbbwbbbw肥妇,免费乱码人妻系列日韩,一级黄片

Redis接口訪問(wèn)優(yōu)化的方法步驟

 更新時(shí)間:2024年10月16日 11:11:11   作者:何中應(yīng)  
本文基于之前的Redis接口訪問(wèn)進(jìn)行優(yōu)化,引入了接口防抖功能,通過(guò)時(shí)間段參數(shù)限制接口調(diào)用頻率,文中通過(guò)示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來(lái)一起學(xué)習(xí)學(xué)習(xí)吧

說(shuō)明:之前寫過(guò)一篇使用Redis接口訪問(wèn)的博客,如下。最近有相關(guān)需求,把代碼拿出來(lái)后,做了一些優(yōu)化,挺有意思的,本文介紹在原基礎(chǔ)上

使用Redis實(shí)現(xiàn)接口防抖

優(yōu)化

總的來(lái)說(shuō),這次使用Redis實(shí)現(xiàn)接口防抖,增加了一個(gè)時(shí)間段參數(shù),可以限制接口在某個(gè)時(shí)間段內(nèi),訪問(wèn)不能超過(guò)多少次。如下:

(自定義注解,打在接口上)

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 {

    /**
     * 限制訪問(wèn)的key
     * @return
     */
    String key();

    /**
     * 限制訪問(wèn)次數(shù)
     * @return
     */
    int times();

    /**
     * 時(shí)間段
     * @return
     */
    int duration();
}

(切面,實(shí)現(xiàn)限制訪問(wèn))

import com.hezy.annotation.LimitAccess;
import lombok.extern.log4j.Log4j2;
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.beans.factory.annotation.Value;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.stereotype.Component;
import java.util.concurrent.TimeUnit;

/**
 * AOP類(通知類)
 */
@Component
@Aspect
@Log4j2
public class LimitAspect {

    @Value("${access.enable:false}")
    private boolean enable;

    @Autowired
    private RedisTemplate redisTemplate;

    @Pointcut("@annotation(com.hezy.annotation.LimitAccess)")
    public void pt(){};

    @Around("pt()")
    public Object aopAround(ProceedingJoinPoint pjp) throws Throwable {
        // 設(shè)置一個(gè)開關(guān),控制是否執(zhí)行
        if (!enable) {
            return pjp.proceed();
        }
        // 獲取切入點(diǎn)上面的自定義注解
        Signature signature = pjp.getSignature();
        MethodSignature methodSignature = (MethodSignature) signature;

        // 獲取方法上面的注解
        LimitAccess limitAccess = methodSignature.getMethod().getAnnotation(LimitAccess.class);
        // 獲取注解上面的屬性值
        int limit = limitAccess.times();
        String key = limitAccess.key();
        int duration = limitAccess.duration();

        // 遞增鍵的值,如果鍵不存在則初始化為1
        Long currentCount = redisTemplate.opsForValue().increment(key, 1);

        // 如果鍵是新創(chuàng)建的,設(shè)置過(guò)期時(shí)間
        if (currentCount != null && currentCount == 1) {
            redisTemplate.expire(key, duration, TimeUnit.SECONDS);
        }

        // 檢查是否超過(guò)限制
        if (currentCount != null && currentCount > limit) {
            log.info("訪問(wèn)過(guò)于頻繁: " + pjp.toLongString());
            throw new RuntimeException("訪問(wèn)過(guò)于頻繁");
        }
        return pjp.proceed();
    }
}

(使用,在對(duì)應(yīng)的接口上,打上注解,填上數(shù)值,如下表示,1秒內(nèi)不能訪問(wèn)超過(guò)3次)

    @LimitAccess(key = "test", times = 3, duration = 1)
    @GetMapping
    public String test() {
        return demoService.test();
    }

另外,在代碼中加了一個(gè)開關(guān),可在配置文件中設(shè)置此配置,表示開啟或者關(guān)閉,默認(rèn)是關(guān)閉的

access:
  enable: true

啟動(dòng)項(xiàng)目,測(cè)試一下

在這里插入圖片描述

思考

以上代碼,有兩點(diǎn)需要思考:

  • 注解能不能加在Service層的方法上,加了有沒有用?另外加了會(huì)不會(huì)讓聲明式事務(wù)失效?

  • 這個(gè)限制,沒有到用戶的維度,也就是說(shuō)所有的用戶,只要在一個(gè)時(shí)間段內(nèi)訪問(wèn)超過(guò)次數(shù)就限制,這顯然是不行的。有什么辦法嗎?

第一點(diǎn),我測(cè)試過(guò),注解可以加在Service層方法上,是可以的,不會(huì)讓事務(wù)失效,如下:

    @LimitAccess(key = "deleteUserById", times = 3, duration = 1)
    @Transactional
    @Override
    public void deleteUserById(Integer id) {
        // 刪除用戶
        userMapper.deleteUserById(id);
        
        int i = 1 / 0;

        // 刪除用戶對(duì)應(yīng)的角色
        userMapper.deleteUserRoleMapper(id);
    }

接口限制,事務(wù),都生效了。

第二點(diǎn),這確實(shí)是個(gè)問(wèn)題,要做到針對(duì)用戶層面的接口限制是必須的,不然有一個(gè)用戶惡意刷新,其他用戶都用不了了,這怎么可以。要解決這個(gè)問(wèn)題,首先要拿到當(dāng)前操作用的標(biāo)識(shí),用戶名、用戶ID,然后再存入key的時(shí)候,拼接上這個(gè)標(biāo)識(shí)作為key。

	String key = limitAccess.key() + 用戶標(biāo)識(shí)(用戶名、用戶id);

獲取當(dāng)前用戶信息,參考下面這篇文章:

獲取當(dāng)前用戶信息的幾種方式

如果你不是自己從0開發(fā)項(xiàng)目,一般成熟的項(xiàng)目都會(huì)有獲取當(dāng)前操作用戶信息的方式的。實(shí)在不行,你讓前端把用戶id作為參數(shù)傳給你,你在切面里獲取這個(gè)用戶id都可以。

總結(jié)

本文是對(duì)之前用Redis接口訪問(wèn)的優(yōu)化,以及對(duì)兩個(gè)問(wèn)題的考慮,希望能對(duì)大家有啟發(fā)。

獲取源碼:https://github.com/HeZhongYing/limit_access_demo

到此這篇關(guān)于Redis接口訪問(wèn)優(yōu)化的方法步驟的文章就介紹到這了,更多相關(guān)Redis接口訪問(wèn)優(yōu)化內(nèi)容請(qǐng)搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!

相關(guān)文章

  • Redis超詳細(xì)分析分布式鎖

    Redis超詳細(xì)分析分布式鎖

    在單體應(yīng)用中,如果我們對(duì)共享數(shù)據(jù)不進(jìn)行加鎖操作,會(huì)出現(xiàn)數(shù)據(jù)一致性問(wèn)題,我們的解決辦法通常是加鎖。下面我們一起聊聊使用redis來(lái)實(shí)現(xiàn)分布式鎖
    2022-07-07
  • Redis集群Lettuce主從切換問(wèn)題解決方案

    Redis集群Lettuce主從切換問(wèn)題解決方案

    這篇文章主要為大家介紹了Redis集群Lettuce主從切換問(wèn)題解決方案,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪
    2023-07-07
  • Redis+自定義注解+AOP實(shí)現(xiàn)聲明式注解緩存查詢的示例

    Redis+自定義注解+AOP實(shí)現(xiàn)聲明式注解緩存查詢的示例

    實(shí)際項(xiàng)目中,會(huì)遇到很多查詢數(shù)據(jù)的場(chǎng)景,這些數(shù)據(jù)更新頻率也不是很高,一般我們?cè)跇I(yè)務(wù)處理時(shí),會(huì)對(duì)這些數(shù)據(jù)進(jìn)行緩存,本文主要介紹了Redis+自定義注解+AOP實(shí)現(xiàn)聲明式注解緩存查詢的示例,文中通過(guò)示例代碼介紹的非常詳細(xì),需要的朋友們下面隨著小編來(lái)一起學(xué)習(xí)學(xué)習(xí)吧
    2025-04-04
  • Redis數(shù)據(jù)庫(kù)安全詳解

    Redis數(shù)據(jù)庫(kù)安全詳解

    這篇文章主要為大家介紹了Redis數(shù)據(jù)庫(kù)安全詳解,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪
    2022-11-11
  • RedisTemplate 實(shí)現(xiàn)基于Value 操作的簡(jiǎn)易鎖機(jī)制(示例代碼)

    RedisTemplate 實(shí)現(xiàn)基于Value 操作的簡(jiǎn)易鎖機(jī)制(示例代碼)

    本文將介紹如何使用 RedisTemplate 的 opsForValue().setIfAbsent() 方法來(lái)實(shí)現(xiàn)一種簡(jiǎn)單的鎖機(jī)制,并提供一個(gè)示例代碼,展示如何在 Java 應(yīng)用中利用這一機(jī)制來(lái)保護(hù)共享資源的訪問(wèn),感興趣的朋友跟隨小編一起看看吧
    2024-05-05
  • Redis TTL命令實(shí)現(xiàn)數(shù)據(jù)生存時(shí)間

    Redis TTL命令實(shí)現(xiàn)數(shù)據(jù)生存時(shí)間

    生存時(shí)間可以通過(guò)Redis中的不同命令來(lái)設(shè)置、查看和管理,TTL命令是其中之一,本文主要介紹了Redis TTL命令實(shí)現(xiàn)數(shù)據(jù)生存時(shí)間,具有一定的參考價(jià)值,感興趣的可以了解一下
    2024-06-06
  • 利用Redis實(shí)現(xiàn)防止接口重復(fù)提交功能

    利用Redis實(shí)現(xiàn)防止接口重復(fù)提交功能

    大家好,本篇文章主要講的是利用Redis實(shí)現(xiàn)防止接口重復(fù)提交功能,感興趣的同學(xué)趕快來(lái)看一看吧,對(duì)你有幫助的話記得收藏一下,方便下次瀏覽
    2021-12-12
  • 在不重啟的情況下熱更新Redis集群密碼的流程步驟

    在不重啟的情況下熱更新Redis集群密碼的流程步驟

    當(dāng)我們需要在運(yùn)行中的 Redis 集群中修改密碼時(shí),可以通過(guò) Redis 的配置命令 CONFIG SET 實(shí)現(xiàn)即時(shí)修改,并使用 CONFIG REWRITE 將更改持久化到配置文件中,在本文中,我們將詳細(xì)介紹如何安全地更新你的 Redis 集群密碼,需要的朋友可以參考下
    2024-05-05
  • 利用yum安裝Redis的方法詳解

    利用yum安裝Redis的方法詳解

    Redis是一個(gè)開源的使用ANSI C語(yǔ)言編寫、支持網(wǎng)絡(luò)、可基于內(nèi)存亦可持久化的日志型、Key-Value數(shù)據(jù)庫(kù),并提供多種語(yǔ)言的API。從2010年3月15日起,Redis的開發(fā)工作由VMware主持。這篇文章主要介紹的是利用yum安裝Redis的方法,有需要的朋友們可以參考借鑒,下面來(lái)一起看看吧
    2016-11-11
  • Redis在項(xiàng)目中常見的12種使用場(chǎng)景示例和說(shuō)明

    Redis在項(xiàng)目中常見的12種使用場(chǎng)景示例和說(shuō)明

    Redis是一個(gè)開源的高性能鍵值對(duì)數(shù)據(jù)庫(kù),它以其內(nèi)存中數(shù)據(jù)存儲(chǔ)、鍵過(guò)期策略、持久化、事務(wù)、豐富的數(shù)據(jù)類型支持以及原子操作等特性,在許多項(xiàng)目中扮演著關(guān)鍵角色,以下是整理的12個(gè)Redis在項(xiàng)目中常見的使用場(chǎng)景舉例說(shuō)明和解釋
    2024-06-06

最新評(píng)論