【发布时间】:2015-12-02 01:07:17
【问题描述】:
除了避免async void的原因,是否有可能从调用代码中捕获以下错误?
private static Action ErrorAction
{
get
{
return async () =>
{
await Task.Delay(0);
throw new NotImplementedException();
};
}
}
例如在以下两个中我想收集抛出的异常,但是两个测试都失败了:
[Test]
public void SelfContainedExampleTryCatch()
{
List<Exception> errors = new List<Exception>();
try
{
ErrorAction();
}
catch (Exception ex)
{
errors.Add(ex);
}
errors.Count().Should().Be(1);
}
[Test]
public void SelfContainedExampleContinueWith()
{
List<Exception> errors = new List<Exception>();
var task = Task.Factory.StartNew(ErrorAction);
task.ContinueWith(t =>
{
errors.Add(t.Exception);
}, TaskContinuationOptions.OnlyOnFaulted);
task.Wait();
errors.Count().Should().Be(1);
}
我知道我可以使用带有async Task 签名的方法;但具体来说,这是我需要处理的 Action 可分配委托异步代码示例,并且在全局级别进行捕获是不切实际的。如果可能的话,同步和异步操作通用的解决方案将是理想的。
希望我错过了一个简单的解决方案,但到目前为止,我只是走入了许多死胡同,并且(可能是错误地)得出结论这是不可能的。任何帮助(或节省时间的浪费)将不胜感激!
【问题讨论】:
-
测试在什么时候失败?
-
错误未处理 - 它不会添加到
errors列表中。 -
@mason 断言
errors.Count().Should().Be(1);上的测试将失败,因为不会传播异常。 -
我发现如果我在我的内部处理程序中引入异步代码,我必须使调用代码异步,以及 THAT 的调用代码异步。它最终是异步的。你能解释一下为什么不能使用带有
async Task签名的方法吗? -
@AndrewShepherd 它不必一直是异步的。您可以通过
var task = MyCallAsync(); task.Wait();从未标记为异步的方法中运行异步命令。
标签: c# asynchronous async-await