C# 为什么可以';";异步无效“;单元测试被认可了吗?

C# 为什么可以';";异步无效“;单元测试被认可了吗?,c#,unit-testing,visual-studio-2012,async-await,c#-5.0,C#,Unit Testing,Visual Studio 2012,Async Await,C# 5.0,async void无法在Visual Studio 2012中运行单元测试: [TestClass] public class MyTestClass { [TestMethod] public async void InvisibleMyTestMethod() { await Task.Delay(1000); Assert.IsTrue(true); } } 如果要进行异步单元测试,测试方法必须返回一个任务: [TestM

async void
无法在Visual Studio 2012中运行单元测试:

[TestClass]
public class MyTestClass
{
    [TestMethod]
    public async void InvisibleMyTestMethod()
    {
        await Task.Delay(1000);
        Assert.IsTrue(true);
    }
}
如果要进行异步单元测试,测试方法必须返回一个任务:

[TestMethod]
public async Task VisibleMyTestMethod()
{
    await Task.Delay(1000);
    Assert.IsTrue(true);
}

为什么会这样?我并不是绝对需要一个
异步void
测试方法,我只是好奇。Visual Studio 2012在生成
异步无效
测试方法时不会给出警告或错误,即使它无法运行…

异步无效
方法应被视为“触发并忘记”-无法等待它们完成。如果VisualStudio要启动其中一个测试,它将无法等待测试完成(将其标记为成功)或捕获任何引发的异常

使用
异步任务
,调用方可以等待执行完成,并捕获运行时引发的任何异常


有关
async void
vs
async Task

的更多讨论,请参阅,这只是因为MSTest不支持
async void
单元测试。通过引入它们可以执行的上下文,可以实现这一点

MSTest不支持这一点,可能是因为Microsoft决定对现有测试进行太多的更改(如果给现有测试一个意外的上下文,则它们可能会死锁)


没有编译器警告/错误,因为它是完全有效的C代码。它不起作用的唯一原因是因为单元测试框架(即,我相信xUnit确实支持
async void
tests),C编译器查看您的属性,确定您正在使用MSTest,这将严重违反关注点分离,并确定您确实不想使用
async void

我在VS2015中发现,任何用async修饰的测试方法都不会显示在测试资源管理器中。最后,我删除了async关键字,并用task.Wait()替换了测试中的Wait调用,并在task.Result上完成了一系列操作

看起来还可以。还没有尝试过异常测试

var task = TheMethodIWantToTestAsync(someValue);
task.Wait();
var response = task.Result;

Assert.IsNotNull(response);
Assert.IsTrue(response.somevalue);

在第一个实现(VisualStudioPreview)中,测试将被重新命名并“运行”。问题是该方法将在第一次等待时结束,而这是测试的结果。这不是真的。NUnit确实支持
async void
测试,本文在一定程度上详细介绍了支持它的方式和原因。请参见下文。不要认为它需要调用task.Wait()作为调用任务。如果任务尚未完成,Result将自动调用task.Wait()。