redis使用场景

使用场景
最近联系人列表 维护长度为 100 的最近联系人列表

  1. 如果指定的联系人已在列表中,则从列表中移除 (lrem) lrem list 1 mobile
  2. 将指定的联系人添加到列表最前面 (lpush) lpush list mobile
  3. 如果添加完成后,列表长度超过 100 ,则对列表进行修剪,仅保留列表前面的 100 个联系人 (ltrim) ltrim list 0 99
限制短信频率,比如同一手机号60分钟之内只能发送3条 限制短信频率,同一手机号60分钟之内只能发送3条
精华版采用队列实现
local lKey = KEYS[1] -- 列表键,比如直接使用手机号 local maxCount = tonumber(ARGV[1]) --一定时间内短信最多发送条数 -- 当前时间戳,毫秒 local currentTime = tonumber(ARGV[2]) -- 一段时间:一分钟、一小时、一天,毫秒 local period = tonumber(ARGV[3]) -- 查看当前队列大小。 local lSize = redis.call("llen", lKey)-- 说明一段时间内队列未满,直接压入队列,返回 1,表示可以发送短信 local flag = false if lSize < maxCount then -- 记录短信的发送时间(毫秒) redis.call("lpush", lKey, currentTime) flag = true else -- 取队列当中最早一条短信的发送时间,拿当前时间减去此时间,如果超过“一段”时间,则可以移掉,并压入当前短信时间。 local oldestTime = tonumber(redis.call("lindex", lKey, -1)) local result = currentTime - oldestTime -- 当前时间与第一条短信的发送时间间隔大于“周期”,才可继续发送 if result > period then redis.call("rpop", lKey) -- 弹出队列中最早一条短信发送时间 redis.call("lpush", lKey, currentTime) -- 压入最新一条短信的发送时间 flag = true end end -- 刷新键的过期时间为“一段”时间。 redis.call("expire", lKey, period/1000) -- flag: true 表示可以发送短信,false 则不能发送短信 if flag then return 1 end return 0

简陋版
--[[ 实现访问频率的脚本. 参数:KEY[1] 用来标识同一个用户的id ARGV[1] 过期时间 ARGV[2] 过期时间内可以访问的次数 返回值: 如果没有超过指定的频率, 则返回1; 否则返回0 ]] local times = redis.call('incr', KEYS[1]) if times == 1 then-- 说明刚创建, 设置生存时间 redis.call('expire', KEYS[1], ARGV[1]) end if times > tonumber(ARGV[2]) then return 0 endreturn 1

队列实现 一、非阻塞消费队列 生产者rpush或lpush
消费者lpop或rpop
二、阻塞消费队列 生产者rpush或lpush
消费者blpop或brpop
一、二两种实现有丢掉消息的风险,当消费者网络问题或消费的过程中出现异常,消息会丢掉。
三、可靠消费队列 生产者rpush或lpush
消费者端增加一个辅助列表(处理中列表processing list),消费者消费消息的时候采用命令love messageList processingList right left,当消费处理完了,从处理中列表移走处理好的消息lrem processingList 1 element。由于lmove是原子操作,所以不会丢失消失。最好另开一个线程用于监视processingList列表,如果滞留processingList列表时间过长,视场景处理。
三、优先级队列 【redis使用场景】blpop或brpop可以给定多个列表作为弹出操作的执行对象。把优先级高的队列放在第一个参数,优先级中等的队列放在第二个参数,优先级低等的队列放在第三个队列。这样就可以通过多个队列实现优先级特性。

    推荐阅读