使用ExecuteSqlCommand调用存储过程(期望未提供的参数)

我正在尝试使用context.Database.ExecuteSqlCommand从EF调用存储过程,因为我的一个参数是一个数据表。

以下是程序的参数:

 ALTER PROCEDURE [mySchema].[myProc] @customerId INT, @indicatorTypeId INT, @indicators [mySchema].[IndicatorList] READONLY, @startDate DATETIME, @endDate DATETIME 

这是调用存储过程的c#代码:

 var indicatorsDt = new DataTable(); indicatorsDt.Columns.Add("Date", typeof(DateTime)); indicatorsDt.Columns.Add("Ongoing", typeof(int)); indicatorsDt.Columns.Add("Success", typeof(int)); indicatorsDt.Columns.Add("Warning", typeof(int)); indicatorsDt.Columns.Add("Error", typeof(int)); indicatorsDt.Columns.Add("Other", typeof(int)); var customerIdParam = new SqlParameter("customerId", SqlDbType.Int); customerIdParam.Value = customerId; var typeIdParam = new SqlParameter("indicatorTypeId", SqlDbType.Int); typeIdParam.Value = typeId; var startDateParam = new SqlParameter("startDate", SqlDbType.DateTime); startDateParam.Value = startDate; var endDateParam = new SqlParameter("endDate", SqlDbType.DateTime); endDateParam.Value = endDate; foreach (var indicator in indicators) { indicatorsDt.Rows.Add(indicator.Date, indicator.Ongoing, indicator.Success, indicator.Warning, indicator.Error, indicator.Other); } var tableParameter = new SqlParameter("indicators", SqlDbType.Structured); tableParameter.Value = indicatorsDt; tableParameter.TypeName = "MySchema.IndicatorList"; context.Database.ExecuteSqlCommand("exec MySchema.MyProc", customerIdParam, typeIdParam, tableParameter, startDateParam, endDateParam); 

如您所见,提供了所有参数,它们都没SqlException值但我总是得到这个SqlException

过程或函数’UpdateIndicators’需要参数’@customerId’,这是未提供的。

我无法弄清楚我错过了什么。 是使用SqlParameter错了吗? 参数在ExecuteSqlCommand中以相同的顺序提供,即使它不重要。

预先感谢。

您缺少正在执行的SQL字符串中的参数。 尝试使用名称前面的“@”创建参数,然后将ExecuteSqlCommand调用更改为:

 context.Database.ExecuteSqlCommand("exec MySchema.MyProc @customerId, @indicatorTypeId, @indicators, @startDate, @endDate", customerIdParam, typeIdParam, tableParameter, startDateParam, endDateParam); 

试试这个:

 var customerIdParam = new SqlParameter("@customerId", SqlDbType.Int); 

这是我目前如何使用参数调用我的存储过程。 用您自己的参数名称/值替换参数名称/值。 请记住,您可能必须按照存储过程中声明的顺序列出参数。

创建一个SqlParameter数组:

 SqlParameter[] parameters = new SqlParameter[] { new SqlParameter("@ParamName1", Value1), new SqlParameter("@ParamName2", Value2), new SqlParameter("@ParamName3", Value3), new SqlParameter("@ParamName4", Value4), new SqlParameter("@ParamName5", Value5) }; 

然后调用您的存储过程:

  _context.Database.ExecuteSqlCommand(DbHelper.GenerateCommandText("SpName", parameters), parameters); 

这是DbHelper代码:

 public class DbHelper { public static string GenerateCommandText(string storedProcedure, SqlParameter[] parameters) { string CommandText = "EXEC {0} {1}"; string[] ParameterNames = new string[parameters.Length]; for (int i = 0; i < parameters.Length; i++) { ParameterNames[i] = parameters[i].ParameterName; } return string.Format(CommandText, storedProcedure, string.Join(",", ParameterNames)); } } 

这有效:

 var bookIdParameter = new SqlParameter(); bookIdParameter.ParameterName = "@BookId"; bookIdParameter.Direction = ParameterDirection.Output; bookIdParameter.SqlDbType = SqlDbType.Int; var authors = context.Database.ExecuteSqlCommand("usp_CreateBook @BookName, @ISBN, @BookId OUT", new SqlParameter("@BookName", "Book"), new SqlParameter("@ISBN", "ISBN"), bookIdParameter);