category
type
status
date
slug
summary
tags
password
Property
Feb 17, 2023 06:54 AM
icon
写扩散和读扩散
写扩散

- 在写扩散中,每个人都只从自己的信息从读取消息,但写(发)消息时,根据单聊和群聊进行如下不同的处理:
单聊:会同时往自己和对方的信箱中写入一份消息 群聊:需要往所有群成员的信箱中都写入一份消息
- 写扩散的优点: 读操作轻,可以很方便做消息的多端同步
- 写扩散的缺点: 写操作很重,尤其是对于群聊来说
在Open-IM-Server项目中就采用了写扩散模型
读扩散

- 在读扩散中,每个对象之间都有一个信箱用来存放一方到另一方的消息,如此如果一方想要向另一方发送一条消息,则无论是群聊还是单聊都只要进行一次写操作,但是如果一方想要读取新消息时则需要读取所有与其关联的信箱。
- 读扩散的优点: 写操作很轻,每一个信箱天然就是两人对象的聊天记录,可以方便查看聊天记录跟进行聊天记录的搜索
- 读扩散的缺点: 读操作很重
Open-IM-Server的写扩散实现思路
信箱实现
- 创建一个topic(对应Open-IM-Server中名称为ws2ms_chat的topic),并在该topic上开启hash partition,这样做的好处是,相同key的消息就会落到同一个partition中,因为同一个partition中的消息是有序的。通过这种思路就可以在使用一个topic的情况下,创建多个信箱且能保证每个信箱内的消息读取的有序性。
我之前的IM系统为每个对象创建信箱的策略是给每个对象新建一个topic,然后对应topic的partition数设置为1,这样不同的topic中的消息的有序性就可以得到保障。 但是,这样做有一个致命的缺点:由于kafka在设计上的问题,topic的数量不是越多越好,在数量到达一定的阈值后,kafka的性能会和topic的数量成反比。
- 通过使用userid或者groupid充当上述在topic中key,就可以实现为IM系统中的每一个对象创建一个信箱的目的。
消息的读写流程
- 写消息的流程 每次产生的消息都会通过msg层的rpc服务根据userid或者groupID写入topic中
- 读消息的流程 这部分代码还没有读到。。。🤣
- 作者:axiszql
- 链接:https://axiszql.com/article/im-kafka-write-spread
- 声明:本文采用 CC BY-NC-SA 4.0 许可协议,转载请注明出处。