PubSub

Overview

There are situations where one to send messages to all actors that have registered interest in a named topic. PubSub provides a way to implement publish-subscribe communication between actors distributed across multiple nodes when cluster is enabled or on a single node.

By encapsulating topic management and message routing, it simplifies the development of reactive and scalable distributed systems in Go. Its design ensures that messages are efficiently delivered to all subscribers both locally and across the cluster when cluster is enabled, making it an essential building block for any distributed actor-based application.

PubSub is activated with the option WithPubsub during the creation of the actor system.

PubSub can be used in cluster mode or on a single node.

Design

Topic Registry

PubSub maintain a Topic registry that is managed by a dedicated system actor TopicActor

A single instance of TopicActor when pubsub is enabled is created on a given node. You register actors to the local TopicActor by a Subscribe message using Tell. To unsubscribe actors need to send Unsubscribe message using Tell.

Successful Subscribe and Unsubscribe is acknowledged with SubscribeAck and UnsubscribeAck replies from the local TopicActor .

Once pubsub is enabled one can access the local instance of TopicActor from the ActorSystem.

Code Snippet

// create an actor on the actor system of the node1.
actor1, err := node1.Spawn(ctx, "actor1", Subscriber())

topic := "test-topic"
// subscribe to the topic
err = actor1.Tell(ctx, node1.TopicActor(), &goaktpb.Subscribe{Topic: topic})

Publish

To publish a message to a given topic, local actors send a Publish using Tell message to the local TopicActor. The local TopicActor will route the message to all the local subscribers as well as to all the subscribers to the named topic in the cluster when cluster is enabled.

This is the true pub/sub mode. A typical usage of this mode is a chat room in an instant messaging application.

Code Snippet

// create an publisher actor
publisher, err := node1.Spawn(ctx, "publisher", Publisher())

// create the publish message
message := &goaktpb.Publish{
	Id:      "messsage1",
	Topic:   topic,
	Message: transformed,
}

// publish the message
err = publisher.Tell(ctx, node1.TopicActor(), message)

Last updated