SpringBoot使用Lua脚本操作Redis

本文涉及的产品
云数据库 Redis 版,社区版 2GB
推荐场景:
搭建游戏排行榜
简介: SpringBoot使用Lua脚本操作Redis

本文介绍SpringBoot如果通过Lua脚本去执行Redis,介绍简单用法例子,如对Lua脚本还不了解的可以先参考我这边文章Lua脚本快速入门更深层次的用法请参考Redis官网

1. 添加依赖

<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-data-redis</artifactId>
</dependency>
<dependency>
     <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-web</artifactId>
</dependency>

2. 编写Lua脚本

---
--- Created by Gjing.
--- DateTime: 2019/6/21 10:49
---
--- 获取key
local key = KEYS[1]
--- 获取value
local val = KEYS[2]
--- 获取一个参数
local expire = ARGV[1]
--- 如果redis找不到这个key就去插入
if redis.call("get", key) == false then
    --- 如果插入成功,就去设置过期值
    if redis.call("set", key, val) then
        --- 由于lua脚本接收到参数都会转为String,所以要转成数字类型才能比较
        if tonumber(expire) > 0 then
            --- 设置过期时间
            redis.call("expire", key, expire)
        end
        return true
    end
    return false
else
    return false
end

3. 编写配置

/**
 * @author Gjing
 **/
@Configuration
public class LuaConfiguration {
    @Bean
    public DefaultRedisScript<Boolean> redisScript() {
        DefaultRedisScript<Boolean> redisScript = new DefaultRedisScript<>();
        redisScript.setScriptSource(new ResourceScriptSource(new ClassPathResource("script/Test.lua")));
        redisScript.setResultType(Boolean.class);
        return redisScript;
    }
}

4. 调用测试

/**
 * @author Gjing
 **/
@RestController
public class LockController {
    @Resource
    private DefaultRedisScript<Boolean> redisScript;
    @Resource
    private StringRedisTemplate stringRedisTemplate;

    @GetMapping("/lua")
    public ResponseEntity lua() {
        List<String> keys = Arrays.asList("testLua", "hello lua");
        Boolean execute = stringRedisTemplate.execute(redisScript, keys, "100");
        assert execute != null;
        return ResponseEntity.ok(execute);
    }
}

5. 返回结果

  • 执行成功控制台输出
    1561686776_1_
  • 执行失败控制台输出
    1561686789_1_
  • Redis中内容
    1561686820_1_

6. Redis使用Lua的好处

1.减少网络开销:本来5次网络请求的操作,可以用一个请求完成,原先5次请求的逻辑放在redis服务器上完成。使用脚本,减少了网络往返时延。

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

3.复用:客户端发送的脚本会永久存储在Redis中,意味着其他客户端可以复用这一脚本而不需要使用代码完成同样的逻辑。

7. Redis使用Lua的注意点

1.Lua脚本的bug特别可怕,由于Redis的单线程特点,一旦Lua脚本出现不会返回(不是返回值)得问题,那么这个脚本就会阻塞整个redis实例。

2.Lua脚本应该尽量短小实现关键步骤即可。(原因同上)

3.Lua脚本中不应该出现常量Key,这样会导致每次执行时都会在脚本字典中新建一个条目,应该使用全局变量数组KEYS和ARGV, KEYS和ARGV的索引都从1开始

4.传递给lua脚本的的键和参数:传递给lua脚本的键列表应该包括可能会读取或者写入的所有键。传入全部的键使得在使用各种分片或者集群技术时,其他软件可以在应用层检查所有的数据是不是都在同一个分片里面。另外集群版redis也会对将要访问的key进行检查,如果不在同一个服务器里面,那么redis将会返回一个错误。(决定使用集群版之前应该考虑业务拆分),参数列表无所谓。。

5.lua脚本跟单个redis命令和事务段一样都是原子的已经进行了数据写入的lua脚本将无法中断,只能使用SHUTDOWN NOSAVE杀死Redis服务器,所以lua脚本一定要测试好。


以上为个人理解,如有误欢迎各位指正

