【问题标题】:How to execute Entity Framework SQLQuery stored procedure with return value parameter?如何使用返回值参数执行实体框架 SQLQuery 存储过程?
【发布时间】:2016-01-19 12:19:21
【问题描述】:

我正在尝试执行并使用来自存储过程的返回值,该存储过程具有状态代码的返回参数。

这是存储过程:

DECLARE @RetVal int;
DECLARE @CustPK int;

BEGIN
    SET @RetVal = 0;
    SET NOCOUNT ON;

    SET @CustPK = (SELECT CustPK FROM tCustomer WHERE WebCustomerId = @WebCustomerId);

    -- Insert statements for procedure here
    INSERT INTO tOrder(CustPK, WebOrderId, TxCode,DelCompany, DelContact, DelAddress1, DelAddress2, DelCity, DelPostcode, DelPhone, WhiteLabel, ServiceLevelPK, DeliveryCharge, ProductionSpeed, Paid, DateOrdered, [IP Contact], vc, ProductionTIME, ProductionCharge, VDiscountExVAT, VDiscountVAT,QuoteName,[Cost Centre Reference], [Client Reference], MethodOfTransport) 
    VALUES(@CustPK, @WebOrderId, @TxCode, @DelCompany, @DelContact, @DelAddress1, @DelAddress2, @DelCity, @DelPostcode, @DelPhone, @WhiteLabel, @DeliveryType, @DeliveryCharge, @ProductionSpeed, 1, @DateOrdered, 'NEW', @Voucher, @ProductionSpeed, @ProductionCharge, @VoucherDiscount, @VoucherVAT, @PersonalReference, @CostCentreReference, @ClientReference, @MethodOfTransport)

IF @@ERROR = 0
BEGIN
    SET @RetVal = 1
END

RETURN @RetVal

此存储过程是旧的,无法更改。我正在尝试在我的应用程序中使用Retval。我正在使用实体框架的Database.SqlQuery() 来执行这个存储过程。

我正在创建 SqlParameter 的列表,然后调用 toArray() 以便 EF 读取它们。真的是正常的东西。

这是我的 EF 代码:

    public string PlaceOrder(IPOPPlaceOrderRequest order)
    {
        try
        {
            string storedProcedure = BuildSQLExecutionString<IPOPPlaceOrderRequest>(order, "Web_NewOrder");
            //storedProcedure = storedProcedure + ", @RetVal";
            List<SqlParameter> parameters = BuildSQLParameters<IPOPPlaceOrderRequest>(order);
            var retVal = new SqlParameter("RetVal", System.Data.SqlDbType.Int) { Direction = System.Data.ParameterDirection.Output };
            parameters.Add(retVal);
            var test = tOrderRepository.RunSqlStoredProcedureSingle<IPOPPlaceOrderRequest>(storedProcedure, parameters.ToArray());
            return "";
        }
        catch (Exception ex)
        {
            throw ex;
        }
    }

这里是RunSqlStoredProcedureSingle()

return unitOfWork.DataContext.Database.SqlQuery<T>(sql, parameters.ToArray()).FirstOrDefault();

这会运行,但 retVal 的值从未设置为任何值。我对此感到茫然。

我尝试在存储过程字符串中使用@RetVal,最后有和没有 OUT。

我也尝试过在SqlParameter 对象的参数名称中使用和不使用@。

这两种构建方法都只是使用反射来根据传递给方法的对象的名称和值来构建字符串和列表,如果需要,我也会提供此代码。

【问题讨论】:

  • 本例中的存储过程非常简单。你真的需要使用它还是可以只使用实体来做同样的事情?实体将在运行插入命令时返回 ID,这反过来会告诉您它是否出错。
  • 有人告诉我我需要使用存储过程。它做了一些与问题无关的其他事情,所以我没有包括它。
  • 你见过这个:stackoverflow.com/questions/14735477/… 吗?您的版本和那个版本之间的区别在于,为了获取参数,对存储过程的调用被包装在 SQL 片段中。
  • 多亏了这条评论,我现在可以正常工作了,我已经看到了这个,但再次回顾它给了我一些新的见解。您想提出问题吗?我可以将其标记为正确答案。

标签: c# sql-server entity-framework stored-procedures


【解决方案1】:

我通过从@galenus 提供的comment 修改对存储过程的调用来完成这项工作

        public string PlaceOrder(IPOPPlaceOrderRequest order)
    {
        try
        {
            string storedProcedure = BuildSQLExecutionString<IPOPPlaceOrderRequest>(order, "exec @RetVal = Web_NewOrder");
            List<SqlParameter> parameters = BuildSQLParameters<IPOPPlaceOrderRequest>(order);
            var retVal = new SqlParameter("@RetVal", System.Data.SqlDbType.Int) { Direction = System.Data.ParameterDirection.Output, DbType = System.Data.DbType.Int32};
            parameters.Add(retVal);
            return tOrderRepository.RunSqlStoredProcedureSingle<object>(storedProcedure, parameters.ToArray());
        }
        catch (Exception ex)
        {
            throw ex;
        }
    }

通过在storedProcedure 字符串中添加返回参数的声明,它现在返回正确的值。

这是我从中获得此信息的问题和答案:Get return value from stored procedure

【讨论】:

  • 为什么使用ParameterDirection.Output而不是ParameterDirection.ReturnValue
猜你喜欢
  • 1970-01-01
  • 2012-05-07
  • 1970-01-01
  • 2013-10-31
  • 1970-01-01
  • 2011-12-30
  • 2014-03-30
  • 1970-01-01
相关资源
最近更新 更多