AskOverflow.Dev

AskOverflow.Dev Logo AskOverflow.Dev Logo

AskOverflow.Dev Navigation

  • 主页
  • 系统&网络
  • Ubuntu
  • Unix
  • DBA
  • Computer
  • Coding
  • LangChain

Mobile menu

Close
  • 主页
  • 系统&网络
    • 最新
    • 热门
    • 标签
  • Ubuntu
    • 最新
    • 热门
    • 标签
  • Unix
    • 最新
    • 标签
  • DBA
    • 最新
    • 标签
  • Computer
    • 最新
    • 标签
  • Coding
    • 最新
    • 标签
主页 / dba / 问题 / 217831
Accepted
JW-OP
JW-OP
Asked: 2018-09-18 10:57:38 +0800 CST2018-09-18 10:57:38 +0800 CST 2018-09-18 10:57:38 +0800 CST

带有持久化计算的 CLR 原始数据的表,标记为 has_unchecked_assembly_data = 1,但 DBCC CHECKTABLE 不会取消设置相同的标志

  • 772

我们有一个包含列的 OrderLines 表:

Quantity int not null
QtyCancelled int not null
QtyBackorder int not null
QtyPicking int not null
QtyPacking int not null
QtyShiped int not null

计算列和持久列 FulfillmentStatusId 为:

dbo.clr_GetFulfillmentStatusByLineQuantities(Quantity, QtyCancelled, QtyBackorder, QtyPicking, QtyPacking, QtyShiped)

