Practical ASP.NET

Distributed Concurrent Actor Models with Akka.NET

Ease the pain of concurrent programming with the Actor Model and Akka.NET.

Building concurrent systems that are capable of working on multiple pieces of work at the same time can be difficult, particularly when there's some shared mutable state being accessed by multiple threads.

The Actor Model gives you a way of representing systems using the higher-level abstractions of actors and messages. This can ease the burden of building concurrent systems.

Akka.NET is a port of the original Akka framework from Java/Scala to the Microsoft .NET Framework.

The Actor Model
The Actor Model describes a system whereby the fundamental unit of computation is the actor. A collection of actors performs the work of the system. Actors do not expose their internal state to the outside world (including other actors) but instead communicate via messages. The idea of this approach is to remove any shared mutable state; while actors do have mutable (internal) state, messages should be immutable.

An actor is able to do four essential things:

  • Respond to messages sent to it
  • Send messages to other actors
  • Create new actors
  • Change its behaviour in response to an incoming message

In Akka.NET, actors are classes that inherit from specific Akka.NET base classes, while messages can be simple .NET types such as a string, and they can also be custom types that are simple POCO classes.

Actors may exist in the same process on the same machine, different processes on the same machine, or even in different processes on different machines across the network. This ability to distribute actors out across multiple machines enables a system to scale out as required. One important feature in Akka.NET is that the code you write in your actors doesn't need to change depending on whether you're sending messages to a remote or local actor.

Defining an Akka.NET Actor
There is a choice of Akka.NET base classes to inherit from when defining an actor class, the basic being the untyped actor API. To get access to the core Akka.NET features the "Akka" NuGet package is installed.

In Listing 1 you can see an actor that's able to handle string or int messages that are sent to it.

Listing 1: Simple Actor Class Using the Untyped API
public class DemoActor : UntypedActor
  protected override void OnReceive(object message)
    if (message is string)
      // Do something with string message
      Console.WriteLine("Received string message {0}", message);
    if (message is int)
      // Do something with int message
      Console.WriteLine("Received int message {0}", message);

An Actor System
In Akka.NET, actors live inside a managed actor system. This actor system manages the creation and lifetime of actors and the sending of messages around the system.

In Listing 2 you can see the Main method of a console application that creates an actor system, populates it with an actor instance and then sends a message to the actor using the Tell method.

Listing 2: Creating Actor Systems and Actor Instances
class Program
  static void Main(string[] args)
    var actorSystem = ActorSystem.Create("DemoSystem");

    var actorReference = actorSystem.ActorOf<DemoActor>("DemoActor1");


    // Wait for enter before closing console application

The output of running this code is shown in Figure 1.

[Click on image for larger view.] Figure 1. Console Application Showing Messages Being Received and Processed

Using Receive Actors
Receive actors offer a higher level API that does not require the kind of "if (message is string)" type statements. Instead the actor class inherits from the ReceiveActor base class and uses its Receive method to specify what types of messages it can handle. In Listing 3 we can see the same actor from Listing 1 refactored to a receive actor.

Listing 3: Inheriting from ReceiveActor
public class DemoActor : ReceiveActor
  public DemoActor()
    Receive<string>(message =>
        // do something with string message
        Console.WriteLine("Received string message {0}", message);

    Receive<int>(message =>
        // do something with int message
        Console.WriteLine("Received int message {0}", message);

This produces the same output when executed in the console application.

To find out more about Akka.NET, check out the project homepage at

About the Author

Jason Roberts is a Microsoft C# MVP with over 15 years experience. He writes a blog at, has produced numerous Pluralsight courses, and can be found on Twitter as @robertsjason.

comments powered by Disqus


  • Move Over, Stack Overflow: Microsoft Launches Q&A for .NET

    Stack Overflow probably isn't worried, but Microsoft has launched its own Q&A site for all things .NET, seeking to provide a one-stop-shop for getting .NET technical questions answered by the community.

  • Developer Decries WinForms-to-Blazor Performance Degradation

    Since shipping .NET 5, Visual Studio 2019 v16.8 and more goodies recently, Microsoft has been touting speed improvements in many components -- including the red-hot Blazor project -- but some real-world developers are finding different results.

  • Google Cloud Functions Supports .NET Core 3.1 (but not .NET 5)

    Google Cloud Functions -- often used for serverless, event-driven projects -- now supports .NET, but the new support is a release behind Microsoft's latest .NET offering.

  • Binary Classification Using PyTorch: Model Accuracy

    In the final article of a four-part series on binary classification using PyTorch, Dr. James McCaffrey of Microsoft Research shows how to evaluate the accuracy of a trained model, save a model to file, and use a model to make predictions.

  • Visual Basic in .NET 5: Ready for WinForms Apps

    With the milestone .NET 5 and Visual Studio 2019 v16.8 releases now out, Microsoft is reminding Visual Basic coders that their favorite programming language enjoys full support and the troublesome Windows Forms Designer is even complete -- almost.

Upcoming Events