I'm developing a class library that implements a protocol stack. There I have an asynchronous operation DoSomething that implements IAsyncResult. The user of this method can use BeginDoSomething and EndDoSomething. So long it's quite a common task.
Now I got the requirement to make the asynchronous operation abortable. I can think of several ways to achieve this, but I'm not sure which one is the best:
- Have a CancelDoSomething method besides BeginDoSomething and EndDoSomething. This is not the common asaync pattern and thus not easy to find out for the user of the operation.
- According to no. 1: Have a Cancel property
- The instance of IAsyncResult that is returned by BeginDoSomething can be casted to DoSomethingAsyncResult. DoSomethingAsyncResult has a Cancel method. Again, this is not the common usage of the async pattern and hardly to know for the "common user" of the class library.
- According to no. 3: Have a Cancel property
- The instance of IAsyncResult that is returned by BeginDoSomething implements IAbortableAsyncResult:
public IAbortableAsyncResult:IAsyncResult { void Abort(); }
. For me this seems to be the most elegant way. When the user starts the operation using BeginDoSomething he gets an instance of IAbortableAsyncResult which means that this special feature is prominently introduced to him.
What is the best solution? Are there even more ways to solve this? I prefer no. 5 because it doesn't have a code smell ( at least I didn't recognize until now).
[EDIT]
An approach not relying on TPL/.NET 4 is appreciated to have a solution that is also applicable in legacy code that cannot be ported to the newest version of .NET framework.
[/EDIT]