“clr_GetFulfillmentStatusByLineQuantities”,当然,通过标量函数映射到数据库中的 ASSEMBLY,相关方法 (C#) 标记为:

[SqlFunction(DataAccess = None, IsDeterministic = true, IsPrecise = true, SystemDataAccess = None)]

关于这个问题,我多次针对这个表运行 DBCC CHECKTABLE ,它仍然是 has_unchecked_assembly_data=1。当列首次添加到表中时确实如此,但我相信 DBCC CHECKTABLE 命令在迁移到 SQL 2016 之前成功了。


虽然该表已在 has_unchecked_assembly_data=1 下使用了很长时间,但似乎对该表的功能没有影响。我担心 ALTER ASSEMBLY 在不使用 WITH UNCHECKED DATA 时抛出异常,然后在我确实使用该选项时抛出另一个异常,但似乎“根据 MVID”更新程序集。

对不起,如果我漫无边际,我不会问太多问题而且我主要是潜伏。

不过,请提前致谢!


更新 (20180917T17:34-05:00):感谢 Sean 提出了初步方向。DBCC CHECKTABLE ('OrderLines') WITH EXTENDED_LOGICAL_CHECKS的结果是两行类似于:

Msg 2537, Level 16, State 106, Line 1
Table error: object ID 1486732449, index ID 1, partition ID 72057594403946496, alloc unit ID 72057594422755328 (type In-row data), page (1:1430554), row 5. The record check (valid computed column) failed. The values are 38 and 0.

因此,我对表的主键(即上面指示的索引 ID 1)执行了 REBUILD,这成功了。然而,重新运行DBCC CHECKTABLE('OrderLines') WITH EXTENDED_LOGICAL_CHECKS再次返回类似的错误,只是这次使用不同的分区 ID 和分配单元 ID(正如人们所预料的那样)。

极端的解决方案可能是删除、重新创建并使用标识插入重新填充表,可以这么说,“从轨道上删除站点”,但出于显而易见的原因,这是极端的。

“表的聚集索引中的计算列数据似乎不一致”的正确解决方案是什么?

sql-server sql-clr
  • 1 1 个回答
  • 176 Views

1 个回答

  • Voted
  1. Best Answer
    JW-OP
    2018-09-20T10:12:21+08:002018-09-20T10:12:21+08:00

    OP在这里,回答我自己的(也是第一个)问题!

    在肖恩·加拉迪 (Sean Gallardy) 的帮助下,使用EXTENDED_LOGICAL_CHECKS指出了与持久计算列的数据不一致的地方。我首先尝试重新创建主键(聚集索引),但这实际上并没有解决任何问题(一个极端而奇怪的解决方案)。

    我也尝试使用DBCC CHECKTABLE ('{table}', REPAIR_ALLOW_DATA_LOSS),但再次返回相同的错误。我不相信任何东西都被修复了。

    我的第一个解决方案是删除并重新创建持久计算列。这奏效了。

    但是,考虑到这也有点“极端”(考虑到该表有 1000 万多行,并且因为还有一个针对该列的索引而需要永远这样做),我对更直接的解决方案感到好奇。

    因为只有两行报告了DBCC CHECKTABLE 它们的页面和行引用,所以我调查了DBCC PAGE。精确地使用这个命令得到了实际的行数据/行标识,当我执行驱动计算列的 CLR 方法时,确实存在不一致。

    基本实际和不一致的表格数据:

    OrderLineId  QtyOrd  QtyCancl  QtyBack  QtyPick  QtyPack  QtyShip  FulfillId
        1234567       4        12        0        0        0        0          0
        4567890       4        12        0        0        0        0          0
    

    FulfillId在这种情况下应该是 1(表示已取消),但是这两个表行表示两行都是 0(未完成/未完成)。

    我使用SELECT语句通过 CLR 函数运行实际行数据:

    select
      ol.OrderLineId,
      ol.QtyOrd, ol.QtyCancl, ol.QtyBack, ol.QtyPick, ol.QtyPack, ol.QtyShip,
      ol.FulfillId [CurrentFulfillId],
      CLR(ol.QtyOrd, ol.QtyCancl, ol.QtyBack, ol.QtyPick, ol.QtyPack, ol.QtyShip) [ComputedFulfillId],
    from
      OrderLines [ol]
    where
      ol.OrderLineId in (1234567, 4567890)
    

    这基本上返回了完全相同的信息,ComputedFulfillId也解析为 0(打开)。因此,我直接在 .Net 控制台应用程序中重新测试了 CLR 代码,并给出了应该在 SQL 调用中传递的显式值,结果是预期值 1(已取消)。

    我修改了SELECT语句以包括使用显式常量值而不是来自可疑行的值对 CLR 方法的调用:

    SELECT ..., CLR(4, 12, 0, 0, 0, 0) [ForcedFulfillId] FROM OrderLines [ol] ...
    

    该ForcedFulfillId列包含正确的值 1。

    使用 DBCC PAGE 查找确切的行标识并更新有问题的行会强制重新计算计算列数据。一个决赛DBCC CHECKTABLE没有返回任何错误,一切都很好。

    因此,与其删除并重新创建整个计算列,不如使用DBCC PAGE来自的信息DBCC CHECKTABLE({table}) WITH EXTENDED_LOGICAL_CHECKS来修复导致错误的原始“has_unchecked_assembly_data=1”问题ALTER ASSEMBLY。

    呼

    抱歉冗长的解释 - 想确保我为下一个可怜的灵魂记录了我的旅行。

    • 7

相关问题

  • SQL Server - 使用聚集索引时如何存储数据页

  • 我需要为每种类型的查询使用单独的索引,还是一个多列索引可以工作?

  • 什么时候应该使用唯一约束而不是唯一索引?

  • 死锁的主要原因是什么,可以预防吗?

  • 如何确定是否需要或需要索引

Sidebar

Stats

  • 问题 205573
  • 回答 270741
  • 最佳答案 135370
  • 用户 68524
  • 热门
  • 回答
  • Marko Smith

    连接到 PostgreSQL 服务器:致命:主机没有 pg_hba.conf 条目

    • 12 个回答
  • Marko Smith

    如何让sqlplus的输出出现在一行中?

    • 3 个回答
  • Marko Smith

    选择具有最大日期或最晚日期的日期

    • 3 个回答
  • Marko Smith

    如何列出 PostgreSQL 中的所有模式?

    • 4 个回答
  • Marko Smith

    列出指定表的所有列

    • 5 个回答
  • Marko Smith

    如何在不修改我自己的 tnsnames.ora 的情况下使用 sqlplus 连接到位于另一台主机上的 Oracle 数据库

    • 4 个回答
  • Marko Smith

    你如何mysqldump特定的表?

    • 4 个回答
  • Marko Smith

    使用 psql 列出数据库权限

    • 10 个回答
  • Marko Smith

    如何从 PostgreSQL 中的选择查询中将值插入表中?

    • 4 个回答
  • Marko Smith

    如何使用 psql 列出所有数据库和表?

    • 7 个回答
  • Martin Hope
    Jin 连接到 PostgreSQL 服务器:致命:主机没有 pg_hba.conf 条目 2014-12-02 02:54:58 +0800 CST
  • Martin Hope
    Stéphane 如何列出 PostgreSQL 中的所有模式? 2013-04-16 11:19:16 +0800 CST
  • Martin Hope
    Mike Walsh 为什么事务日志不断增长或空间不足? 2012-12-05 18:11:22 +0800 CST
  • Martin Hope
    Stephane Rolland 列出指定表的所有列 2012-08-14 04:44:44 +0800 CST
  • Martin Hope
    haxney MySQL 能否合理地对数十亿行执行查询? 2012-07-03 11:36:13 +0800 CST
  • Martin Hope
    qazwsx 如何监控大型 .sql 文件的导入进度? 2012-05-03 08:54:41 +0800 CST
  • Martin Hope
    markdorison 你如何mysqldump特定的表? 2011-12-17 12:39:37 +0800 CST
  • Martin Hope
    Jonas 如何使用 psql 对 SQL 查询进行计时? 2011-06-04 02:22:54 +0800 CST
  • Martin Hope
    Jonas 如何从 PostgreSQL 中的选择查询中将值插入表中? 2011-05-28 00:33:05 +0800 CST
  • Martin Hope
    Jonas 如何使用 psql 列出所有数据库和表? 2011-02-18 00:45:49 +0800 CST

热门标签

sql-server mysql postgresql sql-server-2014 sql-server-2016 oracle sql-server-2008 database-design query-performance sql-server-2017

Explore

  • 主页
  • 问题
    • 最新
    • 热门
  • 标签
  • 帮助

Footer

AskOverflow.Dev

关于我们

  • 关于我们
  • 联系我们

Legal Stuff

  • Privacy Policy

Language

  • Pt
  • Server
  • Unix

© 2023 AskOverflow.DEV All Rights Reserve