MissingSchemaAction.AddWithKey 究竟做了啥?

Posted

技术标签:

【中文标题】MissingSchemaAction.AddWithKey 究竟做了啥?【英文标题】:What does MissingSchemaAction.AddWithKey really do?MissingSchemaAction.AddWithKey 究竟做了什么? 【发布时间】:2015-11-10 23:20:43 【问题描述】:

SqlDataAdapter.MissingSchemaAction 的默认值为MissingSchemaAction.Add,但是当我指定AddWithKey 时,我无法理解它的真正作用是什么?

System.Data.SqlClient.SqlDataAdapter da = new System.Data.SqlClient.SqlDataAdapter();
da.MissingSchemaAction = MissingSchemaAction.AddWithKey;

DataSet ds = new DataSet();
da.Fill(ds, "mytable");

什么时候使用AddWithKey 有用?

【问题讨论】:

它似乎做了一些不同于文档中解释的事情。如果我使用 MissingSchemaAction.Add(默认值)填充数据集并查看字符串列(System.Data.DataColumn)的 MaxLength,它会返回 -1。使用 MissingSchemaAction.AddWithKey 它返回列的数据库定义!!我将它与 SQL 和 Oracle 驱动程序进行了比较,两者都做同样的事情。这令人困惑,因为根本没有关于此行为的信息:-( @Raul 我的测试机器正好相反:Add 将返回正确的 MaxLength 值,而 AddWithKey 将返回 -1s。您是否找到了原因,或者找到了解决这种行为的更好方法? 【参考方案1】:

Documentation here 说,它“添加必要的列和主键信息以完成架构”

它将AddWithKey 的主要功能声明为:“这确保与现有记录匹配的传入记录被更新而不是追加。”

一点逆向工程揭示了以下内容:

当您调用DbDataAdapter.Fill(DataSet, string) 时,它会执行DbCommand.ExecuteReader 并将CommandBehavior 设置为SequentialAccess

如果您指定MissingSchemaAction = MissingSchemaAction.AddWithKey;,则会将CommandBehavior.KeyInfo 添加到行为中。

这会导致内部调用的 DbCommand.ExecuteReader 在您的查询之上添加以下内容:

SET NO_BROWSETABLE ON;

这是微软的documented here(如下)

浏览模式允许您扫描 SQL Server 表中的行并 一次更新一行中的数据。访问 SQL 在浏览模式下你的应用程序中的服务器表,你必须使用一个 以下两个选项之一:

用于从 SQL 访问数据的 SELECT 语句 服务器表必须以关键字 FOR BROWSE 结尾。当你打开 FOR BROWSE 选项使用浏览模式,临时表是 已创建。

您必须运行以下 Transact-SQL 语句才能打开 使用 NO_BROWSETABLE 选项浏览模式:

SET NO_BROWSETABLE ON

当您打开 NO_BROWSETABLE 选项时,所有 SELECT 语句 就像在语句中附加了 FOR BROWSE 选项一样。 但是,NO_BROWSETABLE 选项不会创建临时 FOR BROWSE 选项通常用于发送结果的表 到您的应用程序。

【讨论】:

以上是关于MissingSchemaAction.AddWithKey 究竟做了啥?的主要内容,如果未能解决你的问题,请参考以下文章