在java中使用lua脚本操作redis

前言

众所周知,redis可以执行lua脚本,至于为什么要用lua脚本来操作redis,自行百度咯

开始

Bean类

package cn.daenx.myadmin.common.config.redis;

import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.data.redis.core.script.DefaultRedisScript;


/**
 * Redis LUA脚本
 *
 * @author DaenMax
 */
@Configuration
public class RedisScript {

    /**
     * 限流脚本
     *
     * @return
     */
    @Bean
    public DefaultRedisScript<Long> limitScript() {
        DefaultRedisScript<Long> redisScript = new DefaultRedisScript<>();
        redisScript.setScriptText(limitScriptText());
        redisScript.setResultType(Long.class);
        return redisScript;
    }

    private String limitScriptText() {
        return "local key = KEYS[1]\n" +
                "local count = tonumber(ARGV[1])\n" +
                "local time = tonumber(ARGV[2])\n" +
                "local current = redis.call('get', key);\n" +
                "if current and tonumber(current) > count then\n" +
                "    return tonumber(current);\n" +
                "end\n" +
                "current = redis.call('incr', key)\n" +
                "if tonumber(current) == 1 then\n" +
                "    redis.call('expire', key, time)\n" +
                "end\n" +
                "return tonumber(current);";
    }

    /**
     * 邮箱轮询队列脚本
     *
     * @return
     */
    @Bean
    public DefaultRedisScript<String> nextEmailScript() {
        DefaultRedisScript<String> redisScript = new DefaultRedisScript<>();
        redisScript.setScriptText(nextEmailScriptText());
        redisScript.setResultType(String.class);
        return redisScript;
    }

    private String nextEmailScriptText() {
        return "local key = KEYS[1];\n" +
                "local email= redis.call('rpop',key);\n" +
                "redis.call('lpush',key,email);\n" +
                "return email;";
    }
}

使用

    @Resource
    private RedisTemplate<String, Object> redisTemplate;
    //限流脚本
    @Resource
    private RedisScript<Long> limitScript;
    //邮箱轮询队列脚本
    @Resource
    private RedisScript<String> nextEmailScript;

    /**
     * 测试
     *
     * @return
     */
    @GetMapping("/test")
    public void test() {
        String data1 = redisTemplate.execute(nextEmailScript, CollUtil.newArrayList(SystemConstant.EMAIL_POLL_KEY), "");
        Long data2 = redisTemplate.execute(limitScript, CollUtil.newArrayList("1"), 2, 3);
        
    }
posted @ 2023-05-20 23:23  DaenMax  阅读(762)  评论(0编辑  收藏  举报