Redis 队列实现并发抢红包逻辑?

使用laravel5.5+mysql5.7+redis.3.x
最近处理抢红包逻辑,遇到一些问题。
页面逻辑

  1. 用户发出红包(初始化红包)
  2. 用户分享
  3. 其他用户点击进入(可以理解为红包详情页)
  4. 点击“抢”按钮,发出抢红包请求
  5. 根据请求结果显示用户是否抢到红包

一、方案一

1. 流程图

2. 介绍

这个方案主要是提前计算出每个小红包的金额插入到队列,然后领取时进行出队操作。

3. 疑问

  • 提前插入队列,在红包数量total_size>1000的情况下会比较慢
  • 在进行出队操作时如何与前端页面交互?
    在抢红包时发送请求到服务器端,服务器端应该返回给我是否成功操作,但是由于在Lavael中出队操作是异步(。。。也就是说这个请求并不能返回我到底有没有抢到红包),我该如何判断状态?难道要比如过5s后再执行ajax请求看一下数据库里队列任务是否生成了领取记录?

    二 、方案二

    1. 流程图

    2. 介绍

    这个方案是在“抢”红包的时候生成随机金额,然后插入到队列,之后取前几名

    3. 疑问

  • 这个操作只有在高并发(并发数>total_size)时使用
  • 同方案一,如何处理队列的异步处理问题。

主要问题:如何处理队列的异步处理问题。看了其他一些解决方案,大致都是说用队列处理并发问题,但是在抢红包请求中,队列操作是异步的,也就是说,我这个抢的请求是获取不到正确结果的(只有队列执行完成),难道要比如过5s后再执行ajax请求看一下数据库里队列任务是否生成了领取记录?。。。
队列之前没有用过。。。所以希望大神们给点意见。或者更好的解决方案

附言 1  ·  7年前

基于redis的抢红包方案。
把原始的红包称为大红包,拆分后的红包称为小红包。
1.小红包预先生成,插到数据库里,红包对应的用户ID是null。
2.每个大红包对应两个redis队列,一个是未消费红包队列,另一个是已消费红包队列。开始时,把未抢的小红包全放到未消费红包队列里。
未消费红包队列里是json字符串,如{userId:'789', money:'300'}。
3.在redis中用一个map来过滤已抢到红包的用户。
4.抢红包时,先判断用户是否抢过红包,如果没有,则从未消费红包队列中取出一个小红包,再push到另一个已消费队列中,最后把用户ID放入去重的map中。
5.用一个单线程批量把已消费队列里的红包取出来,再批量update红包的用户ID到数据库里。

这个是方案一的详细过程,但是还是那个问题,队列是异步执行,导致抢红包的请求并没有马上得到结果。而是要等队列执行完毕才可以判断用户是否抢到红包。

附言 2  ·  7年前

抢红包最终实现效果~,有需要源码的私聊我~
领你妹

franktrue
《L03 构架 API 服务器》
你将学到如 RESTFul 设计风格、PostMan 的使用、OAuth 流程,JWT 概念及使用 和 API 开发相关的进阶知识。
《L02 从零构建论坛系统》
以构建论坛项目 LaraBBS 为线索,展开对 Laravel 框架的全面学习。应用程序架构思路贴近 Laravel 框架的设计哲学。
讨论数量: 1

1,队列有执行回调事件
2,队列回调触发事件广播

7年前 评论

讨论应以学习和精进为目的。请勿发布不友善或者负能量的内容,与人为善,比聪明更重要!