恢复路径

如果您使用差异或日志备份并且通过下列方式之一将数据库恢复到以前的时间点,则很有必要理解恢复路径:

  • 执行时点还原
  • 执行恢复而不先还原所有日志备份或最新的差异备份。

如果将数据库恢复到更早的恢复点并从该点开始使用数据库,会生成一个新的恢复路径。“恢复路径”**是指通过正常的数据库使用或特定的数据和日志还原将数据库恢复到特定时间点的数据和日志备份的序列。恢复路径由一组不同的转换(随着时间的变化对数据库进行演变并保持一致性)组成。下图说明了恢复点与其生成的恢复路径之间的关系。

恢复点和最终恢复路径

通常,由于必须回滚事务并且数据库现在处于唯一的状态,恢复点将开始一个新的恢复路径。预先存在的备份现在可能具有比此恢复点的日志序列号 (LSN) 更大的 LSN。这些备份中的 LSN 存在于由当前恢复操作创建的新分支以外的恢复分支中。

ms175078.note(zh-cn,SQL.90).gif注意:
在不使用任何其他备份类型的情况下,还原完整数据库备份并恢复数据库将创建新的恢复路径。

最佳方法 若要避免创建具有多个恢复分叉的恢复路径,请在恢复数据库之后尽快执行一组完整的数据备份。此方法可保证对单个恢复分支执行所有备份。若要对此进行验证,您可以查看 last_recovery_fork_guid 列(位于 backupset 表或 RESTORE HEADERONLY 结果集中)。

下列情况会创建新的恢复路径,因为数据库未还原到“结束时间”。此后,会出现使数据库进入两个或两个以上恢复路径的备份,它们都使用同一组 LSN。

  • 不应用现有的事务日志备份还原完整数据库备份和差异数据库备份并恢复数据库。
  • 将数据库恢复到非最新的差异备份的结尾处。
  • 将数据库恢复到非最新的事务日志备份的结尾处。
  • 将数据库恢复到特定时间或事务日志备份中的某个标记事务处。

恢复路径示例

下图显示了恢复数据库时新恢复路径的分叉。在此图中,创建了一个完整的数据库备份和一个由四个日志备份组成的序列。然后,此数据库通过还原完整数据库备份、日志备份 1 和日志备份 2 而还原到日志备份 2 的末尾。数据库从该点开始恢复并创建一个新的恢复分叉。然后,该数据库使用一段时间后,又创建了两个事务日志备份:日志备份 5 和日志备份 6。

恢复路径示例

数据库备份和前四个日志备份都在分支 1 上。日志备份 5 和日志备份 6 在分支 2 上。恢复分叉包含日志备份 2 的最后一个 LSN (Log_Backup_2.LastLSN) 和日志备份 5 的第一个 LSN (Log_Backup_5.FirstLSN)。

在日志备份 5 中,first_recovery_fork_guid 标识分支 1,last_recovery_fork_guid 标识分支 2。恢复路径为分支 1、分支 2。

ms175078.note(zh-cn,SQL.90).gif注意:
分叉到新路径不需要还原到日志备份的结尾处。

还原并沿旧路径前滚

建议您不要使用旧的恢复路径。因为使用旧的恢复路径会导致数据库拥有在两个不同的时间间隔提交的事务。但是,如有必要,您可以按照在创建当前恢复路径之前所做的备份顺序,沿着旧的恢复路径前滚。例如,可以使用在时点恢复之前所做的备份来到达旧路径上的各个点。

ms175078.note(zh-cn,SQL.90).gif注意:
若要从一个公共父级创建两个数据库,请考虑为每个数据库选择一个您必须用来到达该数据库以前备份结束时间的恢复路径。

例如,根据上图中创建的备份,创建日志备份 5 和日志备份 6 之后,仍可以还原到位于旧恢复路径上的日志备份 3 的末尾。

还原并从旧路径前滚到新路径

SQL Server 数据库引擎禁止在一个还原顺序中使用来自不同路径的备份(即试图沿不同恢复路径前滚)。此限制使得数据库在恢复之后仍能保持一致。

