当前位置: 代码网 > it编程>编程语言>Java > springboot lua检查redis库存的实现示例

springboot lua检查redis库存的实现示例

2024年09月12日 Java 我要评论
需求最近需求需要实现检查多个马戏场次下的座位等席对应库存渠道的库存余量,考虑到性能,决定采用lua脚本实现库存检查。数据结构库存层级结构redis库存hash类型结构实现lua脚本--- 字符串分割为

需求

最近需求需要实现检查多个马戏场次下的座位等席对应库存渠道的库存余量,考虑到性能,决定采用lua脚本实现库存检查。

数据结构

库存层级结构

在这里插入图片描述

redis库存hash类型结构

在这里插入图片描述

实现

lua脚本

--- 字符串分割为数组
local function split(str, char)
    local arr = {};
    local pattern = string.format('([^%s]+)', char);
    for item in string.gmatch(str, pattern) do
        table.insert(arr, item);
    end
    return arr;
end
--- 数组转成map
local function tomap(tb)
    if (tb == nil) then
        return {};
    end
    local map = {};
    for i = 1, #tb do
        if (i % 2 == 1) then
            map[tb[i]] = tb[i+1];
        end
    end
    return map;
end
--- 初始化数据,入参01:1,02:2.01:3
local argarr = {};
for rowitem in string.gmatch(argv[1], '([^.]+)') do
    local row = {};
    for keyval in string.gmatch(rowitem, '([^,]+)') do
    -- 解析出每个key与value
        local temparr = split(keyval, ':');
        row[temparr[1]] = temparr[2];
    end
    table.insert(argarr, row);
end
--- 检查库存
for i = 1, #keys do
    --local rdata = redis.call("hmget", keys[i], '01 02');
    local rdsmap = tomap(redis.call("hgetall", keys[i]));
    for tier, quantity in pairs(argarr[i]) do
        --redis.log(redis.log_notice, string.format('key is:%s,tier is:%s,quantity is:%s', keys[i], tier, quantity));
        if (rdsmap[tier] == nil or tonumber(quantity) > tonumber(rdsmap[tier])) then
            return string.format("库存key:%s,tier:%s不足", keys[i], tier);
        end
    end
end
return '';

遍历键值对时需要使用pairs而不是ipairs,二者区别如下:
for k,v in pairs(argarr)的遍历顺序并非是table类型数据的排列顺序,而是根据table中key的hash值排列的顺序来遍历的。
for k,v in ipairs(argarr)必须要求table中的key为有序的,而且必须是从1开始,ipairs只会从1开始按连续的key顺序遍历到key不连续为止。

  • 入参设计
    由于redistemplate直接传入集合为参数序列化后会有中括号,而lua脚本table类型使用花括号定义,因此采用字符串作为入参,在lua脚本中解析字符串为table类型。例如参数01:1,02:2.01:3代表二维数组,第一行为01:1,02:2,其中01为渠道,1为渠道对应的库存,英文逗号作为渠道分隔符。
  • springboot调用lua脚本
@autowired
private stringredistemplate redisjsontemplate;

@test
public void checkinventory() {
    list<string> keylist = list.of("stock:gz7:433680411156197407", "stock:gz7:433680411156197408");
    // 执行 lua 脚本
    defaultredisscript<string> redisscript = new defaultredisscript<>();
    // 指定 lua 脚本
    redisscript.setscriptsource(new resourcescriptsource(new classpathresource("/lua/theaterstockcheck.lua")));
    // 指定返回类型
    redisscript.setresulttype(string.class);
    object result = redisjsontemplate.execute(redisscript, keylist, "01:1,0101:2.01:3");
    //01:1,02:2.01:3
    system.out.println(result);
}

调用lua脚本需要使用string序列化方式,使用jdk序列化方式会导致序列化后的数据lua脚本无法解析

测试效果

redis库存数据

在这里插入图片描述

调用效果

在这里插入图片描述

到此这篇关于springboot lua检查redis库存的实现示例的文章就介绍到这了,更多相关springboot lua检查redis库存内容请搜索代码网以前的文章或继续浏览下面的相关文章希望大家以后多多支持代码网! 

(0)

相关文章:

版权声明:本文内容由互联网用户贡献,该文观点仅代表作者本人。本站仅提供信息存储服务,不拥有所有权,不承担相关法律责任。 如发现本站有涉嫌抄袭侵权/违法违规的内容, 请发送邮件至 2386932994@qq.com 举报,一经查实将立刻删除。

发表评论

验证码:
Copyright © 2017-2025  代码网 保留所有权利. 粤ICP备2024248653号
站长QQ:2386932994 | 联系邮箱:2386932994@qq.com