CS-Notes 学习笔记
Java 后端 · 系统设计

聊天消息怎样做到不丢失、不重复、不乱序?离线期间的消息怎样补上?

先自己想一想,再看参考要点

参考要点

  • 不丢、不重:发送方为每条消息生成 msg_id,服务端存储后回复 ACK,超时没收到就用同一个 msg_id 重发,服务端用 (sender_id, msg_id) 唯一索引去重
  • 不乱序:服务端为每个会话分配递增的 seq,接收方按 seq 排序,不按各机器的时间
  • 离线:推送只负责通知,接收方记住连续收齐的最大 seq(例如 58),重连时拉取它之后的消息,收到 61 而本地只到 58 时补拉中间的 59、60
  • 用 INCR 分配 seq 时写入失败会留下补不到的空号,后分配的也可能先写入,要求序号连续时在一个事务中把会话的最大序号加 1 并插入消息
在学习站中自测这道题看这道题所在的一天

学习站:先用面试题自评定级,按水平和面试日期排出每天的计划,自评过的题按间隔复习。免费、无需注册,记录只保存在自己的浏览器中。