springboot中使用redis并且执行调试lua脚本

 更新时间:2022年04月25日 10:22:44   作者:香菜_香菜  
今天有个项目需要使用redis,并且有使用脚本的需求,本文主要介绍了springboot中使用redis并且执行调试lua脚本,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们下面随着小编来一起学习学习吧

今天有个项目需要使用redis,并且有使用脚本的需求。但是因为之前没有写过,所以还有一点点不熟悉,今天记录一下。

原因:

原子操作,redis会将整个脚本作为一个整体执行,中间不会被其他命令插入。

1、创建一个基本的web项目

文件 ->新建 -> 项目,选择spring initializr ,勾选spring web 方便测试,最主要勾选 spring data redis,和下图一样

2、配置redis

因为我是为了测试redis,所以直接使用的本地的redis,你可以替换成application.yaml,或者使用环境变量替换。

#Redis服务器ip
spring.redis.host=127.0.0.1
#Redis服务器连接端口
spring.redis.port=6379

注: 你不配置的话默认值就是上面的

3、测试redis 的lua脚本

先写个能方便测试的接口,因为我为了测试lua 的脚本执行,所以就没讲什么设计,直接验证脚本

这里要做的就是删除过期的key,同时移除hash中的key

package com.pdool.main;
 
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.core.io.ClassPathResource;
import org.springframework.data.redis.core.StringRedisTemplate;
import org.springframework.data.redis.core.script.DefaultRedisScript;
import org.springframework.scripting.support.ResourceScriptSource;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
 
import java.util.*;
import java.util.stream.Collectors;
 
@RestController
public class TestController {
    @Autowired
    private StringRedisTemplate redisTemplate;
 
    @RequestMapping("test")
    public String test() {
        System.out.println("xxxxxxxxxxxxxx");
        try {
            //调用lua脚本并执行
            DefaultRedisScript<Void> redisScript = new DefaultRedisScript<>();
            redisScript.setResultType(Void.class);//返回类型是Long
            //lua文件存放在resources目录下的redis文件夹内
            Set<String> webApiRequestSet = new HashSet<>();
            webApiRequestSet.add("aa");
            webApiRequestSet.add("bb");
 
            Set<String> webWebsocketRequestSet = new HashSet<>();
 
            String shortHashKey = "abc";
            String longHashKey = "def";
            String delShortKeys = webApiRequestSet.stream().map((requestId) -> shortHashKey + ":" + requestId).collect(Collectors.joining(";"));
            String delLongKeys = webWebsocketRequestSet.stream().map((requestId) -> longHashKey + ":" + requestId).collect(Collectors.joining(";"));
            List<String> keys = Arrays.asList(shortHashKey, longHashKey);
 
            redisScript.setScriptSource(new ResourceScriptSource(new ClassPathResource("redis/clear-local-key.lua")));
            redisTemplate.execute(redisScript, keys, delShortKeys, delLongKeys);
        } catch (Exception e) {
            e.printStackTrace();
        }
        return "sssssssss";
    }
}

再来看下lua脚本,这东西花了我不少的时间

local short_hash_key = KEYS[1];
local long_hash_key = KEYS[2];
local del_short_hash_keys = ARGV[1];
local del_long_hash_keys = ARGV[2];
 
local function tt_split(str,reps )
          local resultStrList = {}
          string.gsub(str,'[^'..reps..']+',function ( w )
              table.insert(resultStrList,w)
          end)
          return resultStrList
      end
local del_short_key_list= tt_split(del_short_hash_keys,";")
for i = 1, #del_short_key_list do
    local del_key = del_short_key_list[i];
    redis.call("DEL", del_key)
    redis.call("HDEL", short_hash_key, del_key)
end
 
local del_long_key_list = tt_split(del_long_hash_keys,";")
for i = 1, #del_long_key_list do
    local del_key = del_long_key_list[i];
    redis.call("DEL", del_key)
    redis.call("HDEL", long_hash_key, del_key)
end

4、技术点

1、redis 传参可以有两个全局变量,一个KEYS,一个是ARGV

2、redis执行的lua 不可以有全局变量,因为会污染环境,所以这里的function 是local

3、lua没有线程的字符串拆分函数,上面的函数是我找些unity的同学从项目中扒出来的

4、lua 列表的下标从1 开始的

5、redis中执行的lua 是 事务性的

6、lua 会阻塞线程,如果脚本太耗时会卡主服务器

5、调试方式

