So in the last post we have been presented a “strange” issue with tasks continuation. If on would run the example he/she would see a “OnCanceled!” message printed to the console too. This feel strange at the beginning but if we structure the code a bit differently it would be obvious why.

So how we can split this differently? For starters let’s split the main task from its continuations.

var task = Task.Run(() => Console.WriteLine("Main part"));

var continuation = task.ContinueWith(t =>
         Console.WriteLine("OnFaulted!"),
         TaskContinuationOptions.OnlyOnFaulted)
    .ContinueWith(t =>
        Console.WriteLine("OnCanceled!"),
        TaskContinuationOptions.OnlyOnCanceled);

And now let’s split it even further. One might think that the correct splitting would be like this:

var continuationOnFaulted = task.ContinueWith(t =>
                    Console.WriteLine("OnFaulted!"),
                    TaskContinuationOptions.OnlyOnFaulted);

var contiuationOnCancelled = task.ContinueWith(t =>
                    Console.WriteLine("OnCanceled!"),
                    TaskContinuationOptions.OnlyOnCanceled);

WRONG! The correct is this:

var continuationOnFaulted = task.ContinueWith(t =>
                    Console.WriteLine("OnFaulted!"),
                    TaskContinuationOptions.OnlyOnFaulted);

var contiuationOnCancelled = continuationOnFaulted.ContinueWith(t =>
                    Console.WriteLine("OnCanceled!"),
                    TaskContinuationOptions.OnlyOnCanceled);

Yes, that is correct – the actual behavior is that in the second continuation it’s actually a continuation of the previous continuation and that one never get’s called (since the main task run to completion) so it get’s cancelled! Bingo.

As I mentioned in the last post – if you think about it for a while, it makes perfect sens to expect such behavior. If I would blame someone/something for this it would be LINQ/fluent APIs. I think we got quite used to such dot-dot-dot notations and even though internally new objects are created underneath we feel like we are operating on the same one. Be careful!