文章内容主要是群友 大叮当 提的一个问题,然后 大佬李 的回答整理的。
问题:分布式聊天服务器, 当 a 服务器的用户要给 b 服务器的用户发消息时, a服务器需要根据用户 id 找到目标用户在哪台服务器, 然后让那台服务器去发消息,这种用户和服务器的对应关系, 怎样处理最好,也是最高效的?
基础方案: 将用户ID hash一下,分布到各个服务器,用 Redis set 结构存储 hash 之后的值,不要用用户ID 的范围分布到各个服务器,容易导致热点 key 的情况。而某些用户ID 的交互很大,hash 之后的结果会有极小的概率出现热点 key 的情况,热点 key 会导致某一台服务器承受很大压力,其他的服务器围观,而不能分担压力。
升级方案: 为了提前避免 hash 之后有热点 key 的情况,可以提前监控服务器运行,根据服务器的负载状况加权分配。例如 A 服务器负载长期为50%,B 服务器负载为80%,则分配方面,A要多分配一些用户ID,A 有更多的空闲资源处理消息业务,同理 B 则分配少一些,将用户 ID 和计算分配后的对应关系,存储在 Redis set中一份,可以根据用户 ID 查询处理。
额外知识点: 一致性 hash 是为了解决底层存储节点扩展或者减少时候,缓存需要 rehash 的问题,一致性的本质就是虚拟节点。
延伸阅读可以自行搜索 github 及互联网了解一致性的内容。
讨论请联系邮箱: hexiaodong1992@outlook.com, 同在学习分布式中。
最后恰饭 阿里云全系列产品/短信包特惠购买 中小企业上云最佳选择 阿里云内部优惠券