更改数据捕获(CDC)清理作业一次只能删除一些记录

时间:2014-08-13 14:34:50

标签: sql-server ssis jobs cdc change-data-capture

我是SQL Server的初学者。对于一个项目,我需要打开CDC。我将cdc数据复制到另一个(存档)数据库,然后立即清理CDC表。因此,保留时间不需要很高,我只需将它放在1分钟,当清理作业运行时(保留时间已经完成),它似乎只删除了一些记录(最旧的记录)。为什么不删除所有内容?有时它根本不删除任何东西。几次运行作业后,其他记录将被删除。我发现这很奇怪,因为保留时间早已过去。

我将保留时间设置为1分钟(我实际上想要0但不可能)并且没有更改阈值(= 5000)。我禁用了计划,因为我希望在将CDC记录复制到我的存档数据库后立即运行清理作业,而不是特别在某个时间。

我对这个想法的逻辑是,例如下午会有更新。将CDC记录复制到存档数据库的任务应该在凌晨2:00运行,在此任务之后调用清理作业。因此,由于最短保留时间,清理作业应删除所有CDC记录。毕竟保留时间过去了吗?

我只是试着看看当我在工作中再次设置一个时间表时发生了什么,就像CDC的使用方式一般。经过一段时间后,我检查了CDC表,结果发现它也只删除了最旧的记录。那么我做错了什么?

我做了一个解决方法,我完成了一项新任务,删除了CDC表中的所有记录(并禁用了整个默认的CDC清理作业)。这样做效果更好,因为它删除了所有内容,但它困扰我,因为我想使用原始的清理工作,我认为它应该能够以我想要的方式工作。

谢谢,

1 个答案:

答案 0 :(得分:0)

我不会担心表格中的内容,而是使用为每个捕获实例创建的辅助函数。具体来说,cdc.fn_cdc_get_all_changes_和cdc.fn_cdc_get_net_changes_。我使用wuth的典型工作流程如下所示(对所有捕获实例都这样做)。首先,您需要一个表来保持处理状态。我用的是:

create table dbo.ProcessingStatus (
   CaptureInstance sysname,
   LSN numeric(25,0),
   IsProcessed bit
)
create unique index [UQ_ProcessingStatus] 
   on dbo.ProcessingStatus (CaptureInstance) 
   where IsProcessed = 0
  1. 使用fn_cdc_get_max_lsn获取当前的最大日志序列号(LSN)。
  2. 获取最后处理的LSN并使用fn_cdc_increment_lsn递增它。如果您没有(即这是您第一次处理),请对此实例使用fn_cdc_get_min_lsn并使用它(但不要递增它!)。记录您在表中使用的任何LSN,设置IsProcessed = 0。
  3. 从cdc.fn_cdc_get ...中选择哪个函数对您的场景有意义并处理结果,但是您将要处理它们。
  4. 此次运行更新IsProcessed = 1。
  5. 至于监控原始问题,只需确保捕获表中的数据通常在保留期内。也就是说,如果你把它设置为2天,我甚至不会想到它是一个问题,直到它超过4天(假设你的清理工作的调用安排在每小时一样)。当你使用上述方案处理时,你不必担心太多"数据在那里;你总是处理一个特定的间隔,而不是"一切"。