在火灾后忘记处理任务已完成

时间:2016-05-12 05:27:07

标签: c# asynchronous async-await task-parallel-library dispose

我使用一个通过调用一个方法来监听消息的库,该方法返回的任务仅在与服务器的连接关闭时结束。

// Return a task that completes the connection ends
Task Listen();

我使用听的方式是火和忘记,因为我不想阻止接收消息。

该库还提供订阅,以便在完成发送消息时执行任务(基本上在监听结束时)。

// Exception is null if no problem occurs during processing messages
void SubscribeToOnEnd(Func<Exception, Task> OnEnd);

在我的代码中,我希望能够在监听结束之后处理库对象,或者我们收到了OnEnd。

现在我可以想到3个选项:

  1. 如果我从OnEnd任务调用它,我不确定它可能导致的行为是从我试图处置的对象调用OnEnd。
  2. 在Listen()方法的延续中处理对象,但我不确定此选项的后果,选项1的任何副作用。

  3. 使用Task.Run在OnEnd上触发任务以处置该对象。哪个不是真的认为是一种好的做法,它可能会导致一些同步问题。

  4. 处理此类案件的最佳做法是什么?

    为简单起见,想象一下我的代码为

    public class Class
    {
        private Library library;
    
        public async Task MyMethod(List<string> messages)
        {
            // in reality this is synchronized check
            if(this.library == null)
            {
                this.library = new Library();
                this.library.SubscribeToRecieve((m) => 
                {
                    Console.WriteLine(m);
                });
    
                this.library.SubscribeToOnEnd(this.OnEnd);
                this.library.Listen();
            }
    
    
            foreach(var s in messages)
            {
                await this.library.SendAsync(s);
            }
        }
    
        private Task OnEnd(Exception)
        {
            // do some stuff
        }
    }
    

    只要连接处于活动状态,库对象就可以使用,如果由于任何原因连接被关闭/ droped,我希望能够在那时处置它,所以当再次调用MyMethod时可以创建另一个对象并再次开始监听。

0 个答案:

没有答案