调试lua脚本是真的费劲,因为在redis desktop manage中不太好测试,下面说下怎么测试,如果你本机安装了redis。

1、进入服务关闭关闭正在运行的服务器

2、从命令行启动redis

找到redis 在本机的安装路径,我的路径是 C:\Program Files\Redis

打开命令行,输入下面的命令就能启动redis服务器了

redis-server.exe redis.windows.conf

3、在lua脚本中增加打印

redis.log(redis.LOG_WARNING, "last_tokens " .. last_tokens)

4、运行代码

调用lua脚本,就可以看到下面的输出了,如果你不想看了,就直接从服务启动redis就好了

注意:正式应用的时候把log 注释掉。

6、总结

今天主要的时间耗费在lua 函数的定义,一直没有搞懂怎么调用,点有背,碰了好多次都没成功。

到此这篇关于springboot中使用redis并且执行调试lua脚本的文章就介绍到这了,更多相关springboot使用redis执行调试lua内容请搜索脚本之家以前的文章或继续浏览下面的相关文章希望大家以后多多支持脚本之家!

相关文章

  • Java List集合取交集的五种常见方式总结

    Java List集合取交集的五种常见方式总结

    在Java中取两个List集合的交集可以通过多种方式实现,下面这篇文章主要给大家介绍了关于Java List集合取交集的五种常见方式,文中通过代码介绍的非常详细,需要的朋友可以参考下
    2024-07-07
  • 设计模式之原型模式_动力节点Java学院整理

    设计模式之原型模式_动力节点Java学院整理

    这篇文章主要介绍了设计模式之原型模式,小编觉得挺不错的,现在分享给大家,也给大家做个参考。一起跟随小编过来看看吧
    2017-08-08
  • mybatis3使用@Select等注解实现增删改查操作

    mybatis3使用@Select等注解实现增删改查操作

    这篇文章主要介绍了mybatis3使用@Select等注解实现增删改查操作,具有很好的参考价值,希望对大家有所帮助。一起跟随小编过来看看吧
    2020-11-11
  • springBoot基于webSocket实现扫码登录

    springBoot基于webSocket实现扫码登录

    最近做了个新项目,涉及到扫码登录。之前项目使用的是 ajax轮询的方式。感觉太low了。所以这次用webSocket的方式进行实现,感兴趣的可以了解一下
    2021-06-06
  • Java OpenCV图像处理之背景消除

    Java OpenCV图像处理之背景消除

    GMM(高斯混合模型)是基于像素样本统计信息的背景表示方法,利用像素在较长时间内大量样本值的概率密度等统计信息表示别境,然后使用统计差分进行目标像素判断达到预期效果。本文将利用GMM方法实现图像背景消除,需要的可以参考一下
    2022-02-02
  • RandomAccessFile简介_动力节点Java学院整理

    RandomAccessFile简介_动力节点Java学院整理

    RandomAccessFile 是随机访问文件(包括读/写)的类。它支持对文件随机访问的读取和写入,即我们可以从指定的位置读取/写入文件数据。这篇文章主要介绍了RandomAccessFile简介,需要的朋友可以参考下
    2017-05-05
  • java如何获取指定文件夹下的所有文件名

    java如何获取指定文件夹下的所有文件名

    这篇文章主要介绍了java如何获取指定文件夹下的所有文件名问题,具有很好的参考价值,希望对大家有所帮助,如有错误或未考虑完全的地方,望不吝赐教
    2024-01-01
  • java后台如何接收get请求传过来的数组

    java后台如何接收get请求传过来的数组

    这篇文章主要介绍了java后台如何接收get请求传过来的数组问题,具有很好的参考价值,希望对大家有所帮助,如有错误或未考虑完全的地方,望不吝赐教
    2023-11-11
  • Spring Boot简介与快速搭建详细步骤

    Spring Boot简介与快速搭建详细步骤

    SpringBoot其本身没有添加什么新的技术,就是整合了一些现有的框架,并提供了一些默认的配置,就是这些默认的配置,极大的提高了我们的开发效率。这篇文章主要介绍了Spring Boot简介与快速搭建,需要的朋友可以参考下
    2021-05-05
  • java时间戳与日期相互转换工具详解

    java时间戳与日期相互转换工具详解

    这篇文章主要为大家详细介绍了java各种时间戳与日期之间相互转换的工具,具有一定的参考价值,感兴趣的小伙伴们可以参考一下
    2017-12-12

最新评论