代码之家  ›  专栏  ›  技术社区  ›  StuiterSlurf Marius

MongoDB C#驱动程序取消令牌

  •  6
  • StuiterSlurf Marius  · 技术社区  · 6 年前

    是否有人知道CancellationToken在示例中添加参数时的作用

    public static UpdateResult UpdateMany<TDocument>(
        this IMongoCollection<TDocument> collection,
        Expression<Func<TDocument, bool>> filter,
        UpdateDefinition<TDocument> update,
        UpdateOptions options = null,
        CancellationToken cancellationToken = null
    )
    

    https://mongodb.github.io/mongo-csharp-driver/2.3/apidocs/html/M_MongoDB_Driver_IMongoCollectionExtensions_UpdateMany__1.htm

    是回滚吗?或者它有什么作用?

    1 回复  |  直到 6 年前
        1
  •  5
  •   StuiterSlurf Marius    3 年前

    A. CancellationToken 通常在通过mongodb驱动程序编写异步I/O代码时使用( InsertOneAsync 例如)。让我们考虑以下场景。你在做早餐。 Example taken from here.

    static async Task Main(string[] args)
    {
        //Find eggs and bacon in database
        Task<List<Egg>> eggTask = FindEggsAsync(2);
        Task<List<Bacon>> baconTask = FindBaconAsync(3);
    
        Coffee cup = PourCoffee();
        Console.WriteLine("coffee is ready");
        
        Juice oj = PourOJ();
        Console.WriteLine("oj is ready");
        
        List<Egg> eggs = await eggTask;
        List<Bacon> bacon = await baconTask;
        
        FryEggs(eggs);
        Console.WriteLine("eggs are ready");
    
        FryBacon(bacon);
        Console.WriteLine("bacon is ready");
        
        Console.WriteLine("Breakfast is ready!");
    }
    

    这是很好的异步代码,对吗?只有当我们需要任务的结果时,我们才在等待任务。

    我们首先需要通过I/O找到我们的鸡蛋和培根,让我们想象一下,我们的鸡蛋和培根存储在mongodb中,而不是食品储藏室。所以我们给你的两个想象中的孩子 tasks 从食品储藏室(数据库)中查找鸡蛋和培根。

    当他们发现你给自己倒了一杯OJ和咖啡时,你已经准备好了(基本上是任何CPU工作)。

    有了咖啡和果汁,你意识到你已经准备好了配料,所以你 await 返回给孩子的任务和 FryEggs FryBacon

    早餐做得很好——但让我们假设你是一个脾气暴躁的人,度过了一个糟糕的早晨,你的咖啡洒了,这让你完全不吃早餐(我知道这很荒谬),你需要告诉你的孩子不要再找了。让我们修改上面的代码来集成这一点。

    static async Task Main(string[] args)
    {
         var cancellationToken = new CancellationTokenSource(); 
        //Find eggs and bacon in database
        Task<List<Egg>> eggTask = FindEggsAsync(2,cancellationToken.Token);
        Task<List<Bacon>> baconTask = FindBaconAsync(3,cancellationToken.Token);
    
        Coffee cup = PourCoffee();
        if(cup.IsSpilled())
        {
            //Freak out and cancel tasks
            cancellationToken.Cancel();
            //Quit
            Environment.Exit(0)
        }  
        Console.WriteLine("coffee is ready");
        
        Juice oj = PourOJ();
        Console.WriteLine("oj is ready");
        
        List<Egg> eggs = await eggTask;
        List<Bacon> bacon = await baconTask;
        
        FryEggs(eggs);
        Console.WriteLine("eggs are ready");
    
        FryBacon(bacon);
        Console.WriteLine("bacon is ready");
    
        Console.WriteLine("Breakfast is ready!");
        //Dispose of token
        cancellationToken.Dispose();
    }
    

    取消令牌本身将传递给相关mongodb驱动程序方法的异步版本。 FindAsync 将在我们的两个find方法中调用,并传入取消令牌。如果任务尚未完成,它将相应地取消输入/输出操作。