若要还原并沿新恢复路径前滚,请为恢复点之前和之后的备份构造不同的还原顺序:

  1. 还原在引入新恢复路径的恢复之前所做的备份。排除包含恢复点的备份。
  2. 通过还原在创建恢复路径之后所做的备份,沿新恢复路径前滚。

例如,根据上图中创建的备份,假设日志备份 3 涵盖的时间是从上午 10 点到上午 11 点。这说明已经执行了时点还原,指定 STOPAT**=10:**30。此操作使恢复路径分叉并产生新的恢复分支:分支 2。新分支上的第一个日志备份(日志备份 5)所包含的第一个 LSN 与日志备份 3 相同,日志备份 5 将替换现已失效的日志备份 3。若要对新恢复路径还原备份(从分支 1 开始,到分支 2 结束),则其还原顺序为:完整数据库备份、日志备份 1、日志备份 2、日志备份 5 及日志备份 6。

管理恢复分叉

“恢复分支”是共享同一 GUID 的一组 LSN。恢复路径描述从“起点” (LSN,GUID) 到“终点”** (LSN,GUID) 的一组 LSN。恢复路径中的 LSN 可以从起点到终点遍历一个或多个恢复分支。创建数据库并用 RESTORE WITH RECOVERY 生成恢复分叉之后,会生成新的恢复分支。

“恢复分叉”**指每次执行 RESTORE WITH RECOVERY 时,开始新的恢复分支的点 (LSN,GUID)。每个恢复分叉都确定了恢复分支之间的父子关系。

恢复数据库会将整个数据库状态(包括下一个 LSN)设置到恢复点。然后从 fork_point_lsn 开始重用 LSN。因此,在构造还原顺序时,必须按恢复分叉和 LSN 将备份链接起来,因为同一 LSN 可能存在于多个分叉中。下图说明了如何重用 LSN。它显示了在不同的恢复分叉中如何重用 LSN。

在不同的恢复分支中如何重用 LSN

如果还原顺序必须包含遍历恢复分叉的备份,则在构造还原顺序时必须使所用的备份沿正确的恢复路径到达恢复点。因此,备份包括 backupset.first_recovery_fork_guidbackupset.last_recovery_fork_guid。它们用于链接备份,以确保顺序中采用了正确的分叉。

使用 backupset 历史记录表中的值可以确定使用哪个备份集:

  • 对于顺序中要还原的每个日志备份,first_recovery_fork_guid 必须等于顺序中前一备份的 last_recovery_fork_guid
    first_recovery_fork_guid 等于 last_recovery_fork_guid
  • 数据和差异备份也必须链接起来。
    如果日志备份同时包含完整数据库备份或差异数据库备份的最后一个 LSN 和分叉点,则链接测试将取决于最后一个 LSN 相对于分叉点的位置。
    链接测试如下(使用来自 backupset 的值):
    • 如果 last_lsn 小于或等于 fork_point_lsn,则数据或差异备份的 last_recovery_fork_guid 必须等于日志备份的 first_recovery_fork_guid。下图说明了 last_lsn 小于 fork_point_lsn 的情况。
      last_lsn 小于 fork_point_lsn
    • 如果 last_lsn 大于 fork_point_lsn,则数据或差异备份的 last_recovery_fork_guid 必须等于日志备份的 last_recovery_fork_guid。下图说明了 last_lsn 大于 fork_point_lsn 的情况。
      last_lsn 大于 fork_point_lsn
  • 对于差异备份,使用 backupset.differential_base_guid 找到差异基准。
    如果差异为多基准,则 backupset.differential_base_guid 为 NULL,您必须使用 backupfile.differential_base_guid 按文件逐一确定差异基准。

请参阅

概念

通过备份和还原来复制数据库
计划和执行还原顺序(完整恢复模式)
日志序列号简介
日志序列号和还原计划
差异备份的基准

其他资源

实现 SQL Server 数据库还原方案

帮助和信息

获取 SQL Server 2005 帮助