Sql server 使用WebApi EntityFrameWorkCore 1.1进行的存储过程调用获取和对象而不是整数结果

Sql server 使用WebApi EntityFrameWorkCore 1.1进行的存储过程调用获取和对象而不是整数结果,sql-server,stored-procedures,asp.net-web-api,asp.net-core,Sql Server,Stored Procedures,Asp.net Web Api,Asp.net Core,使用WebApi EntityFrameWorkCore 1.1进行的存储过程调用获取和对象而不是整数结果 我使用以下用户定义的过程调用数据库中的计算数据,并使用2个参数返回一个整数(Count(*) 要调用该过程的存储库: public async Task GetCansTotals(int hospitalId) { using (appContext) { var hospitalid =

使用WebApi EntityFrameWorkCore 1.1进行的存储过程调用获取和对象而不是整数结果

我使用以下用户定义的过程调用数据库中的计算数据,并使用2个参数返回一个整数(Count(*)

要调用该过程的存储库:

 public async Task GetCansTotals(int hospitalId)
        {
            using (appContext)
            {
                var hospitalid = new SqlParameter("@hospitalId", 1);
                var cans = appContext.Cans.FromSql("Exec GetCansTotals @hospitalId", hospitalId);
            }
        }
以及控制器:

[HttpGet("byParams")]
        public IActionResult GetCanTotal(int hospitalId)
        {
            var res = _unitOfWork.Cans.GetCansTotals(hospitalId);
            return Ok(res);
        }
向邮递员传递请求时:

我得到的是一个对象,而不是COUNT(*)的结果


您能帮忙吗?

您的代码有几个问题。以下是你能做的-

  • 您将从存储过程返回一个标量值(count),并通过FromSql方法在DbSet上调用它。当存储过程返回映射到“Can”类型属性(或“Cans”属性在DbSet中返回的任何类型)的结果集时,应使用此方法。这是行不通的
  • 似乎要执行返回标量值的存储过程,仍然需要使用普通的ADO.NET。您可以在DbContext或存储库中添加扩展方法来完成此操作。请检查此答案以了解更多详细信息-
  • 也可以不使用存储过程而使用LINQ返回计数。 还将方法的返回类型更改为Task并使其异步

    public async Task<int> GetCansTotals(int hospitalId)
    {
        using (appContext)
        {
            return appContext.Cans.CountAsync(c => c.HospitalId == hospitalId);
        }
    }
    
    public异步任务GetCansTotals(int hospitalId)
    {
    使用(appContext)
    {
    返回appContext.Cans.CountAsync(c=>c.HospitalId==HospitalId);
    }
    }
    
  • 考虑将控制器方法也标记为异步,并使用wait调用存储库方法。您还需要将控制器方法的返回类型更改为Task

    [HttpGet("byParams")]
    public async Task<IActionResult> GetCanTotal(int hospitalId)
    {
        var res = await this._unitOfWork.GetCansTotals(hostpitalId);
        return Ok(res);
    }
    
    [HttpGet(“byParams”)]
    公共异步任务GetCanTotal(int hospitalId)
    {
    var res=等待此消息。_unitOfWork.GetCansTotals(hostpitalId);
    返回Ok(res);
    }
    

  • 您的代码有几个问题。以下是你能做的-

  • 您将从存储过程返回一个标量值(count),并通过FromSql方法在DbSet上调用它。当存储过程返回映射到“Can”类型属性(或“Cans”属性在DbSet中返回的任何类型)的结果集时,应使用此方法。这是行不通的
  • 似乎要执行返回标量值的存储过程,仍然需要使用普通的ADO.NET。您可以在DbContext或存储库中添加扩展方法来完成此操作。请检查此答案以了解更多详细信息-
  • 也可以不使用存储过程而使用LINQ返回计数。 还将方法的返回类型更改为Task并使其异步

    public async Task<int> GetCansTotals(int hospitalId)
    {
        using (appContext)
        {
            return appContext.Cans.CountAsync(c => c.HospitalId == hospitalId);
        }
    }
    
    public异步任务GetCansTotals(int hospitalId)
    {
    使用(appContext)
    {
    返回appContext.Cans.CountAsync(c=>c.HospitalId==HospitalId);
    }
    }
    
  • 考虑将控制器方法也标记为异步,并使用wait调用存储库方法。您还需要将控制器方法的返回类型更改为Task

    [HttpGet("byParams")]
    public async Task<IActionResult> GetCanTotal(int hospitalId)
    {
        var res = await this._unitOfWork.GetCansTotals(hostpitalId);
        return Ok(res);
    }
    
    [HttpGet(“byParams”)]
    公共异步任务GetCanTotal(int hospitalId)
    {
    var res=等待此消息。_unitOfWork.GetCansTotals(hostpitalId);
    返回Ok(res);
    }
    

  • 据我所知,使用ado.net(ICommand和EF所依赖的东西)无法获得存储过程的结果。你能换个sp吗?您是否尝试执行“声明ATMyCount INT;从..中选择ATMyCount=COUNT(*);返回ATMyCount”。然后你也必须改变C#中的呼叫。类似于appContext.Cans.FromSql(“DECLARE ATResult INT;EXEC ATResult=GetCansTotals AThospitalId;RETURN ATResult”)
    GetCansTotals
    返回的是一个
    任务
    ,但您没有将其视为一个
    异步
    函数。您需要在控制器中使用
    async/wait
    您的
    GetCanTotal
    。您调用存储过程的方式,系统将期望它返回Cans类型的数据。据我所知,使用ado.net(ICommand和EF依赖的东西)无法获得存储过程的结果。你能换个sp吗?您是否尝试执行“声明ATMyCount INT;从..中选择ATMyCount=COUNT(*);返回ATMyCount”。然后你也必须改变C#中的呼叫。类似于appContext.Cans.FromSql(“DECLARE ATResult INT;EXEC ATResult=GetCansTotals AThospitalId;RETURN ATResult”)
    GetCansTotals
    返回的是一个
    任务
    ,但您没有将其视为一个
    异步
    函数。在控制器中需要
    async/await
    您的
    GetCanTotal
    。调用存储过程的方式,系统将期望它返回CAN类型的数据。