在本文中, 我们将学习以下案例:
1, 使用 RDB
2, 使用 AOF
3,RDB 和 AOF 的结合使用
概要
由于 Redis 是在内存中储存数据的, 所以当 Linux 服务器重新启动后, 所有数据都将丢失 (重启 Redis 不会是因为 Redis 默认开启了 RDB 保存了一份 dump.rdb, 每次启动 Redis, 则会加载 rdb 文件进行数据恢复).
为了保证数据的安全, Redis 提供了将数据持久化到硬盘的机制. Redis 共有两种数据持久化类型: RDB 和 AOF.RDB 可以看作是 Redis 在某个时间点的快照, 非常适合永远备份和灾难恢复. AOF 则是一个写入操作的日志, 将在服务器启动时被重放.
一, 使用 RDB
对于一个像 Redis 这样的内存数据存储, 启用持久化功能是防止数据丢失的最好方法, 实现持久化的一种显而易见的方法是不断的对存储数据的内存进行快照, 而这基本上正式 Redis 的 RDB 的工作方式, 下面介绍如何配置 RDB 持久化功能, 并了解有关快照执行过程的更多细节.
1.1 操作步骤:
1, 调用 config set 命令, 在一个正在运行的 Redis 实例上启用 rdb 持久化:
2, 如果要永久性的启用 RDB 持久化, 可以在 Redis 配置文件中设置 save 参数:
3, 如果需要在一个运行的 Redis 实例上就用 RDB 持久化, 可以直接通过 Redis-cli 设置 save 参数为空字符串: bin/Redis-cli config set save ""
4, 要永久禁用 RDB 持久化, 则可以在 Redis.conf 配置文件中注释 / 删除掉 save 参数
5, 通过 Redis-cli 获取 RDB 是否开启: bin/Redis-cli config get save . 如果 save 选项为一个空字符串则表示 RDB 是被禁用的. 否则, 则返回 RDB 快照的触发策略, RDB 的快照策略格式为 x1,y1,x2,y2...., 其中含义是, 如果超过 y 个 key 发生了改变, 且此时没有转储正在发生, 则在 x 秒后进行数据转储.
6,RDB 文件默认文件名称为: dump.rdb
7, 如果需要手动执行 RDB 快照, 在 Redis-cli 中调用 save 命令即可, Redis-cli 客户端将会被阻塞一段时间, 然后命令提示符会返回如下内容:
8, 或者我们可以调用 BGSAVE 的命令来执行非阻塞的 RDB 转储, 可以通过 ps -ef|grep Redis 命令查看转储进程的 pid.
9, 通过 Redis-cli 执行 info persistence 命令可以获取到与持久化相关的指标与状态:
1.2, 工作原理
RDB 默认为开启, 当设置 config set save "900 1" 表示如果有超过 1 个键发生了改变, 则在 900 秒后进行数据转储, 在 save 选项中, 我们可以配置多个策略来控制 RDB 快照文件的频率.
通过 save/bgsave 命令可以手动启动一次 RDB 转储, 这两个命令的不同之处在于, save 使用的是主线程进行同步存储, 会阻塞 Redis 服务器. bgsave 则是在后台开启一个子进程进行数据转储. 所以一般建议永远不要在生产环境使用 save, 除非是凌晨停机状态.
bgsave 由于是异步的, 它不会阻塞主进程继续收集请求, 它会在通过 fork() 系统调用创建一个子进程将数据转储保存在一个名为 temp-<bgsave-pid>. rdb 的临时文件中. 当转储过程结束后, 这个临时文件会被重命名为由参数 dbfilename 定义的名字覆盖并保存在 dire 指定的本地目录中. 上述两个参数都可以通过 Redis-cli 进行动态修改.
在子进程替换旧转储文件后, 它会根据子进程使用的私有数据量输出一条日志:
我们还可以通过 info persistence 命令可以获取到与持久化相关的指标与状态:
rdb_bgsave_in_progress:1 表示转储正在进行
rdb_last_bgsave_time_sec 的值表示当前正在进行的 bgsave 命令所持续的时间
rdb_last_save_time:1543846365 表示最后一次成功的时间戳
1.3, 更多细节
下面是一些与 RDB 持久化相关的一些配置选项, 建议全部使用默认值 (yes:
1,stop-writes-on-bgsave-error yes: 如果该选项设置为 yes 的化, 那么作为保护机制, 当 bgsave 失败时, Redis 服务器将停止接收写入操作.
2,rdbcompression yes: 压缩可以显著的减少转储文件的大小, 但是会占用消耗更多的 CPU
3,rdbchecksum yes: 在快照文件的末尾创建一个 CRC64 的校验和. 使用该选项将在保存时加载快照文件时额外的消耗约 10% 的性能, 如果设置为 no 可以获得最大的性能, 但同时会降低对数据损坏的抵抗力.
4, 由于 save/bgsave 命令生成的转储文件可以用作数据备份文件, 我们可以使用 Linux 系统中的 crontab 定期将 RDB 文件复制到本地目录, 供日后恢复使用
5, 如果要还原 RDB 快照, 我们需要把快照文件复制到 dir 选项指定的位置.
二, 使用 AOF
在上述案例当中, 我们学习了 RDB 的方式进行数据持久化, 但 RDB 做数据持久化并不能提供非常强的一致性, AOF(append-only file) 是一种只记录 Redis 写入命令的追加式日志文件. 因为每个写入命令都会被追加到 AOF 文件中, 所以 AOF 的数据一致性比 RDB 更高, 在下面我们开始展示如何在 Redis 中使用 AOF 进行数据持久化, 并介绍一些重要的配置参数.
2.1 操作步骤
1: 使用 config set 命令, 对一个正在运行的 Redis 实例上启用 AOF 持久化:
2: 如果想要永久的启动 AOF 持久化, 可以在 Redis 配置文件中添加 appendonly yes, 然后重新启动 Redis 服务:
3:: 要在一个正在运行的 Redis 实例中, 禁用 AOF 持久化, 可以把 appendonly 设置为 no, 然后重新启动 Redis.
4: 要永久的禁用 AOF 持久化, 则修改配置文件 Redis.conf 中 appendonly no 并重新启动 Redis 服务即可.
5: 使用 info persistence 命令检查 AOF 相关的内容判断是否启用 AOF 功能
6:AOF 文件名默认保存为 appendonly.aof
2.2 工作原理
当 AOF 功能被启用时, Redis 将会在数据目录创建 AOF 文件, AOF 文件名默认保存为 appendonly.aof, 并可以通过配置文件中 appendonlyfilename 参数进行修改. 同时 Redis 还会将当前内存的数据填充到这个 AOF 文件中来.
每当 Redis 接收到会实际修改内存数据的写入命令时, Redis 会将该命令追加到 aof 文件中, 如果深入研究 AOF 的写入过程, 就会发现操作系统实际上维护了一个缓冲区, Redis 的命令首先会被写入到这个缓冲区当中, 而缓冲区的数据必须被刷新到磁盘当中才能永久保存. 这个过程是通过 Linux 系统调用 fsync() 完成的, 这是一个阻塞调用, 只有磁盘设备报告缓冲区中的数据写入完成后才会返回.
在将命令追加到 AOF 文件时候, 我们可以通过配置 Redis 的参数 appendfsync 来调整调用 fsync 的频率, 该参数共有三个选项:
1,always: 对每个写入的命令都调用 fsync, 这个选项可以确保 Redis 服务器发生意外崩溃或硬件故障时, 只会丢失一个命令, 但是由于 fsync 是一个阻塞调用, Redis 的性能会收到物理磁盘写入性能的限制, 所以此举是不明智的, Redis 的性能会显著降低!
2,everysec: 每秒调用一次 fsync, 采用这一选项时, 在意外灾难事件中只会有一秒钟的数据会被丢失.
3,no 永远不调用 fsync, 采用该选项时, 将由操作系统决定何时把数据从缓冲区写入到磁盘, 大多数 Linux 系统中, 这个频率是每 30s.
在 Redis 服务器关闭时, fsync 都会显式的被调用, 以确保吸入缓冲区的数据都会被刷新在磁盘当中. 当 Redis 启动时, AOF 文件都会被用来恢复数据
2.3 更多细节
随着 Redis 将写入命令不断的追加到 AOF 文件当中, aof 文件的大小会显著的增加, 这回拖慢 Redis 启动时的数据重建过程, Redis 提供了一种机制, 即通过 AOF 重写要压缩 AOF 文件, Redis 主进程会创建一个子进程来执行 AOF 的重写, 这个子进程会创建一个新的 AOF 文件来存储重写的结果, 父进程则继续相应请求并将命令追加到旧的 AOF 文件当中, 这里不讲述 AOF 重写的过程细节.
三, 使用 RDB+AOF 结合使用
在涉及到数据持久化时, 我们总是需要考虑几个因素: 意外停机导致数据丢失, 保存数据时的性能开销, 持久化文件的大小以及数据恢复的速度. 对于 RDB 而言, 两次快照之间写入的数据可能会丢失, 当写入流量较大且数据集也很大时, RBD 中系统调用 fork() 的延迟和内存开销也可能变成一个问题. 不过, 与 AOF 相比, RDB 转储文件占用的硬盘空间更少, 并且从 RDB 转储中恢复数据的速度更快. 事实上, 我们可以同时启用这两个功能.
同时开启 RDB 跟 AOF, 我们会发现数据同时以 RDB 和 AOF 的方式保存到了 Redis 的数据目录, 并且可以清楚的发现 AOF 文件要比 RDB 文件更大.
在同时开启 RBD 和 AOF 后, 我们将配置参数 aof-use-rdb-preamble 设置为 yes, 来启用 4.x 开始提供的新的混合持久化功能. 这里建议在 redis4.x 之后启用 AOF 和混合持久化, 如果我们能够忍受某些可能的数据丢失, 那么只使用 RDB 能够获得更好的性能.
最后, Redis 保证 RDB 转储跟 AOF 重写不会同时进行. 当 Redis 启动时, 即便 RDB 和 AOF 持久化同时启用且 AOF,RDB 文件都存在, 则 Redis 总是会先加载 AOF 文件, 这是因为 AOF 文件被认为能够更好的数据一致性, 当家宅 AOF 文件时, 如果启用了混合持久化, 那么 Redis 将首先检查 AOF 的前五个字符, 如果这五个字符是 Redis, 那么该 AOF 文件就是混合格式的, Redis 服务器会先加载 RDB 部分, 然后再加载 AOF 部分.
以上参考:《Redis 4.x Cookbook》持久化.
三千多字, 我滴妈呀!!!!!
来源: http://www.jianshu.com/p/694ff0705426