dot 速度的未来即将来到您所在的城市。

加入我们,参加 Redis 发布会

DevOps 最头疼的 Redis 问题 - 复制缓冲区

Redis 提供了各种工具,旨在改进和维护高效的内存数据库使用。虽然它独特的 数据类型和命令可以微调数据库以满足应用程序请求,而无需在应用程序级别进行任何 额外的处理,但配置错误,或者更确切地说,使用开箱即用的配置,会导致操作 挑战和性能问题。尽管这些挫折导致了不少头痛,但解决方案确实存在,甚至可能 比预期更简单。

本系列文章将重点介绍使用 Redis 时出现的一些最令人恼火的 问题,以及如何解决这些问题的技巧。这些问题基于我们运行数千个 Redis 数据库 实例的实际经验。

复制缓冲区限制

复制缓冲区是内存缓冲区,在从属 Redis 服务器与主服务器同步时,这些缓冲区 用于保存数据。在完全主从同步中,在同步的初始阶段对数据执行的更改将由 主服务器保存在复制缓冲区中。在初始阶段完成后,缓冲区的内容将发送到 从属服务器。此过程中的缓冲区大小存在限制,导致复制在达到最大值时从头 开始,如我们关于无休止的 Redis 复制循环的文章中所述。为了防止这种情况发生,需要根据预期在复制过程 中进行的更改的数量和类型来对缓冲区进行初始配置。例如,少量更改和/或 更改中的数据量较小,可以用较小的缓冲区来解决,而如果更改很多和/或更改 很大,则需要较大的缓冲区。更全面的解决方案是将缓冲区设置为非常高的级别, 以抵消可能发生的冗长或繁重的复制过程,最终会耗尽缓冲区(如果缓冲区太 小)。最终,此解决方案需要对所涉及的特定数据库进行微调。

Redis 默认设置

> config get client-output-buffer-limit
1) "client-output-buffer-limit"
2) "normal 1073741824 536870912 30 slave 268435456 67108864 60 pubsub 33554432 8388608 60"

此处所述,此默认配置复制链接将在达到 256MB 硬限制时断开(导致 同步从头开始),或者如果连续 60 秒达到 67MB 软限制并保持该限制。在很多 情况下,尤其是写入负载很高且从属服务器的带宽不足时,复制过程永远不会 完成。这会导致一种无限循环的情况,其中主 Redis 服务器不断地派生并快照 整个数据集到磁盘,这会导致最多使用三倍的额外内存以及高 I/O 操作速率。 此外,这种无限循环情况会导致从属服务器永远无法赶上并与主 Redis 服务器完全 同步。

通过将硬限制和软限制都设置为 512MB 来增加从属服务器输出缓冲区 的大小,可以实现一个简单的解决方案,并立即改善性能。

> config set client-output-buffer-limit "slave 536870912 536870912 0"

与许多重新配置一样,重要的是要理解

  1. 在增加复制缓冲区的大小之前,您必须确保机器上有足够的内存。
  2. Redis 内存使用量计算不考虑复制缓冲区大小。

这让我们进入了我们关于 Redis 操作头痛问题的第一篇文章的结尾。如上所述,在复制缓冲区限制方面,适当的配置可以起到很大的作用。请务必关注本系列 的下一篇文章,其中将介绍复制超时以及如何相应地处理它们。