当前位置: 首页 > news >正文

Redis项目应用总结(苍穹外卖/黑马头条/乐尚代驾)

目录

苍穹外卖

黑马头条

乐尚代驾

本文主要总结目前开源项目中Redis的使用场景,提供在项目中使用Redis来实现功能的思路,主要是提供实现思路,如果读者想要深入学习的话,可以去B站搜索对应课程学习。

苍穹外卖(缓存)

利用Redis缓存高频数据以适应高并发环境和构造锁来缓解优惠券秒杀等问题,并通过乐观锁解决商品超卖问题;

在我们餐饮项目里,系统显示餐厅的营业状态,营业状态分为营业中打烊中,若当前餐厅处于营业状态,自动接收任何订单,客户可在小程序进行下单操作;若当前餐厅处于打烊状态,不接受任何订单,客户便无法在小程序进行下单操作。虽然,可以通过一张表来存储营业状态数据,但整个表中只有一个字段,所以意义不大;最后,我们选择基于Redis的字符串来进行存储店铺的营业状态,用SHOP_STATUS来作为key,1/0作为value进行存储,其中,我们约定1表示营业,0表示打烊。

在我们餐饮项目中,有这样一个场景,用户端小程序展示的菜品数据都是通过查询数据库获得,如果用户端访问量比较大,数据库访问压力随之增大,这会造成系统响应慢、用户体验差等缺陷。最终,我们通过Redis来缓存菜品数据,减少数据库查询操作,从而来提高系统处理并发的能力。当第一次查询某个分类的商品时,会从数据库中进行查询,同时将查询的结果存储到Redis中,在后续的访问中,若查询相同分类的菜品时,直接从Redis缓存中查询,不再查询数据库。同时,当在后台修改商品数据时,为了保证Redis缓存中的数据和数据库中的数据时刻保持一致,当修改后,需要清空对应的缓存数据。用户再次访问时,还是先从数据库中查询,同时再把查询的结果存储到Redis中,这样,就能保证缓存和数据库的数据保持一致。

黑马头条(消息队列)

通过整合Redis技术实现了延迟任务的功能,并解决了未来数据定时刷新和分布式锁解决集群下方法抢占的难题;

在项目的开发过程中,有这样一个场景:对于文章发布的时间,有立即发布和定时发布两种场景,对于定时发布,这里需要通过延迟任务精准发布文章。对于延迟任务来说,没有固定的开始时间,它常常是由一个事件触发的,而在这个事件触发之后的一段时间内触发另一个事件,任务可以立即执行,也可以延迟。要实现这一功能,我们通常有两种方式,第一种是基于RabbitMQ实现延迟任务,它是通过TTL(消息存活时间)+死信队列来实现的,即当消息成为Dead message后,可以重新发送另一个交换机里进行处理,这种方式具体实现流程如下所示:

而另一种方式是基于Redis来实现,这一实现原理是基于Redis的zset数据类型的去重有序(分数排序)的特点来达到延迟效果的,这一实现的主要流程是:

当我们发布定时任务后,首先需要将定时任务写入到数据库中;然后我们对任务的执行时间进行判断,如果执行时间小于或者等于当前时间的话,那么我们认为这条任务需要在当前时间处理,直接将该任务加入到当前消费队列当中去(也就是Redis的list数据类型),然后直接安排消费即可;相反,当任务的执行大于当前时间的话,我们会将当前任务写入到未来数据队列当中去(也就是Redis的zset数据类型);

其次,为了将Redis未来数据队列当中的数据定时刷新到当前消费队列中(也就是从Redis的zset转到list的过程),在Redis的管道中我们采取Pipeline请求模型定时地从Redis客户端到Redis 服务端传送数据,以此来达到将未来数据定时刷新的目的;

再次,在通过Redis技术实现了延迟任务的功能的过程中,如果有多个端口的服务都去执行refresh定时任务方法,简单来说就是有多个线程对共享数据进行变更,这样会导致数据不一致的情况出现,这就需要使用到分布式锁来解决这一问题。在Java中的常见的分布式锁有以下三种:

在本项目中,我们采取的是redis的分布式锁,底层是基于setnx来实现的,setnx命令即SET if Not Exists,它在指定的key不存在时,为key设置指定的值。在执行未来数据定时刷新的方法时,先通过refresh()方法获取锁,只有持有锁的线程才能够对共享变量进行操作;而获取锁失败的线程会不断重试直到达到阈值进入阻塞状态。

最后,数据库中的数据也需要同步到Redis里面去,我们当时定义了一个重新加载数据的方法,这个方法会每五分钟从数据库中加载即将执行的任务到Redis缓存当中去,在这个过程中,我们需要考虑到数据库和Redis的一致性的问题,所以在每次执行这一操作之前,我们都需要先清理Redis的缓存,以此来达到Redis缓存中的数据都是最新的并且是不重复的数据。

