c# - 使用 ADO,使用 SqlDataAdapter.FillSchema 清除 @ReturnValues 和其他标记为输出的存储过程参数
问题描述
[编辑 - 答案的解释在问题的底部,因为从接受的答案中微妙之处并不完全明显。]
原始问题:
在我做出进一步努力之前,我正在寻找一个快速的“是的,这种方法应该可行”的答案。
设想:
- 我有一个运行查询的简单 SQL Server 存储过程。我还想 (1) 返回一个
varchar(100)
声明为 的参数OUTPUT
,以及 (2) 使用@ReturnValue
来返回一个进一步的(整数)值。 - 我使用该方法从 C# 调用此过程
SqlDatAdapter.DataSet.Fill()
。 - 回到 C# 代码中,我可以访问过程参数,但无法获取其中一个
@ReturnValue
或另一个OUTPUT
参数的值。
我在期待什么?
- 从选择中抓取数据的
SqlDataAdapter
填充过程。这可行,我可以在 C# 中访问这些数据。 - 标记为 的 SQL Server 存储过程参数
OUTPUT
和自动@ReturnValue
参数的值在 C# 中可用。
我看到了什么?
- 数据按预期从查询中返回。
- SQL 命令参数存在于 C# 中,但它们的
.Value
属性为空。
我做了什么研究?
- 大量搜索包含
SqlDataAdapter
和@returnvalue
. 没有显着的阳性结果。 - 仔细阅读了相关的旧 SO 问题
SqlDataAdapter
- 似乎没有什么与我的问题重叠。 - 发布了这个问题。
我需要询问 SO 社区这是否可能。那么 - 是否可以OUTPUT
从与 一起使用的存储过程中收集参数值SqlDatAdapter.DataSet.Fill()
?
如果答案是肯定的并且没有简单的示例,那么我会将我的代码缩减为一个有代表性的案例,并将其发布在这里(希望)用于社区调试。
编辑感谢@NDJ 和提供的示例代码,我能够确认SqlDatAdapter.DataSet.Fill()
不会干扰存储过程的返回值。然后我能够继续发现我的问题是由立即调用引起的SqlDatAdapter.DataSet.FillScheam()
。这会将数据表的元数据传递到一个方便的矩阵中,我们可以从 C# 访问该矩阵,这是我的用例的一部分。
但是,FillSchema() 会清除存储过程参数值。在我的代码中,我试图在调用 FillSchema 后收集存储过程的输出参数值,这就是我目睹的原因。我找不到关于这一点的任何文档。
如果您的代码看起来像这样,它将起作用。
da.Fill(ds);
var returnVal = returnParam.Value; // value as expected
da.FillSchema(ds, SchemaType.Source);
如果您的代码看起来像这样,它将无法正常工作
da.Fill(ds);
da.FillSchema(ds, SchemaType.Source);
var returnVal = returnParam.Value; // value reset by prev line !!!!
解决方案
是的你可以。
Create PROCEDURE TestSP
@test varchar(max) output
AS
BEGIN
select @test = 'abc'
select top 10 * from MyTable
return 4
END
using (SqlConnection connection = new SqlConnection(conString))
{
connection.Open();
SqlCommand cmd = new SqlCommand("TestSP", connection);
cmd.CommandType = CommandType.StoredProcedure;
SqlParameter param = new SqlParameter("@test", SqlDbType.VarChar, -1);
param.Direction = ParameterDirection.Output;
var returnParam = cmd.Parameters.Add("@Return", SqlDbType.Int);
returnParam.Direction = ParameterDirection.ReturnValue;
cmd.Parameters.Add(param);
SqlDataAdapter da = new SqlDataAdapter(cmd);
DataSet ds = new DataSet();
da.Fill(ds);
var returnVal = returnParam.Value; //4
var output = param.Value; // abc
var data = ds.Tables[0].Rows[0][0]; //data from my table
}
推荐阅读
- .net-core - 如何使用 MqttNET 在 azure 函数中使用 PEM 文件
- amazon-web-services - ElasticBeanstalk:无法在 GUI 中将环境类型更改为负载平衡?
- ssl - 我只想用wireshark的dissector功能,需要关闭Qt界面
- javascript - 如何捕获从服务器发送到我的 ws 侦听器的 ping/pong 帧?
- python - pandas.DataFrame.append 正在向 python 中的数据框添加新列
- python - 如何执行断言以验证项目是否在 Python 的字典列表中
- flutter - Flutter App 通过 url lancher 包打开 Linked In App
- go - 将 float 转换为 int 时的 Golang 奇怪行为
- python - 如何使用 Scikit-learn 计算多类问题的特异性
- javascript - 具有多个返回对象的复杂正则表达式可选搜索