数据库镜像会话期间的自动页修复

从 SQL Server 2008 开始,数据库镜像伙伴会通过解决某些阻止读取数据页的错误,自动尝试从镜像数据库上损坏的页中恢复。无法读取页的伙伴会向其他伙伴请求新副本。如果此请求成功,则将以新副本替换不可读的页,这通常会解决该错误。

注意注意

数据库镜像伙伴进行的自动页修复不同于 DBCC 修复。自动页修复会保留所有数据。相反,使用 DBCC REPAIR_ALLOW_DATA_LOSS 选项更正错误可能需要删除某些页(从而会删除数据)。

导致自动页修复尝试的错误类型

数据库镜像自动页修复只尝试修复特定数据文件中的页,此数据文件是指对其执行的操作由于下表中列出的某一错误而失败的数据文件。

错误号

说明

导致自动页修复尝试的实例

823

仅当操作系统对数据执行循环冗余检查 (CRC) 失败时才执行此操作。

ERROR_CRC。此错误的操作系统值为 23。

824

逻辑错误。

逻辑数据错误,例如残缺写或错误的页校验和。

829

页已标记为还原已挂起。

全部。

若要查看最近的 823 CRC 错误和 824 错误,请参阅 msdb 数据库中的 suspect_pages 表。

无法自动修复的页类型

以下控制页类型无法通过数据库镜像修复:

  • 文件头页(页 ID 0)。

  • 页 9(数据库引导页)。

  • 分配页:全局分配映射 (GAM) 页、共享全局分配映射 (SGAM) 页和页可用空间 (PFS) 页。

处理主体数据库中的 I/O 错误

在主体数据库中,仅当节点处于 SYNCHRONIZED 状态且主体服务器仍向镜像服务器发送日志记录时,才会尝试自动页修复。自动页修复尝试中操作的基本顺序如下:

  1. 当主体数据库中的数据页上发生读取错误时,主体服务器将使用相应的错误状态在 suspect_pages 表中插入一行。然后,主体服务器从镜像服务器请求此页的副本。此请求指定当前在刷新日志末尾的页 ID 和 LSN。此页将标记为“还原已挂起”。这将使它在自动页修复尝试期间不可访问。修复尝试期间对此页的访问尝试将失败,并显示错误 829(还原已挂起)。

  2. 收到页请求后,镜像服务器将等待,直到将日志重做到请求中指定的 LSN 处。然后,镜像服务器将尝试访问镜像数据库中的此页。如果可以访问此页,则镜像服务器将此页的副本发送到主体服务器。否则,镜像服务器将向主体服务器返回错误,并且自动页修复失败。

  3. 主体服务器处理包含此页新副本的响应。

  4. 自动页修复尝试修复可疑页后,此页将在 suspect_pages 表中标记为已还原 (event_type = 4)。

  5. 如果此页 I/O 错误导致出现任何延迟的事务,则修复此页后,主体服务器将尝试解决这些事务。

处理镜像数据库中的 I/O 错误

将用以下方式处理在镜像数据库中发生的数据页 I/O 错误。

  1. 如果镜像服务器在其重做日志记录时遇到一个或多个页 I/O 错误,则镜像会话将进入 SUSPENDED 状态。此时,镜像服务器使用相应的错误状态在 suspect_pages 表中插入一行。然后,镜像服务器从主体服务器请求此页的副本。

  2. 主体服务器尝试访问主体数据库中的此页。如果可以访问此页,则主体服务器将此页的副本发送到镜像服务器。

  3. 如果镜像服务器收到它请求的每一页的副本,则镜像服务器将尝试恢复镜像会话。如果自动页修复尝试修复可疑页,此页将在 suspect_pages 表中标记为已还原 (event_type = 5)。

    如果镜像服务器未从主体服务器收到它请求的页,则自动页修复尝试将失败并且镜像会话保持挂起。如果手动恢复镜像会话,则损坏的页将在同步阶段再次导致错误。

开发人员最佳做法

自动页修复是一个运行在后台的异步进程。因此,即使对于镜像数据库,请求不可读的页的数据库操作也会失败,并且不管导致失败的条件是什么均返回错误代码。当开发用于镜像数据库的应用程序时,应截获失败操作的异常。如果 SQL Server 错误代码为 823、824 或 829,则应稍后重试操作。