我正在尝试调用一个接受表值参数的存储过程。我知道Entity Framework尚不直接支持此功能,但是据我了解,您可以使用的ExecuteStoreQuery命令来实现ObjectContext。我有一个通用实体框架存储库,其中有以下ExecuteStoredProcedure方法:
ExecuteStoreQuery
ObjectContext
ExecuteStoredProcedure
public IEnumerable<T> ExecuteStoredProcedure<T>(string procedureName, params object[] parameters) { StringBuilder command = new StringBuilder(); command.Append("EXEC "); command.Append(procedureName); command.Append(" "); // Add a placeholder for each parameter passed in for (int i = 0; i < parameters.Length; i++) { if (i > 0) command.Append(","); command.Append("{" + i + "}"); } return this.context.ExecuteStoreQuery<T>(command.ToString(), parameters); }
命令字符串最终如下所示:
EXEC someStoredProcedureName {0},{1},{2},{3},{4},{5},{6},{7}
我试图在接受表值参数的存储过程中运行此方法,但它会中断。我在这里读到,参数必须是类型SqlParameter,而表值参数需要将其SqlDbType设置为Structured。所以我这样做了,并得到一个错误说明:
SqlParameter
SqlDbType
Structured
The table type parameter p6 must have a valid type name
因此,我将SqlParameter.TypeName设置为在数据库上创建的用户定义类型的名称,然后在运行查询时收到以下真正有用的错误:
Incorrect syntax near '0'.
如果我恢复到ADO.NET并执行数据读取器,则可以使查询运行,但是我希望可以使用数据上下文使它正常工作。
有没有办法使用传递表值参数ExecuteStoreQuery?另外,我实际上使用的是Entity Framework Code First,并将强制转换DbContext为ObjectContext以获得ExecuteStoreQuery可用的方法。这是否有必要,或者我也可以针对DbContext?
DbContext
更新
我在Nuget软件包上添加了对此的支持-https: //github.com/Fodsuk/EntityFrameworkExtras#nuget (EF4,EF5,EF6)
查看GitHub存储库以获取代码示例。
稍有疑问,但是对于尝试将用户定义的表传递到存储过程中的人来说,它仍然有用。在研究了Nick的示例和其他Stackoverflow帖子之后,我想到了:
class Program { static void Main(string[] args) { var entities = new NewBusinessEntities(); var dt = new DataTable(); dt.Columns.Add("WarningCode"); dt.Columns.Add("StatusID"); dt.Columns.Add("DecisionID"); dt.Columns.Add("Criticality"); dt.Rows.Add("EO01", 9, 4, 0); dt.Rows.Add("EO00", 9, 4, 0); dt.Rows.Add("EO02", 9, 4, 0); var caseId = new SqlParameter("caseid", SqlDbType.Int); caseId.Value = 1; var userId = new SqlParameter("userid", SqlDbType.UniqueIdentifier); userId.Value = Guid.Parse("846454D9-DE72-4EF4-ABE2-16EC3710EA0F"); var warnings = new SqlParameter("warnings", SqlDbType.Structured); warnings.Value= dt; warnings.TypeName = "dbo.udt_Warnings"; entities.ExecuteStoredProcedure("usp_RaiseWarnings_rs", userId, warnings, caseId); } } public static class ObjectContextExt { public static void ExecuteStoredProcedure(this ObjectContext context, string storedProcName, params object[] parameters) { string command = "EXEC " + storedProcName + " @caseid, @userid, @warnings"; context.ExecuteStoreCommand(command, parameters); } }
存储过程如下所示:
ALTER PROCEDURE [dbo].[usp_RaiseWarnings_rs] (@CaseID int, @UserID uniqueidentifier = '846454D9-DE72-4EF4-ABE2-16EC3710EA0F', --Admin @Warnings dbo.udt_Warnings READONLY ) AS
用户定义的表如下所示:
CREATE TYPE [dbo].[udt_Warnings] AS TABLE( [WarningCode] [nvarchar](5) NULL, [StatusID] [int] NULL, [DecisionID] [int] NULL, [Criticality] [int] NULL DEFAULT ((0)) )
我发现的约束包括:
ExecuteStoreCommand