相关实践学习
基于Redis实现在线游戏积分排行榜
本场景将介绍如何基于Redis数据库实现在线游戏中的游戏玩家积分排行榜功能。
云数据库 Redis 版使用教程
云数据库Redis版是兼容Redis协议标准的、提供持久化的内存数据库服务,基于高可靠双机热备架构及可无缝扩展的集群架构,满足高读写性能场景及容量需弹性变配的业务需求。 产品详情:https://www.aliyun.com/product/kvstore &nbsp; &nbsp; ------------------------------------------------------------------------- 阿里云数据库体验:数据库上云实战 开发者云会免费提供一台带自建MySQL的源数据库&nbsp;ECS 实例和一台目标数据库&nbsp;RDS实例。跟着指引,您可以一步步实现将ECS自建数据库迁移到目标数据库RDS。 点击下方链接,领取免费ECS&amp;RDS资源,30分钟完成数据库上云实战!https://developer.aliyun.com/adc/scenario/51eefbd1894e42f6bb9acacadd3f9121?spm=a2c6h.13788135.J_3257954370.9.4ba85f24utseFl
目录
相关文章
|
2天前
|
弹性计算 NoSQL Shell
redis没设置密码,莫名被设置了4个sh脚本
阿里云ECS实例上未设密码的Redis服务被发现含有未知来源的SH脚本,这些脚本定时从外部URL下载并执行代码。这可能是服务器遭受恶意攻击的迹象。建议立即检查系统日志,确认是否被黑,并移除这些脚本。同时,为Redis设置密码,加强安全防护。若不确定,可寻求专业安全团队帮助。
24 0
|
2天前
|
JSON NoSQL Java
深入浅出Redis(十三):SpringBoot整合Redis客户端
深入浅出Redis(十三):SpringBoot整合Redis客户端
|
2天前
|
存储 缓存 NoSQL
深入浅出Redis(十):Redis的Lua脚本
深入浅出Redis(十):Redis的Lua脚本
|
2天前
|
缓存 NoSQL Java
springboot业务开发--springboot集成redis解决缓存雪崩穿透问题
该文介绍了缓存使用中可能出现的三个问题及解决方案:缓存穿透、缓存击穿和缓存雪崩。为防止缓存穿透,可校验请求数据并缓存空值;缓存击穿可采用限流、热点数据预加载或加锁策略;缓存雪崩则需避免同一时间大量缓存失效,可设置随机过期时间。文章还提及了Spring Boot中Redis缓存的配置,包括缓存null值、使用前缀和自定义过期时间,并提供了改造代码以实现缓存到期时间的个性化设置。
|
2天前
|
SQL Java 数据库连接
Springboot框架整合Spring JDBC操作数据
JDBC是Java数据库连接API,用于执行SQL并访问多种关系数据库。它包括一系列Java类和接口,用于建立数据库连接、创建数据库操作对象、定义SQL语句、执行操作并处理结果集。直接使用JDBC涉及七个步骤,包括加载驱动、建立连接、创建对象、定义SQL、执行操作、处理结果和关闭资源。Spring Boot的`spring-boot-starter-jdbc`简化了这些步骤,提供了一个在Spring生态中更便捷使用JDBC的封装。集成Spring JDBC需要添加相关依赖,配置数据库连接信息,并通过JdbcTemplate进行数据库操作,如插入、更新、删除和查询。
|
2天前
|
SQL Java 数据库连接
Springboot框架整合Spring Data JPA操作数据
Spring Data JPA是Spring基于ORM和JPA规范封装的框架,简化了数据库操作,提供增删改查等接口,并可通过方法名自动生成查询。集成到Spring Boot需添加相关依赖并配置数据库连接和JPA设置。基础用法包括定义实体类和Repository接口,通过Repository接口可直接进行数据操作。此外,JPA支持关键字查询,如通过`findByAuthor`自动转换为SQL的`WHERE author=?`查询。
|
2天前
|
XML Java 数据库连接
Springboot整合mybatisPlus操作数据库
MyBatis-Plus是MyBatis的增强工具,简化开发、提高效率。它提供官网文档,便于集成到SpringBoot项目中。集成步骤包括添加mybatis-plus-boot-starter和数据库驱动依赖,配置数据源,扫描Mapper类包。Mapper接口继承BaseMapper即可使用基本的CRUD操作。示例代码展示了Service层的增删改查实现。MyBatisPlus还支持逻辑删除、自动填充等功能,同时可与Mybatis XML配合使用,通过调整配置指定XML映射文件位置。
|
2天前
|
存储 NoSQL Java
Spring Boot与Redis:整合与实战
【4月更文挑战第29天】Redis,作为一个高性能的键值存储数据库,广泛应用于缓存、消息队列、会话存储等多种场景中。在Spring Boot应用中整合Redis可以显著提高数据处理的效率和应用的响应速度。
29 0
|
2天前
|
安全 Java API
SpringBoot 实现 elasticsearch 索引操作(RestHighLevelClient 的应用)
SpringBoot 实现 elasticsearch 索引操作(RestHighLevelClient 的应用)
20 1
|
2天前
|
自然语言处理 Java 索引
SpringBoot 实现 elasticsearch 查询操作(RestHighLevelClient 的案例实战)
SpringBoot 实现 elasticsearch 查询操作(RestHighLevelClient 的案例实战)
25 1
http://www.vxiaotou.com