unix - Redis RDB 持久性实际上是如何在幕后工作的?

标签 unix process redis

我正在经历 Redis RDB 持久化。我对 RDB 持久性与其缺点有关有一些疑问。

到目前为止的理解:

当我们需要定期保存内存中当前数据集的快照时,我们应该使用 rdb 持久化。

我可以理解,如果服务器出现故障,我们可能会丢失一些数据。但我无法理解的另一个缺点是,在使用 rdb 持久化大型数据集时,fork 是如何耗时的。

引用文档

RDB needs to fork() often in order to persist on disk using a child process. Fork() can be time consuming if the dataset is big, and may result in Redis to stop serving clients for some millisecond or even for one second if the dataset is very big and the CPU performance not great. AOF also needs to fork() but you can tune how often you want to rewrite your logs without any trade-off on durability.

据我所知,我知道 fork 是如何工作的 当父进程 fork 时,它会创建一个新的子进程,我们可以允许子进程根据其 pid 执行一些代码,或者我们可以为它提供一些新的可执行文件,它将在上面运行使用 exec() 系统调用。

但我不明白当数据集的大小变大时,这将是一项繁重的任务吗?

我想我知道答案,但我不确定

引自此链接 https://www.bottomupcs.com/fork_and_exec.xhtml

当进程调用fork then时

the operating system will create a new process that is exactly the same as the parent process. This means all the state that was talked about previously is copied, including open files, register state and all memory allocations, which includes the program code.

按照上面的语句,redis 的整个数据集将被复制到子进程。

我理解的对吗?

最佳答案

当使用写时复制调用标准 fork 时,操作系统仍必须复制所有页表条目,如果您有小的 4k 页和巨大的数据集,这可能会花费一些时间,这就是真正的 fork()时间慢。

如果您的数据集以稀疏方式进行大量更改,您还会发现需要大量时间和内存,因为写时复制语义会在对原始数据进行更改时触发复制实际内存页面。 Redis 还执行增量重新散列并维护过期时间等,因此更活跃的实例通常需要更长的时间才能保存到磁盘。

更多阅读:

Faster forking of large processes on Linux?

http://kirkwylie.blogspot.co.uk/2008/11/linux-fork-performance-redux-large.html

关于unix - Redis RDB 持久性实际上是如何在幕后工作的?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/46599712/

相关文章:

linux - Matlab MCR 追加环境变量

unix - 删除除匹配的图案行最佳做法以外的所有行(sed)

process - 如何在 Rust 中存储进程

redis - 在 redis-cli 中为从外部 redis 模块加载的新命令添加帮助文档

node.js - 将多个数组字段作为参数

c++ - 在 int main() 中使用类函数

linux - 我如何使用管道或重定向在 Linux 中按照我想要的顺序将文件附加到另一个文件?

java - 使用 C# 检测特定程序何时关闭

Android - 如何使用 PID 获取 processName 或 packageName?

node.js - 使用 Redis 的 Express 应用程序的结构