dotnet / orleans

Cloud Native application framework for .NET
https://docs.microsoft.com/dotnet/orleans
MIT License
10.07k stars 2.03k forks source link

Utilizing CancellationTokens in Orleans #1516

Closed veikkoeeva closed 8 years ago

veikkoeeva commented 8 years ago

Following Gitter discussion, making use of CancellationToken to cancel tasks could be useful. This issue is for more specific discussion. The motivation of this feature conserving system resources and simplifying both Orleans and application code.

The use cases can be divided into three categories:

  1. Cancelling application code that initiates potentially resource consuming operations. A concrete use case can be such that a user initiates action on a web page and this spans via a silo all the way to a storage and starts a computation there. Such an example with ASP.NET WebAPI and Entity Framework is given here. Another example is a business logic reason to cancel an operation with a linked token. An example is given here.
  2. The operations in 1. could start an action that results in Orleans system operation such as grain persistence operations, streaming or the planned event storage. In this situation there is storage dependent technical timeout and possibly a user defined cancellation token linked to this.
  3. Using cancellation tokens in Orleans IMembershipTable, IReminderTable and other system operations more technical in nature. As for an example, a persistent storage could be under unable to serve requests timely. For a reason or another, the timeout (e.g. in a connection string) could have been set to a value as high as minutes. If the storage supports cancellation natively, cancelling individual requests could result in cancelling queries selectively (an example for SQL Server, second example) and hence conserve storage resource.

Questions:

  1. What would be the performance implications? Should this be strictly a pay-for-use feature?
  2. Should code generation define an overload for CancellationToken automatically or should it be user defined?
  3. What guarantees should be associated with cancellation tokens and in which situation do these hold? Documentation likely needs to be clear (i.e. if the requests comes from a web page, how certain is it cancellation works as intended)?
  4. What would be the specific, concrete pieces of interfaces and code affected by cancellation tokens should someone attempt to implement this?
  5. Should cancellation be non-blocking?
dVakulen commented 8 years ago

As I see this:

  1. The simplest way of implementing this is to examine grain method parameters, and for found CancellationToken's register delegate, that will call cancel on corresponding CancellationTokenSource that will be located on the same silo with callee grain. Codegen realization of it effectively makes it pay-for-use feature.
  2. Following the plan above there will be no need to neither define an overload through codegen nor to bother user with it.
  3. While discussing this bullet the fact that cancel request is highly likely to span through 1 or more network calls should be taken into consideration. In my opinion the guarantees must be as strong as possible, as cancelling usually required for heavy tasks, which execution may take hours of CPU time, so cancelling with at most once reliability is not an option. Currently users for this purpose are using separate grain method, through which they cancelling grain local CancellationTokenSource's, and this means that they have at least once cancel semantics, and this semantics should be preserved.
  4. If to follow the rough plan described in the bullet 1 - there will be no changes to the public API. As for the code - code generation will change slightly, though there is a way of implementing this without affecting codegen, but it will be not that efficient.
  5. The implementation wont differ much for both ways, but knowing that it will hit the network and will be called from the grain one would want it to be non-blocking.
sergeybykov commented 8 years ago

Resolved via https://github.com/dotnet/orleans/pull/1599.