.NET Core中使用ADO.NET调用存储过程时SqlParameter无法识别的问题
在.NET Core中使用ADO.NET调用带参数存储过程的正确方式
解决SqlParameter找不到的核心问题
.NET Core环境下,官方已弃用System.Data.SqlClient,推荐使用Microsoft.Data.SqlClient作为SQL Server的ADO.NET驱动。你需要:
- 卸载NuGet包
System.Data.SqlClient - 安装NuGet包
Microsoft.Data.SqlClient - 替换代码中的命名空间引用为
using Microsoft.Data.SqlClient;
几种传递参数到存储过程的方法
方法1:显式创建SqlParameter对象(推荐,类型可控)
修正你的代码,同时注意当CommandType设为StoredProcedure时,CommandText只需填写存储过程名称,无需拼接参数占位符:
using Microsoft.Data.SqlClient; public async Task<List<SynchStockDto>> GetStockForSync(int locationBinId, DateTime lastSyncDate) { await EnsureConnectionOpenAsync(); var command = GetConnection().CreateCommand(); command.CommandText = "sp_GetStockForSync"; command.CommandType = CommandType.StoredProcedure; command.Transaction = GetActiveTransaction(); // 显式创建SqlParameter,可指定参数类型避免隐式转换问题 command.Parameters.Add(new SqlParameter("@LocationBinId", SqlDbType.Int) { Value = locationBinId }); command.Parameters.Add(new SqlParameter("@LastSyncDate", SqlDbType.DateTime) { Value = lastSyncDate }); using (var dataReader = await command.ExecuteReaderAsync()) { var result = new List<SynchStockDto>(); while (dataReader.Read()) { var stockItem = new SynchStockDto { // 填充DTO字段,示例: // LocationBinId = dataReader.GetInt32(dataReader.GetOrdinal("LocationBinId")), // LastUpdateTime = dataReader.GetDateTime(dataReader.GetOrdinal("LastUpdateTime")) }; result.Add(stockItem); } return result; } }
方法2:使用AddWithValue简化写法
如果参数类型简单,可使用AddWithValue快速添加参数:
// 替代显式构造SqlParameter的写法 command.Parameters.AddWithValue("@LocationBinId", locationBinId); command.Parameters.AddWithValue("@LastSyncDate", lastSyncDate);
注意:AddWithValue会自动推断参数类型,对于日期、小数等类型可能存在隐式转换风险,复杂场景建议用方法1。
方法3:批量添加参数(适合多参数场景)
使用AddRange一次性添加多个参数:
var parameters = new SqlParameter[] { new SqlParameter("@LocationBinId", locationBinId), new SqlParameter("@LastSyncDate", lastSyncDate) }; command.Parameters.AddRange(parameters);
额外注意事项
- 确保
GetConnection()返回的是Microsoft.Data.SqlClient.SqlConnection实例,而非旧版的System.Data.SqlClient.SqlConnection。 - 存储过程的参数名需与代码中定义的参数名完全匹配(SQL Server默认区分大小写取决于数据库配置)。
内容的提问来源于stack exchange,提问作者Stanton Roux
相关产品推荐
相关产品推荐

