华为云PB级数据库GaussDB(for Redis)解析第二期:Redis消息队列Stream的应用探讨

摘要:本文将对Stream的经常使用命令和应用场景进行介绍,并探讨原生Redis Stream消息队列的缺陷以及GaussDB(for Redis)提供的解决方案,供你们学习和选用。

华为云高斯Redis团队欢迎各路英才加入,联系邮箱:yuwenlong4@huawei.comhtml

引言:

Redis Stream是Redis 5.0引入的一种新的数据类型,其本质是一个消息队列,相似于 kafka等消息中间件。它提供了消息的落地存储功能,并实现了相似kafka消费组和消费者的功能。与kafka相比,Redis Stream一样拥有强大的功能,但因原生Redis没法有效支持大规模数据存储,成本昂贵,并存在数据丢失/不一致风险等缘由,致使其未能流行起来。本文将对Stream的经常使用命令和应用场景进行介绍,并探讨原生Redis Stream消息队列的缺陷以及GaussDB(for Redis)提供的解决方案,供你们学习和选用。redis

1、Redis Stream简介

与Pub/Sub相比,Redis Stream 具备消息的落地存储功能,每个客户端能访问任意时刻的消息,而且能记录每个客户端的访问位置,还能保证消息不会丢失。Redis Stream 的结构以下所示,它有一个消息链表,将全部加入的消息都连接起来,每一个消息都有惟一的 ID 和对应的内容。数据库

如图所示,每个Stream队列包含多条消息,每条消息由惟一的ID进行标识,由时间戳和序列号组成,例如1627849609889-0。每条消息以追加的方式添加到Stream队列中。同一个Stream队列能够包含多个消费组(Consumer Group),每一个消费组的状态都是独立的,同一个Stream队列的消息能够被多个消费组重复消费。微信

同一个消费组又包含多个消费者(Consumer),这些消费者之间是竞争关系,不一样消费者不会重复消费同一条消息,任意一个消费者读取了队列中的一条消息都会使消费组中的游标last_delivered_id往前移动。该方式提升了并发效率,例如,多个进程并发处理Stream队列中的消息。每一个消费者中维持一个状态变量pending_ids,简称为PEL(Pending Entries List),记录了当前已经被客户端读取的但还没有被ACK的消息,确保消息被客户端成功消费。并发

Redis Stream命令能够分为消息队列命令和消费者命令两类,以下所示:运维

以即时通信中的聊天室场景为例,使用Redis Stream做为中间件,实现聊天室的发言以及信息查看。性能

1)使用XADD命令进行发言。学习

2)使用XLEN命令获取聊天室发言的数量。url

3)使用XRANGE获取消息队列的消息。spa

4)使用XREAD命令读取消息。能够在不设置消费组和消费者的状况下,使用XREAD的命令进行消息读取,此时Stream队列相似于一个普通的列表(list)。

