包含异步调用和同步操作对结果的异步方法
我试图制作一个异步方法,我可以多次调用并稍后等待 - 该方法应该调用数据库,等待结果,一旦有结果,然后返回最终结果。它看起来像这样:包含异步调用和同步操作对结果的异步方法
public async Task<long> GetSomethingFromDbAndSelectSomethingOnServer()
{
//stuff is just an Entity Framework database call
var stuff = await myEfDbContext.StuffTable.ToListAsync();
long itemsCount = stuff.Where(someQueryThatCantGoToDb).Count();
return itemsCount;
}
这似乎是一个明显的失误,因为我指定的返回类型的任务,而我其实只返回一个长。这将编译,而是抛出异常:
类型的第一次机会异常的“System.NotSupportedException” 发生在EntityFramework.dll
我打算使用此代码如下所示:
Task<long> myAsyncCall = GetSomethingFromDbAndSelectSomethingOnServer();
long myCount = await myAsyncCall;
这可能是一个有点文不对题,但阐述,这里有一些很好的的作品:
Task<long> pendingItemCountCall = _mongoItems.Find(filter).CountAsync();
long myCount2 = await pendingItemCountCall;
当然,不同之处在于它只是对db的异步调用,而没有进一步的操作,我正在尝试在我正在问的问题的SQL调用中做什么。
编辑:
所以,实际上,这似乎是有问题的行:
var stuff = await myEfDbContext.StuffTable.ToListAsync();
如果我评论了这一点,并手动设置计数VAR,代码去。我很困惑,但我更关心整体问题 - 我是否在这里正确使用异步,不一定是我的特定错误的错误。
您无法在同一个上下文中等待多个查询。你必须为每个操作使用自己的上下文:
public async Task<long> GetSomethingFromDbAndSelectSomethingOnServer()
{
using(var context = new MyEfDbContext())
{
// include the following if you do not need lazy loading and want some more speed
context.Configuration.AutoDetectChangesEnabled = false;
context.Configuration.ProxyCreationEnabled = false;
var stuff = await myEfDbContext.StuffTable.ToListAsync();
long itemsCount = stuff.Where(someQueryThatCantGoToDb).Count();
return itemsCount;
}
}
感谢您的答案,我在这里看到:http://*.com/questions/20946677/ef-data-context-async-await-multithreading,我会检查并接受答案,如果它的工作,虽然那里似乎是一些ifs和buts。 – VSO
答案是2岁。从今天起,EF和ASP都可以正常工作。对于ASP,您只需知道在ConfigureAwait(false)后您将失去HttpContext.Current,因此如果您需要HttpContext.Current,则不得使用ConfigureAwait(false)。 – wertzui
在使用实体框架(使用实体框架)封装后,它仍然失败,但我会继续寻找。鼓励听到它应该工作,将继续与它混乱。我确实认为这是问题,因为它只在一次调用时才起作用,并且在多次调用时仅在后续迭代中失败。 – VSO
@HenkHolterman:它的工作! – VSO