C# ASP MVC核心3x异步数据库调用-我没有得到什么?

C# ASP MVC核心3x异步数据库调用-我没有得到什么?,c#,sql-server,asp.net-mvc,asp.net-core,async-await,C#,Sql Server,Asp.net Mvc,Asp.net Core,Async Await,我希望有人能给我带来光明,因为在VS中我在一个异常和另一个异常之间跳跃,我真的受够了。我读过关于如何执行异步调用的文章,也看过一些代码示例,但由于某种原因,我并没有根据VS得到它 我有一个简单的POCO,GetCompanyResponse,它将包含一组公司或错误,具体取决于发生的情况: public class GetCompanyResponse { public List<Company> Companies { get; set; } public List&

我希望有人能给我带来光明,因为在VS中我在一个异常和另一个异常之间跳跃,我真的受够了。我读过关于如何执行异步调用的文章,也看过一些代码示例,但由于某种原因,我并没有根据VS得到它

我有一个简单的POCO,GetCompanyResponse,它将包含一组公司或错误,具体取决于发生的情况:

public class GetCompanyResponse
{
    public List<Company> Companies { get; set; }
    public List<ErrorResult> Errors { get; set; }

    public GetCompanyResponse()
    {
        Companies = new List<Company>();
        Errors = new List<ErrorResult>();
    }
}
公共类GetCompanyResponse
{
上市公司{get;set;}
公共列表错误{get;set;}
public GetCompanyResponse()
{
公司=新列表();
错误=新列表();
}
}
我所要做的就是将从数据库加载公司的同步调用转换为异步调用,以便在加载数据的同时释放UI

以下是我转换的方法:

    public async Task<GetCompanyResponse> GetCompaniesByQuery()
    {
        var response = new GetCompanyResponse();

        try
        {
            using (var conn = new SqlConnection(_configuration["Settings:DBConn"]))
            {
                var cmd = conn.CreateCommand();
                cmd.CommandType = CommandType.Text;
                cmd.CommandText = "SELECT TOP (1000) company_id, company_name, postcode FROM dbo.tbl_companies";
                conn.Open();
                var reader = cmd.ExecuteReader();

                while (reader.Read())
                {
                    response.Companies.Add(new Company
                    {
                        CompanyId = Convert.ToInt32(reader["company_id"]),
                        CompanyName = reader["company_name"].ToString(),
                        PostCode = reader["postcode"].ToString()
                    });
                }
            }
        }
        catch (Exception e)
        {
            response.Errors.Add(new ErrorResult
            {
                ErrorMessage = e.Message
            });
        }
        
        return response;
    }
public异步任务GetCompaniesByQuery()
{
var response=new GetCompanyResponse();
尝试
{
使用(var-conn=new-SqlConnection(_-configuration[“Settings:DBConn”]))
{
var cmd=conn.CreateCommand();
cmd.CommandType=CommandType.Text;
cmd.CommandText=“从dbo.tbl_companies中选择前1000名公司id、公司名称、邮政编码”;
conn.Open();
var reader=cmd.ExecuteReader();
while(reader.Read())
{
答复.公司.添加(新公司)
{
CompanyId=Convert.ToInt32(读卡器[“公司id”),
CompanyName=读取器[“公司名称”]。ToString(),
PostCode=读卡器[“PostCode”]。ToString()
});
}
}
}
捕获(例外e)
{
response.Errors.Add(新的ErrorResult
{
ErrorMessage=e.消息
});
}
返回响应;
}
我的控制器动作是:

    public async Task<IActionResult> ByQuery()
    {
        var service = new TestService(_configuration);
        var response = await service.GetCompaniesByQuery();

        return View(response);
    }
public async Task ByQuery()
{
var service=新的TestService(_配置);
var response=await service.getcompanysbyquery();
返回视图(响应);
}

VS中的上述方法一直告诉我无法返回响应,因为它无法转换。我做错了什么