更多的Redis Stream命令使用请参考官方文档(https://redis.io/commands/xread)。

2、应用场景

因为Redis Stream自然有序,特别适合存储时序数据,应用场景包括即时通信、智慧医疗、流量削峰、智慧城市等领域。

(1)即时通信:微信、QQ等是咱们平常生活中经常使用的通信软件,经常使用的聊天方式包含点对点通信和群聊两种方式。下图是一个群聊的模型图,当采用Redis Stream做为通信的中间件,建立一个群聊时,在Redis中对应地为该群聊建立一个Stream队列。在发送消息时,将每一个用户的消息按照时间顺序添加到Stream队列中,保证了消息的有序性。因为Stream是一个持久化的队列,不管是在线仍是离线状态,每一个用户能够屡次查看历史消息,保证了通信的完整性。

(2)智慧医疗:医疗行业的信息化,能够更好地服务于每个人。为每个人从出生起创建一份健康档案,记录相应的健康信息,如体检报告、诊断报告、用药信息、以及智能终端实时上传的健康指标。这些信息都是一些时序数据,一样能够采用Redis Stream来实现智慧医疗系统。创建起智慧医疗系统后,使用终端能够查看全部的医疗信息,并会提示患者按时吃药,在终端上传身体指标异常时,会自动报警并预定挂号。现阶段每一个医院都有本身的信息系统,不一样的医院很难查到同一个患者的医疗信息,在将来,医疗上云将有利于解决医疗信息孤岛,更好的帮助每一位患者。

(3)流量削峰:在常见的秒杀活动或团购中,如春运抢票、商城促销等,一般短期内有大量的流量,致使系统崩溃。因为每个用户在请求时对应惟一的时间戳,全部的请求都有一个前后顺序,一样能够采用Redis Stream做为中间件,将请求加入到Redis Stream消息队列。将消息转存到消息队列间接提供给应用,而非直接发送给应用,能够防止大流量冲击致使的系统崩溃。当消息队列中的请求数量达到规定的最大值时,直接回复客户端抢购失败。

3、原生Redis是否真的适用于以上场景?

如上应用场景具备数据规模大、数据持续增加的特色,虽然原生Redis有良好的设计初衷,可是并不能解决实际问题。具体体如今:

  1. 没法有效应对大规模数据:原生Redis是一个基于内存的数据库,单个节点存储容量有限,当扩展至TB级别的集群,将会出现管理困难,运维成本高等问题。
  2. 集群扩容影响业务性能:原生Redis在进行集群扩容时,须要从新划分hash槽并进行数据迁移,一定会影响业务性能。
  3. 数据可能会丢失:原生Redis虽然能够采用RDB和AOF的方式对数据进行持久化,可是并不会实时地将每一条命令写入到硬盘中,当出现掉电或集群崩溃的状况,一定会丢失一部分数据,对于相似智慧医疗场景,是难以忍受的。

除此之外,必须考虑数据库系统的可用性、数据一致性、成本和备份恢复能力等状况:

  1. 可用性: 原生Redis若采用一主一备的集群模式,当一对主备节点下线,集群部分数据将不可用。
  2. 数据一致性:当主节点宕机,主备节点切换,数据存在没有彻底同步的状况。
  3. 成本:原生Redis是一种内存型数据库,当内存容量扩展至TB级别,成本将很是昂贵。
  4. 备份恢复:须要人工链接数据库执行 SAVE或BGSAVE命令,不能支持按期自动备份,在恢复到新实例时须要手动拷贝备份数据。

4、是否有更好的解决方案?

在以上场景中,亟需一种可以存储和处理大规模Stream数据、鲁棒性强、且成本低廉的数据库系统。而GaussDB(for Redis)(下文简称高斯Redis)正是以上场景中一种很好的应用解决方案。高斯Redis是华为云数据库团队自主研发的兼容Redis协议的云原生数据库,该数据库突破原生Redis的内存限制,可轻松扩展至PB级存储,具备秒扩容、超可用、强一致和低成本等特色。

5、总结

Redis Stream能够普遍应用在即时通信、智慧医疗、流量削峰等领域。在面对大规模的Stream数据时,原生Redis存在成本太高、容量过小、可用性差、数据不一致等问题,没法适用于海量消息队列的场景。与原生Redis相比,高斯Redis具备海量存储,低成本,可持久化等优势,可作为比原生Redis更理想的Stream队列承载方案。

附:参考资料

1. 《华为云GaussDB(for Redis)与自建开源Redis的成本对比》

https://www.modb.pro/db/42739

2. 《一场由fork引起的超时,让咱们从新探讨了Redis的抖动问题》

https://bbs.huaweicloud.com/blogs/227525

3. 《当Redis碰见计算存储分离》

https://developer.huaweicloud.com/hero/forum/thread-83188-1-1.html

4. GaussDB(for Redis)与原生Redis的性能对比》

https://bbs.huaweicloud.com/blogs/236949

5. 《华为云PB级数据库GaussDB(for Redis)揭秘第一期:Redis与存算分离》

https://bbs.huaweicloud.com/blogs/238584

 

 

点击关注,第一时间了解华为云新鲜技术~

相关文章
相关标签/搜索