Redis持久化(Persistence):了解如何配置redis的持久化。

Redis持久化机制

RDB持久化方式:在指定时间间隔对数据进行快照存储redis

AOF持久化方式:每次写操做都会记录下来,当服务器重启的时候会从新执行这些命令来恢复原始数据。AOF命令以redis协议追加保存每次写的操做到文件末尾,Redis还能对AOF文件进行后台重写,使得AOF文件的体积不至于过大。数据库

同时开启两种持久化机制:在这种状况下,当Redis重启的时候会优先载入AOF文件来恢复原始的数据,由于在一般状况下AOF文件保存的数据集要比RDB文件保存的数据集要完整。缓存

不使用任何持久化方式:若是你只但愿你的数据在服务器运行时候存在,你也能够不使用任何持久化方式。安全

RDB的优势

RDB是一个很是紧凑的文件,它保存了某个时间点的数据集,很是适用于数据集的备份,好比:你能够每一个小时保存一下过去24h内的数据,同时天天保存过去30天的数据,这样即便出了问题也能够根据需求恢复到不一样版本的数据集。服务器

RDB是一个紧凑的单一文件,很方便的传送到另外一个远端数据中心,很是适用于灾难恢复app

RDB在保存RDB文件时父进程惟一须要作的就是fork出一个子进程,接下来的工做所有交给子进程来完成,能够最大化Redis的性能工具

与AOF相比,在恢复大的数据集的时候,RDB方式会更快一些性能

RDB的缺点

redis宕机丢失数据更多:若是你但愿在redis意外中止工做(假如电源中断)的状况下丢失数据最少的话,那么RDB不适合你,虽然你能够配置不一样的save时间点(好比每隔5分钟而且对数据集有100个写操做),redis要完整的保存整个数据集是一个比较繁重的工做,你一般每隔5分钟或者更久作一次完整的保存,万一在Redis意外宕机,你可能会丢失几分钟的数据。ui

RDB须要常常fork子进程来保存数据集到硬盘上:当数据集比较大的时候,fork的过程是很是耗时的,可能会致使Redis在一些毫秒级内不能响应客户端的请求,若是数据集巨大而且CPU性能不是很好的状况下,这种状况会持续1秒,AOF也须要fork,可是你能够调节重写日志文件的频率来提升数据集的耐久度。加密

AOF的优势

使用AOF会让你的Redis更加耐久:你能够选择使用不一样的fsync策略:无fsync,每秒fsync,每次写的时候fsync。使用默认的每秒fsync策略,Redis性能依然不错(fsync是由后台线程进行处理的,主线程会尽力处理客户端的请求),一旦出现故障,你最多丢失1秒的数据。

AOF文件是一个只进行追加的日志文件,因此不须要写入seek,即便因为某些缘由(磁盘空间已满,写的过程当中宕机等待)未执行完整的写入命令,你也可使用redis-check-aof工具修复这些问题。

Redis能够在AOF文件体积变得过大时,自动的在后台对AOF进行重写:重写后的新AOF文件包含了恢复当前数据所需的最小命令集合。整个重写过程当中发生宕机,现有的AOF文件也不会丢失。而一旦新的AOF文件建立完毕,Redis就会从旧的AOF文件切换到新的AOF文件,并开始对新的AOF文件进行追加操做。

AOF文件有序的保存了对数据库执行的全部写操做,这些写操做以Redis协议格式保存,所以AOF文件内容很是容易被人读懂,对文件进行分析(parse)也很轻松。导出(export)AOF文件也很是简单:举个例子, 若是你不当心执行了 FLUSHALL 命令, 但只要 AOF 文件未被重写, 那么只要中止服务器, 移除 AOF 文件末尾的 FLUSHALL 命令, 并重启 Redis , 就能够将数据集恢复到 FLUSHALL 执行以前的状态。

AOF的缺点

对于相同的数据集来讲:AOF文件的体积一般要大于RDB文件的体积。

根据所使用的fsync策略,AOF的速度可能会慢于RDB。在通常状况下,每秒fsync的性能依然很是高,而关闭fsync可让AOF的速度和RDB同样快,即便在高负荷之下也是如此。不过在处理巨大的写入载入时,RDB能够提供更有保证的最大延迟时间。

如何选择使用哪一种持久化方式?

通常来讲, 若是想达到足以媲美 PostgreSQL 的数据安全性, 你应该同时使用两种持久化功能

若是你很是关心你的数据, 但仍然能够承受数分钟之内的数据丢失, 那么你能够只使用 RDB 持久化

有不少用户都只使用 AOF 持久化, 但咱们并不推荐这种方式: 由于定时生成 RDB 快照(snapshot)很是便于进行数据库备份, 而且 RDB 恢复数据集的速度也要比 AOF 恢复的速度要快, 除此以外, 使用 RDB 还能够避免以前提到的 AOF 程序的 bug 