Severity    Code    Description Project File    Line    Suppression State
Error   CS0029  Cannot implicitly convert type 'TestApp.Models.GetCompanyResponse' to 'System.Threading.Tasks.Task<TestApp.Models.GetCompanyResponse>'  TestApp C:\Working Copies\TestApp\TestApp\Services\TestService.cs   59  Active
严重性代码描述项目文件行抑制状态
错误CS0029无法将类型“TestApp.Models.GetCompanyResponse”隐式转换为“System.Threading.Tasks.Task”TestApp C:\Working Copies\TestApp\TestApp\Services\TestService.cs 59 Active
如果我试图提取任务中严格处理响应POCO的公司属性的元素,如下所示:

    public async Task<IActionResult> ByQuery()
    {
        var service = new TestService(_configuration);
        var response = new GetCompanyResponse();
        response.Companies = (await service.GetCompaniesByQuery()).ToList();

        return View(response);
    }

    public async Task<IEnumerable<Company>> GetCompaniesByQuery()
    {
        var response = new List<Company>();

        try
        {
            using (var conn = new SqlConnection(_configuration["Settings:DBConn"]))
            {
                var cmd = conn.CreateCommand();
                cmd.CommandType = CommandType.Text;
                cmd.CommandText = "SELECT TOP (1000) company_id, company_name, postcode FROM dbo.tbl_companies";
                conn.Open();
                var reader = cmd.ExecuteReader();

                while (reader.Read())
                {
                    response.Add(new Company
                    {
                        CompanyId = Convert.ToInt32(reader["company_id"]),
                        CompanyName = reader["company_name"].ToString(),
                        PostCode = reader["postcode"].ToString()
                    });
                }
            }
        }
        catch (Exception e)
        {
            //not implemented yet
        }

        await Task.WhenAll((IEnumerable<Task>)response);
        
        return response;
    }
public async Task ByQuery()
{
var service=新的TestService(_配置);
var response=new GetCompanyResponse();
response.companys=(wait service.getcompanysbyquery()).ToList();
返回视图(响应);
}
公共异步任务GetCompaniesByQuery()
{
var response=newlist();
尝试
{
使用(var-conn=new-SqlConnection(_-configuration[“Settings:DBConn”]))
{
var cmd=conn.CreateCommand();
cmd.CommandType=CommandType.Text;
cmd.CommandText=“从dbo.tbl_companies中选择前1000名公司id、公司名称、邮政编码”;
conn.Open();
var reader=cmd.ExecuteReader();
while(reader.Read())
{
答复.添加(新公司)
{
CompanyId=Convert.ToInt32(读卡器[“公司id”),
CompanyName=读取器[“公司名称”]。ToString(),
PostCode=读卡器[“PostCode”]。ToString()
});
}
}
}
捕获(例外e)
{
//尚未实施
}
等待任务。WhenAll((IEnumerable)响应);
返回响应;
}
当VS停止抱怨它时,当代码运行时,我开始运行无效的强制转换错误

InvalidCastException: Unable to cast object of type 'System.Collections.Generic.List`1[TestApp.Models.Company]' to type 'System.Collections.Generic.IEnumerable`1[System.Threading.Tasks.Task]'.
TestApp.Services.TestService.GetCompaniesByQuery() in TestService.cs
+
            await Task.WhenAll((IEnumerable<Task>)response);
TestApp.Controllers.HomeController.ByQuery() in HomeController.cs
+
            response.Companies = (await service.GetCompaniesByQuery()).ToList();
InvalidCastException:无法将“System.Collections.Generic.List`1[TestApp.Models.Company]”类型的对象强制转换为“System.Collections.Generic.IEnumerable`1[System.Threading.Tasks.Task]”。
TestService.cs中的TestApp.Services.TestService.GetCompanyByQuery()
+
等待任务。WhenAll((IEnumerable)响应);
HomeController.cs中的TestApp.Controller.HomeController.ByQuery()
+
response.companys=(wait service.getcompanysbyquery()).ToList();

当我所看到的例子做了与上面完全相同的事情时,我不明白为什么这是原因。我在这里没有理解什么?

为什么要编写异步方法而不调用其中的任何异步代码?至少使用
ExecuteReaderAsync
“VS中的上述方法一直告诉我,我无法返回响应,因为它无法转换。”请编辑您的问题,以包含行给出的实际编译器错误,因为您发布的代码看起来很好。“为了释放UI”-web应用程序不是这样工作的。在发送HTTP响应之前,UI不会对服务器上发生的事情做出任何响应。异步控制器操作的要点是释放服务器上的线程以处理其他工作。您将获得可伸缩性(假设您正在进行适当的异步调用,例如ExecuteReaderAsync),但在处理单个请求的速度稍微慢一点的情况下进行权衡。C#和AJAX中的
async
功能互不相关。@DavidHirst在ASP.Net上下文中,
async
操作方法的目的是释放当前线程池线程以服务于其他HTTP r