《即时消息技术剖析与实战》 学习笔记 day7

117 阅读5分钟

大家好,我是砸锅。一个摸鱼八年的后端开发。熟悉 Go、Lua。今天和大家一起学习 IM 系统😊

缓存分布式算法

  1. 取模求余。例如通过消息 ID 哈希之后对缓存节点取模求余,余数就是缓存到哪个节点。缺点是如果某个节点宕机或者加入新的节点,节点数量发生变化之后,Hash 后取模求余结果就会变化,导致缓存命中率下降

  2. 一致性哈希。将全量缓存空间分为 2^32 个区域,这些区域组成一个环形的存储结构。每一个缓存的消息 ID通过哈希算法都可以转成一个 32 位的二进制数,对应环形区域的其中一个。缓存的节点也遵循同样的哈希算法(比如利用节点的 IP 来哈希),这些缓存节点也都能被映射到 2 的 32 次方个区域中的某一个 每一个映射完的消息 ID,我们按顺时针旋转,找到离它最近的同样映射完的缓存节点,该节点就是消息 ID 对应的缓存节点 相比取模求余,一致性哈希能保证大部分缓存节点不变,只会有小部分缓存需要更改节点

    https://p3-juejin.byteimg.com/tos-cn-i-k3u1fbpfcp/9e2c142f4925428cb181f2473c169651~tplv-k3u1fbpfcp-zoom-1.image

  3. 数据倾斜。如果部署的缓存节点很少的话,容易造成节点之间数据不均衡的情况,发生数据倾斜,所以可以引入虚拟节点来人为创造更多缓存节点,让数据分布更加均匀。将每一个物理节点和多个虚拟节点关联起来,如果缓存哈希定位到虚拟节点的时候,再通过虚拟节点定位到真正的物理节点

  4. 多级缓存架构 -L1 + 主从模式。在主从缓存结构前面加一层 L1 缓存层,L1 缓存用于极热数据

  5. 多级缓存架构 -本地缓存 + L1 + 主从多层模式。增加多层缓存来解决请求量大的问题,但是也会带来数据一致性的问题,要么采取短过期时间的方式来平衡本地缓存命中率和数据更新一致性的问题

服务扩容

垂直扩展:提升资源服务器和应用服务器的单机处理能力,只能解决短期的资源和服务瓶颈

水平扩展:入口可以在 DNS 服务器中,针对接入服务域名配置多个 VIP;当用户访问接入服务时,DNS 服务器就会通过轮询或者其他策略,来从 A 记录中选择某一个 VIP 供用户连接。用户通过接入服务上线后,接入服务会在中央资源中(比如 Redis)记录当前用户在哪台网关机上线。如果业务层有消息需要推送给这个用户时,通过查询这个中央资源,就能知道当前用户连接在哪台网关机上,然后就可以通过网关机的 API 接口,把消息定向投递推送给用户了

业务层的多台服务器在启动上线时,先在“服务注册中心”进行服务注册,登记当前业务机器支持调用的“服务”;启动后,服务注册中心通过“注册中心主动检测”或者“业务服务器主动上报”的方式,定期对服务的可用性进行健康检查,不可用的业务服务器会从注册中心摘除。长连网关机在需要调用业务层服务时,会先通过服务发现、获取当前要用到的服务所注册的业务服务器地址,然后直连某一台具体的业务服务器进行 RPC 服务调用。这样,通过对业务层进行“服务化”改造,利用服务注册和服务自动发现机制,我们就能够让业务层做到完全的无状态化。不管我们的业务层如何进行扩缩容,接入层也能随时调用到业务层提供的服务,从而实现了业务层的“水平扩展”

当我们的服务需要扩容时,先把服务打包为 Docker 镜像,通过运维系统或者第三方的 Kubernetes 等容器管理服务,来动态分发镜像到需要部署的机器上,并进行镜像的部署和容器启停

系统监控

被动监控:系统层监控、应用层监控、全链路 Trace 监控

系统层监控是指对操作系统维度的一些指标做监控,例如 CPU、内存、IO、负载、带宽、PPS、Swap 等数据信息

应用层监控是指实时对消息收发接口的 QPS、耗时、失败数、消息在线推送到达率等分析

基于 Trace 服务,对消息的收发行为进行全链路监控数据收集。

Trace 表示对一次请求完整调用链的跟踪,每一条链路都使用一个全局唯一的 TraceID 来标识。Span 是指在链路调用中,两个调用和被调用服务的请求 / 响应过程叫做一次 Span。一条 Trace 可以被认为是由多个 Span 组成的一个有向无环图(DAG 图)

Annotation 主要用于用户自定义事件,Annotation 可以携带用户在链路环节中的自定义数据,用来辅助定位问题

此文章为3月Day13学习笔记,内容来源于极客时间《即时消息技术剖析与实战》 这门课真的非常好,推荐大家看看