总结来说就是,第一,当用户提交文章之后,系统根据是否有id来判断该操作是发布还是保存操作,如果是草稿,系统直接保存到数据库中并返回成功,而如果是发布操作的话,系统会将文章信息保存到数据库中,并且将审核任务添加到Redis延迟队列中等待被消费;第二,将任务添加到延迟队列中后,根据任务的发布时间来决定任务啥时候被消费,当然,如果任务失败,也是需要记录日志并提供重试机制的;第三,设置定时任务进行消费,我们定义了一个任务每个1秒从延迟队列中拉取任务,如果拉取到了任务,我们进行反序列化任务参数,并获取文章id,再调用审核服务对文章进行审核,如果任务拉取失败的话,也是需要记录日志的,并且将任务重新返回队列或记录到失败队列里去,避免数据丢失的情况;第四,就是文章审核,这一模块需要对文章的文本内容和图片分别进行审核,我们需要根据审核结果更新文章状态,并且审核通过的文章也是需要同步到APP端展示给用户查看的,如果审核失败的话,需要记录失败原因,并且更新文章状态为“审核失败”,方便用户查看文章状态。

乐尚代驾(缓存+GEO+Redisson)

利用Redis缓存机制存储用户信息,有效降低数据库负载,并通过GEO实现对附近司机的快速定位与订单推送;

在代驾这个项目里,我们考虑到在高并发环境下,如果大量的请求直接访问数据库的话,会对数据库造成一定的压力,甚至导致系统崩溃;为了提高系统处理并发的能力,在该项目中,我们利用redis来缓存一些高频数据,这样前端发起请求的时候,会先去redis里面查询数据,如果查询到了数据会直接返回数据,redis缓存中没有数据才会去查询数据库,也就是说部分高频请求不会到达数据库,这在一定提高了系统的并发能力。

其次,在该系统的开发中,我们用到了redis给我们提供的GEO功能,它主要有两个命令,一个是GEOADD+城市+经纬度,用来缓存一个地点的经纬度信息;另一个是GEORADIUS+城市+经纬度+半径,用来查询以该经纬度为中心,半径以内的其他位置信息。在该项目里,司机开启接单服务后,小程序会实时上传经纬度信息到GEO缓存,如果乘客下单,我们就需要查找附近适合接单的司机,如果有对应司机,那就给司机发送新订单消息。我们就是基于这种方式来实现对附近司机的快速定位与订单推送的。

利用Redisson提供分布式锁解决方案,有效避免司机抢单的竞争条件,确保订单分配的公平性和准确性;

在代驾项目中,我们有一个场景,就是乘客发送订单后,半径范围内的司机都可以看到这个订单,但是只能有一个司机接单,这就涉及到了一个典型的超卖问题了。在单体项目中,我们一般会使用synchronized对象锁来解决超卖问题,但是对于分布式项目来说,synchronized无法保证在分布式不同的节点上只能有一个节点获得对象锁;所以在代驾项目中我们选择了采取分布式锁来解决超卖问题。我们首先考虑的是使用redis的setnx命令来实现这一效果,由于redis的单线程的,用了命令之后,只能有一个客户端对某一个key设置值,在没有过期或删除key的时候其他客户端是不能设置这个key的。

但是,redis的setnx指令不好控制分布式锁的时长,所以我们选择了redis的一个框架redisson来实现分布式锁,redisson的话它的底层也是基于setnx和lua脚本的,其中lua脚本用来保证了分布式锁的原子性;另外,redisson这个框架给我们提供了一个WatchDog,也就是看门狗机制,一个线程获取锁之后,这个看门狗线程会持续给持有锁的线程续期,默认是每隔10秒续期一次,这一就能控制Redis实现分布式锁有效时长了。

在上面的三个项目中的应用中,其中黑马头条中基于Redis的消息队列来实现延迟任务的思路较为复杂,如读者想深入了解,我另开帖子分析了,请到Redis类目中查找。

http://www.dtcms.com/a/450329.html

相关文章:

  • 做网站js还是jq2021年世界500强榜单
  • 建设旅游网站的费用预算杭州抖音代运营
  • 【LaTeX】 13 LaTeX 长文档结构管理
  • Python入门:Python3基础练习题详解
  • 高端网站建设加盟帮人做彩票网站
  • 哪个网站做的ppt模板好查查企业网
  • 为什么做的网站别的浏览器打不开怎么回事做网站规划
  • 做影视后期应该关注哪些网站做神马网站优化快速
  • 测试题——1
  • 力扣3634. 使数组平衡的最少移除数目
  • 网站服务器不稳定樟木头网站建设
  • 建设网站都需投入哪些资源wordpress没有图片
  • 网站主栏目投资网站排行
  • 国内永久crmseo刷关键词排名免费
  • 爬虫的道德与法律边界:Robots 协议、版权与个人信息保护
  • @[TOC](文件操作和IO)
  • 打开网站不要出现 index.html携程网站联盟
  • 律师行业协会网站建设做简历的网站叫什么
  • c++ enum和enum class
  • 罗湖网站制作多少钱南京企业网站
  • 【论文阅读】通义实验室,VACE: All-in-One Video Creation and Editing
  • 2025年--Lc165--H637.二叉树的层平均值(二叉树的层序遍历)--Java版
  • 消息顺序消费问题
  • 网站实名制查询唐山网站设计制作
  • 怎么给网站加速长沙房价2020最新价格
  • LeetCode:99.下一个排列
  • 三合一网站源码网站开发后期工作包括那两个部分
  • C49-函数指针(通过指针调用函数)
  • *多棱镜/三极管——AI工具对话本质探讨(智普清言)
  • 外贸网站建设是什么意思磨床 东莞网站建设