快照

在默认状况下, Redis 将数据库快照保存在名字为 dump.rdb的二进制文件中。你能够对 Redis 进行设置, 让它在“ N 秒内数据集至少有 M 个改动”这一条件被知足时, 自动保存一次数据集。你也能够经过调用 SAVE或者 BGSAVE , 手动让 Redis 进行数据集保存操做。

好比说, 如下设置会让 Redis 在知足“ 60 秒内有至少有 1000 个键被改动”这一条件时, 自动保存一次数据集:

save 60 1000

工做方式

当 Redis 须要保存 dump.rdb 文件时, 服务器执行如下操做:

  • Redis 调用forks. 同时拥有父进程和子进程。
  • 子进程将数据集写入到一个临时 RDB 文件中。
  • 当子进程完成对新 RDB 文件的写入时,Redis 用新 RDB 文件替换原来的 RDB 文件,并删除旧的 RDB 文件。

这种工做方式使得 Redis 能够从写时复制(copy-on-write)机制中获益。

只追加操做的文件(Append-only file,AOF)

快照功能并非很是耐久(dura ble): 若是 Redis 由于某些缘由而形成故障停机, 那么服务器将丢失最近写入、且仍未保存到快照中的那些数据。 从 1.1 版本开始, Redis 增长了一种彻底耐久的持久化方式: AOF 持久化。

从如今开始, 每当 Redis 执行一个改变数据集的命令时(好比 SET), 这个命令就会被追加到 AOF 文件的末尾。这样的话, 当 Redis 从新启时, 程序就能够经过从新执行 AOF 文件中的命令来达到重建数据集的目的。

你能够在配置文件中打开AOF方式:

appendonly yes

日志重写

由于 AOF 的运做方式是不断地将命令追加到文件的末尾, 因此随着写入命令的不断增长, AOF 文件的体积也会变得愈来愈大。举个例子, 若是你对一个计数器调用了 100 次 INCR , 那么仅仅是为了保存这个计数器的当前值, AOF 文件就须要使用 100 条记录(entry)。然而在实际上, 只使用一条 SET 命令已经足以保存计数器的当前值了, 其他 99 条记录实际上都是多余的。

为了处理这种状况, Redis 支持一种有趣的特性: 能够在不打断服务客户端的状况下, 对 AOF 文件进行重建(rebuild)。执行 BGREWRITEAOF 命令, Redis 将生成一个新的 AOF 文件, 这个文件包含重建当前数据集所需的最少命令。Redis 2.2 须要本身手动执行 BGREWRITEAOF 命令; Redis 2.4 则能够自动触发 AOF 重写, 具体信息请查看 2.4 的示例配置文件。

AOF有多耐用?

你能够配置 Redis 多久才将数据 fsync 到磁盘一次。有三种方式:

  • 每次有新命令追加到 AOF 文件时就执行一次 fsync :很是慢,也很是安全
  • 每秒 fsync 一次:足够快(和使用 RDB 持久化差很少),而且在故障时只会丢失 1 秒钟的数据。
  • 从不 fsync :将数据交给操做系统来处理。更快,也更不安全的选择。
  • 推荐(而且也是默认)的措施为每秒 fsync 一次, 这种 fsync 策略能够兼顾速度和安全性。

若是AOF文件损坏了怎么办?

服务器可能在程序正在对 AOF 文件进行写入时停机, 若是停机形成了 AOF 文件出错(corrupt), 那么 Redis 在重启时会拒绝载入这个 AOF 文件, 从而确保数据的一致性不会被破坏。当发生这种状况时, 能够用如下方法来修复出错的 AOF 文件:

  • 为现有的 AOF 文件建立一个备份。
  • 使用 Redis 附带的 redis-check-aof 程序,对原来的 AOF 文件进行修复:

    $ redis-check-aof –fix

  • (可选)使用 diff -u 对比修复后的 AOF 文件和原始 AOF 文件的备份,查看两个文件之间的不一样之处。
  • 重启 Redis 服务器,等待服务器载入修复后的 AOF 文件,并进行数据恢复。

工做原理

AOF 重写和 RDB 建立快照同样,都巧妙地利用了写时复制机制:

  • Redis 执行 fork() ,如今同时拥有父进程和子进程。
  • 子进程开始将新 AOF 文件的内容写入到临时文件
  • 对于全部新执行的写入命令,父进程一边将它们累积到一个内存缓存中,一边将这些改动追加到现有 AOF 文件的末尾,这样样即便在重写的中途发生停机,现有的 AOF 文件也仍是安全的。
  • 当子进程完成重写工做时,它给父进程发送一个信号,父进程在接收到信号以后,将内存缓存中的全部数据追加到新 AOF 文件的末尾。
  • 搞定!如今 Redis 原子地用新文件替换旧文件,以后全部命令都会直接追加到新 AOF 文件的末尾。

