Service Fabric actors auto delete

1.2k Views Asked by At

In a ServiceFabric app, I have the necessity to create thousands of stateful Actors, so I need to avoid accumulating Actors when they become useless.

I know I can't delete an Actor from the Actor itself, but I don't want to keep track of Actors and loop to delete them.

The Actors runtime use Garbace collection to remove the deactivated Actor objects (but not their state); so, I was thinking about removing Actor state inside the OnDeactivateAsync() method and let the GC deallocate the Actor object after the usual 60min.

In theory, something like this should be equivalent to delete the Actor, isn't it?

protected override async Task OnActivateAsync()
{
    await this.StateManager.TryRemoveStateAsync("MyState");
}

Is there anything remaining that only explicit deletion can remove?

2

There are 2 best solutions below

2
On

According to the docs, you shouldn't change the state from OnDeactivateAsync.

If you need your Actor to not keep persisted state, you can use attributes to change the state persistence behavior:

No persisted state: State is not replicated or written to disk. This level is for actors that simply don't need to maintain state reliably.

[StatePersistence(StatePersistence.None)]
class MyActor : Actor, IMyActor
{
}

Finally, you can use the ActorService to query Actors, see if they are inactive, and delete them.

3
On

TL;DR There are some additional resources you can free yourself (reminders) and some that only explicit deletion can remove because they are not publicly accessible.

Service Fabric Actor repo is available on GitHub. I am using using persistent storage model which seems to use KvsActorStateProvider behind the scenes so I'll base the answer on that. There is a series of calls that starts at IActorService.DeleteActorAsync and continues over to IActorManager.DeleteActorAsync. Lot of stuff is happening in there including a call to the state provider to remove the state part of the actor. The core code that handles this is here and it seems to be removing not only the state, but also reminders and some internal actor data. In addition, if you are using actor events, all event subscribers are unsubscribed for your actor.

If you really want delete-like behavior without calling the actor runtime, I guess you could register a reminder that would delete the state and unregister itself plus other reminders.