变更数据捕获和其他功能
本文介绍以下功能如何与 SQL Server 和 Azure SQL 托管实例的变更数据捕获进行交互。 有关 Azure SQL 数据库,请参阅 CDC 与 Azure SQL 数据库。
更改跟踪
可以对同一数据库启用变更数据捕获和 更改跟踪 。 没有特殊的注意事项。 有关详细信息,请参阅使用更改跟踪。
数据库镜像
可以对启用变更数据捕获的数据库进行镜像。 为确保捕获和清除操作可在故障转移之后自动发生,请执行以下步骤:
确保在新的主体服务器实例上运行 SQL Server 代理。
在新的主体数据库(以前的镜像数据库)上创建捕获作业和清除作业。 若要创建作业,请使用 sp_cdc_add_job 存储过程。
若要查看清除作业或捕获作业的当前配置,请在新的主体服务器实例上使用 sys.sp_cdc_help_jobs 存储过程。 对于给定数据库,捕获作业名为 cdc.database_name_capture,清除作业名为 cdc.database_name_cleanup,其中 database_name 为数据库的名称。
若要更改作业的配置,请使用 sys.sp_cdc_change_job 存储过程。
有关数据库镜像的信息,请参阅数据库镜像 (SQL Server)。
事务复制
变更数据捕获和事务复制可以共存于同一数据库中,但在启用这两项功能后,更改表的填充处理方式将发生变化。 变更数据捕获和事务复制始终使用相同的过程 sp_replcmds 从事务日志读取更改。 当单独启用变更数据捕获时,SQL Server 代理作业会调用 sp_replcmds。 在同一数据库中启用这两项功能时,日志读取器代理会调用 sp_replcmds。 此代理将填充更改表和分发数据库表。 有关详细信息,请参阅 Replication Log Reader Agent。
假设为 AdventureWorks2022
数据库启用了变更数据捕获,并为捕获启用了两个表。 为了填充更改表,捕获作业将调用 sp_replcmds。 此外,还为该数据库启用了事务复制,并会创建发布。 此时,将为该数据库创建日志读取器代理,并删除捕获作业。 日志读取器代理继续从提交到更改表的最后一个日志序列号开始扫描日志。 这样将确保更改表中的数据一致性。 如果在此数据库中禁用事务复制,则会删除日志读取器代理,并重新创建捕获作业。
注意
当日志读取器代理同时用于变更数据捕获和事务复制时,复制的更改将首先写入分发数据库。 然后,捕获的更改会写入更改表。 两项操作会一起提交。 如果在写入分发数据库时有任何滞后时间,则在更改显示在更改表中之前,将有对应的滞后时间。
在启用了变更数据捕获的情况下,无法使用事务复制的 proc exec 选项。
数据库还原或附加
SQL Server 使用以下逻辑确定还原或附加数据库后变更数据捕获是否继续保持启用状态:
如果数据库以同一数据库名称还原到同一服务器,变更数据捕获将保持启用状态。
如果数据库还原到其他服务器,默认情况下将禁用变更数据捕获,并删除所有相关的元数据。
若要保留变更数据捕获,请在还原数据库时使用 KEEP_CDC 选项。 有关此选项的详细信息,请参阅 RESTORE。
如果数据库在分离后附加到同一服务器或其他服务器,变更数据捕获将保持启用状态。
如果数据库是使用 KEEP_CDC 选项附加或还原到除标准版、企业版或 SQL 托管实例以外的任何版本,操作会遭阻止,因为变更数据捕获需要 SQL 标准版、企业版或 SQL 托管实例版本。 将显示错误消息 934:
SQL Server cannot load database '%.*ls' because change data capture is enabled. The currently installed edition of SQL Server does not support change data capture. Either restore database without KEEP_CDC option, or upgrade the instance to one that supports change data capture.
可以使用 sys.sp_cdc_disable_db 从还原或附加的数据库中删除变更数据捕获。
在 Azure SQL 托管实例上还原数据库后,CDC 将仍然保持启用状态,但你必须确保已添加并正在运行扫描和清理作业。 可运行 sys.sp_cdc_add_job 来手动添加这些作业。
包含的数据库
包含的数据库中不支持变更数据捕获。
可用性组
使用 Always On 可用性组时,应在次要副本上更改枚举以减少主要副本的磁盘负载。
列存储索引
不能对具有聚集列存储索引的表启用变更数据捕获。 从 SQL Server 2016 开始,可以对具有非聚集列存储索引的表启用此功能。
计算列
CDC 不支持计算列的值,即使计算列定义为持久化状态也是如此。 捕获实例中包含的计算列的值始终为 NULL
。 此行为是预期行为,不是 bug。
Linux
从 CU18 开始的 Linux 上的 SQL Server 2017 和 Linux 上的 SQL Server 2019 都支持 CDC。