Sql server 在SQLServer2008中通过更改跟踪检测表截断

Sql server 在SQLServer2008中通过更改跟踪检测表截断,sql-server,sql-server-2008,Sql Server,Sql Server 2008,在以下场景中,我无法通过SQL Server 2008中的更改跟踪检测表截断: 假设CHANGE\u TRACKING\u CURRENT\u VERSION=10,我们正在为表1启用变更跟踪 当前版本=10,最小有效版本(表1)=10 我们正在添加一个新记录-现在我们有:当前版本=11,最小有效版本(表1)=10 我们的客户端应用程序正在请求更改:获取自第10版以来的所有更改,假设MIN_VALID_VERSION(table1)>=10-此处一切正常,并且我们的应用程序收到插入通知并记住当前

在以下场景中,我无法通过SQL Server 2008中的更改跟踪检测表截断:

假设CHANGE\u TRACKING\u CURRENT\u VERSION=10,我们正在为表1启用变更跟踪

  • 当前版本=10,最小有效版本(表1)=10
  • 我们正在添加一个新记录-现在我们有:当前版本=11,最小有效版本(表1)=10
  • 我们的客户端应用程序正在请求更改:获取自第10版以来的所有更改,假设MIN_VALID_VERSION(table1)>=10-此处一切正常,并且我们的应用程序收到插入通知并记住当前版本,现在是11
  • 我们正在截断一个表-现在我们有:CURRENT\u VERSION=11,MIN\u VALID\u VERSION(table1)=11
  • 我们的应用程序要求自第11版以来的所有更改-没有更改,但MIN_VALID_版本(表1)不高于我们要求的版本(11)。我们的应用程序错过了整个表截断

  • 我认为正确的行为不仅应该将MIN_VALID_VERSION设置为CURRENT_VERSION,还应该在执行此操作之前增加CURRENT_VERSION。但是SQL Server没有增加当前的\u版本-因此我的问题是-如何检测表截断?

    如评论中所述,Microsoft SQL Server中的更改跟踪不会检测到截断表

    截断表可以在发生更改的表上执行 已启用跟踪。但是,该操作删除的行 不跟踪,并且更新最低有效版本。当 应用程序检查其版本,该检查指示版本 太旧,需要重新初始化。这和 正在禁用更改跟踪,然后为表重新启用

    您也无法检测到:

    TRUNCATE TABLE无法激活触发器,因为该操作无法激活触发器 不记录单个行的删除


    正如在注释中提到的,使用DELETE代替将跟踪更改,并且在应用程序代码中应该使用DELETE而不是TRUNCATE。(TRUNCATE TABLE还有其他副作用,比如重置标识列。)

    好吧,作为一种黑客,您可以比较alloc单元目录视图前后的b树根页面id。TRUNCATE分配一个新的树。我记得,更改数据捕获使用日志,而
    TRUNCATE TABLE
    根据设计不记录日志。如果需要记录截断,请改用
    DELETE
    。更改跟踪功能会在重置最小有效版本时检测到截断。问题是,这种修改不足以识别截断(或者实际上需要重新加载完整表,即在这种情况下进行清理)。SQL中有3组指令:DML、DDL和DCL。DML是Insert、delete和Update,这些指令将日志存储在数据库日志中(这就是为什么您可以提交或回滚它们),但Truncate是DDL,数据定义语言,DDL(如Create、Alter等)不存储日志,所以您无法回滚或跟踪日志。我用两个Truncate和一个插入来解决这个问题。