怎样从RDB方式切换为AOF方式

在 Redis 2.2 或以上版本,能够在不重启的状况下,从 RDB 切换到 AOF :

  • 为最新的 dump.rdb 文件建立一个备份。
  • 将备份放到一个安全的地方。
  • 执行如下两条命令:
  • redis-cli config set appendonly yes
  • redis-cli config set save “”
  • 确保写命令会被正确地追加到 AOF 文件的末尾。
  • 执行的第一条命令开启了 AOF 功能: Redis 会阻塞直到初始 AOF 文件建立完成为止, 以后 Redis 会继续处理命令请求, 并开始将写入命令追加到 AOF 文件末尾。

执行的第二条命令用于关闭 RDB 功能。 这一步是可选的, 若是你愿意的话, 也能够同时使用 RDB 和 AOF 这两种持久化功能。

重要:别忘了在 redis.conf 中打开 AOF 功能! 不然的话, 服务器重启以后, 以前经过 CONFIG SET 设置的配置就会被遗忘, 程序会按原来的配置来启动服务器。

AOF和RDB之间的相互做用

在版本号大于等于 2.4 的 Redis 中, BGSAVE 执行的过程当中, 不能够执行 BGREWRITEAOF 。 反过来讲, 在 BGREWRITEAOF 执行的过程当中, 也不能够执行 BGSAVE。这能够防止两个 Redis 后台进程同时对磁盘进行大量的 I/O 操做。

若是 BGSAVE 正在执行, 而且用户显示地调用 BGREWRITEAOF 命令, 那么服务器将向用户回复一个 OK 状态, 并告知用户, BGREWRITEAOF 已经被预约执行: 一旦 BGSAVE 执行完毕, BGREWRITEAOF 就会正式开始。 当 Redis 启动时, 若是 RDB 持久化和 AOF 持久化都被打开了, 那么程序会优先使用 AOF 文件来恢复数据集, 由于 AOF 文件所保存的数据一般是最完整的。

备份redis数据

  • 建立一个按期任务(cron job), 每小时将一个 RDB 文件备份到一个文件夹, 而且天天将一个 RDB 文件备份到另外一个文件夹。
  • 确保快照的备份都带有相应的日期和时间信息, 每次执行按期任务脚本时, 使用 find 命令来删除过时的快照: 好比说, 你能够保留最近 48 小时内的每小时快照, 还能够保留最近一两个月的每日快照。
  • 至少天天一次, 将 RDB 备份到你的数据中心以外, 或者至少是备份到你运行 Redis 服务器的物理机器以外

容灾备份

Redis 的容灾备份基本上就是对数据进行备份, 并将这些备份传送到多个不一样的外部数据中心。容灾备份能够在 Redis 运行并产生快照的主数据中心发生严重的问题时, 仍然让数据处于安全状态。

由于不少 Redis 用户都是创业者, 他们没有大把大把的钱能够浪费, 因此下面介绍的都是一些实用又便宜的容灾备份方法:

  • Amazon S3 ,以及其余相似 S3 的服务,是一个构建灾难备份系统的好地方。 最简单的方法就是将你的每小时或者每日 RDB 备份加密并传送到 S3 。 对数据的加密能够经过 gpg -c 命令来完成(对称加密模式)。 记得把你的密码放到几个不一样的、安全的地方去(好比你能够把密码复制给你组织里最重要的人物)。 同时使用多个储存服务来保存数据文件,能够提高数据的安全性。
  • 传送快照可使用 SCP 来完成(SSH 的组件)。 如下是简单而且安全的传送方法: 买一个离你的数据中心很是远的 VPS , 装上 SSH , 建立一个无口令的 SSH 客户端 key , 并将这个 key 添加到 VPS 的 authorized_keys 文件中, 这样就能够向这个 VPS 传送快照备份文件了。 为了达到最好的数据安全性,至少要从两个不一样的提供商那里各购买一个 VPS 来进行数据容灾备份。
  • 须要注意的是, 这类容灾系统若是没有当心地进行处理的话, 是很容易失效的。最低限度下, 你应该在文件传送完毕以后, 检查所传送备份文件的体积和原始快照文件的体积是否相同。 若是你使用的是 VPS , 那么还能够经过比对文件的 SHA1 校验和来确认文件是否传送完整。

另外, 你还须要一个独立的警报系统, 让它在负责传送备份文件的传送器(transfer)失灵时通知你。

相关文章
相关标签/搜索