11

新的 C# 驱动程序完全是异步的,并且在我的理解中稍微扭曲了旧的设计模式,例如 n 层架构中的 DAL。

在我的 Mongo DAL 中,我曾经这样做:

public T Insert(T entity){
     _collection.Insert(entity);
     return entity;
}

这样我就可以得到持久化的ObjectId.

今天,一切都是异步的,例如InsertOneAsync. 方法现在将
如何返回何时完成?你能举个例子吗?InsertentityInsertOneAsync

4

2 回答 2

18

了解async/的基础知识会很有帮助,await因为它是一个有点漏洞的抽象并且有许多陷阱。

本质上,您有两个选择:

  • 保持同步。在这种情况下,分别在异步调用上使用.Result和是安全.Wait()的,例如

    // Insert:
    collection.InsertOneAsync(user).Wait();
    
    // FindAll:
    var first = collection.Find(p => true).ToListAsync().Result.FirstOrDefault();
    
  • 在你的代码库中异步。不幸的是,异步执行非常“具有传染性”,因此您要么将几乎所有内容都转换为异步,要么不进行。小心,不正确地混合同步和异步会导致死锁。使用 async 有很多优点,因为您的代码可以在 MongoDB 仍在工作时继续运行,例如

    // FindAll:
    var task = collection.Find(p => true).ToListAsync();
    // ...do something else that takes time, be it CPU or I/O bound
    // in parallel to the running request. If there's nothing else to 
    // do, you just freed up a thread that can be used to serve another 
    // customer...
    // once you need the results from mongo:
    var list = await task;
    
于 2015-05-07T11:33:39.037 回答
0

就我而言:当我收到此错误时:

源 IQueryable 未实现 IAsyncEnumerable。只有实现 IAsyncEnumerable 的源才能用于实体框架异步操作。

我已经为 mongodb 实现了 async where 函数,如下所示。

public async Task<IEnumerable<TEntity>> Where(Expression<Func<TEntity, bool>> expression = null)
{
     return await context.GetCollection<TEntity>(typeof(TEntity).Name, expression).Result.ToListAsync();
}
于 2020-02-27T08:30:07.660 回答