[TestMethod]
public async Task MyMethodAsync_ReturnsFalse()
{
    var objectUnderTest = ...;
    bool result = await objectUnderTest.MyMethodAsync();
    Assert.IsFalse(result);
}

---

[TestMethod]
public void MyMethodAsync_ReturnsFalse()
{
    AsyncContext.Run(async () =>
    {
        var objectUnderTest = ...;
        bool result = await objectUnderTest.MyMethodAsync();
        Assert.IsFalse(result);
    });
}

---

[TestMethod]
[ExpectedException(typeof(DivideByZeroException))]
public async Task Divide_WhenDenominatorIsZero_ThrowsDivideByZero()
{
    await MyClass.DivideAsync(4, 0);
}

---

[TestMethod]
public async Task Divide_WhenDenominatorIsZero_ThrowsDivideByZero()
{
    await Assert.ThrowsException<DivideByZeroException>(async () =>
    {
        await MyClass.DivideAsync(4, 0);
    });
}

---

/// <summary>
/// Zapewnia, że asynchroniczny delegat będzie rzucać wyjątek.
/// </summary>
/// <typeparam name="TException">
/// Oczekiwany typ wyjątku.
/// </typeparam>
/// <param name="action">Asynchroniczny delegat do przetestowania.</param>
/// <param name="allowDerivedTypes">
/// Określa, czy powinny być akceptowane typy pochodne.
/// </param>
public static async Task ThrowsExceptionAsync<TException>(Func<Task> action,
    bool allowDerivedTypes = true)
{
    try
    {
        await action();
        Assert.Fail("Delegat nie rzucił oczekiwanego wyjątku " +
            typeof(TException).Name + "." );
    }
    catch (Exception ex)
    {
        if (allowDerivedTypes && !(ex is TException))
            Assert.Fail("Delegat rzucił wyjątek typu " + ex.GetType().Name +
                ", ale oczekiwany był typ " + typeof(TException).Name +
                " lub typ pochodny." );
        if (!allowDerivedTypes && ex.GetType() != typeof(TException))
            Assert.Fail("Delegat rzucił wyjątek typu " + ex.GetType().Name +
                ", ale oczekiwany był typ " + typeof(TException).Name + "." );
    }
}

---

[TestMethod]
public void MyMethodAsync_DoesNotThrow()
{
    AsyncContext.Run(() =>
    {
        var objectUnderTest = ...;
        objectUnderTest.MyMethodAsync();
    });
}

---

[TestMethod]
public async Task MyCustomBlock_AddsOneToDataItems()
{
    var myCustomBlock = CreateMyCustomBlock();

    myCustomBlock.Post(3);
    myCustomBlock.Post(13);
    myCustomBlock.Complete();

    Assert.AreEqual(4, myCustomBlock.Receive());
    Assert.AreEqual(14, myCustomBlock.Receive());
    await myCustomBlock.Completion;
}

---

[TestMethod]
public async Task MyCustomBlock_Fault_DiscardsDataAndFaults()
{
    var myCustomBlock = CreateMyCustomBlock();

    myCustomBlock.Post(3);
    myCustomBlock.Post(13);
    myCustomBlock.Fault(new InvalidOperationException());

    try
    {
        await myCustomBlock.Completion;
    }
    catch (AggregateException ex)
    {
        AssertExceptionIs<InvalidOperationException>(
            ex.Flatten().InnerException, false);
    }
}

public static void AssertExceptionIs<TException>(Exception ex,
    bool allowDerivedTypes = true)
{
    if (allowDerivedTypes && !(ex is TException))
        Assert.Fail("Wyjątek ma typ " + ex.GetType().Name + ", ale oczekiwany był typ "
        + typeof(TException).Name + " lub typ pochodny." );
    if (! allowDerivedTypes && ex.GetType() != typeof(TException))
        Assert.Fail("Wyjątek ma typ " + ex.GetType().Name + ", ale oczekiwany był typ "
        + typeof(TException).Name + "." );
}

---

public interface IHttpService
{
    IObservable<string> GetString(string url);
}

public class MyTimeoutClass
{
    private readonly IHttpService _httpService;

    public MyTimeoutClass(IHttpService httpService)
    {
        _httpService = httpService;
    }

    public IObservable<string> GetStringWithTimeout(string url)
    {
        return _httpService.GetString(url)
            .Timeout(TimeSpan.FromSeconds(1));
    }
}

---

class SuccessHttpServiceStub : IHttpService
{
    public IObservable<string> GetString(string url)
    {
        return Observable.Return("stub" );
    }
}

[TestMethod]
public async Task MyTimeoutClass_SuccessfulGet_ReturnsResult()
{
    var stub = new SuccessHttpServiceStub();
    var my = new MyTimeoutClass(stub);

    var result = await my. GetStringWithTimeout("http://www.example.com/" )
        .SingleAsync();

    Assert.AreEqual("stub" , result);
}

---

private class FailureHttpServiceStub : IHttpService
{
    public IObservable<string> GetString(string url)
    {
        return Observable.Throw<string>(new HttpRequestException());
    }
}

[TestMethod]
public async Task MyTimeoutClass_FailedGet_PropagatesFailure()
{
    var stub = new FailureHttpServiceStub();
    var my = new MyTimeoutClass(stub);

    await ThrowsExceptionAsync<HttpRequestException>(async () =>
    {
        await my.GetStringWithTimeout("http://www.example.com/" )
            .SingleAsync();
    });
}

---

public interface IHttpService
{
    IObservable<string> GetString(string url);
}

public class MyTimeoutClass
{
    private readonly IHttpService _httpService;

    public MyTimeoutClass(IHttpService httpService)
    {
        _httpService = httpService;
    }

    public IObservable<string> GetStringWithTimeout(string url,
        IScheduler scheduler = null)
    {
        return _httpService.GetString(url)
            .Timeout(TimeSpan.FromSeconds(1), scheduler ?? Scheduler.Default);
    }
}

---

private class SuccessHttpServiceStub : IHttpService
{
    public IScheduler Scheduler { get; set; }
    public TimeSpan Delay { get; set; }

    public IObservable<string> GetString(string url)
    {
        return Observable.Return("stub" )
            .Delay(Delay, Scheduler);
    }
}

---

[TestMethod]
public void MyTimeoutClass_SuccessfulGetShortDelay_ReturnsResult()
{
    var scheduler = new TestScheduler();
    var stub = new SuccessHttpServiceStub
    {
        Scheduler = scheduler,
        Delay = TimeSpan.FromSeconds(0.5),
    };
    var my = new MyTimeoutClass(stub);
    string result = null;

    my.GetStringWithTimeout("http://www.example.com/" , scheduler)
        .Subscribe(r => { result = r; });

    scheduler.Start();

    Assert.AreEqual("stub" , result);
}

---

[TestMethod]
public void MyTimeoutClass_SuccessfulGetLongDelay_ThrowsTimeoutException()
{
    var scheduler = new TestScheduler();
    var stub = new SuccessHttpServiceStub
    {
        Scheduler = scheduler,
        Delay = TimeSpan.FromSeconds(1.5),
    };
    var my = new MyTimeoutClass(stub);
    Exception result = null;

    my.GetStringWithTimeout("http://www.example.com/" , scheduler)
        .Subscribe(_ => Assert.Fail("Otrzymana wartość" ), ex => { result = ex; });

    scheduler.Start();

    Assert.IsInstanceOfType(result, typeof(TimeoutException));
}

---

