Events

The events mechanism in Ergo Framework is built on top of the pub/sub subsystem. It allows any process to become an event producer, while other processes can subscribe to these events. This enables flexible event-driven architectures, where processes can publish and consume events across the system.

Producer

To register an event (gen.Event), you use the RegisterEvent method available in the gen.Process or gen.Nodeinterface. When registering an event, you can configure the following parameters using the gen.EventOptions:

  • Notify: This flag controls whether the producer should be notified about the presence or absence of subscribers for the event. If notifications are enabled, the process will receive a gen.MessageEventStart message when the first subscriber appears and a gen.MessageEventStop message when the last subscriber unsubscribes. This allows the producer to generate events only when there are active subscribers. If the event is registered using the RegisterEvent method of the gen.Node interface, this field is ignored.

  • Buffer: This specifies how many of the most recent events should be stored in the event buffer. If this option is set to zero, buffering is disabled.

The RegisterEvent function returns a token of type gen.Ref upon success. This token is used to generate events. Only the process that owns the event, or a process that has been delegated the token by the event owner, can produce events for that registration.

To generate events, the gen.Process interface provides the SendEvent method. This method accepts the following arguments:

  • name: The name of the registered event (gen.Atom).

  • token: The key obtained during the event registration (gen.Ref).

  • message: The event payload, which can be of any type.

It's important to note that the RegisterEvent method is not available to a process during its initialization state.

To generate events, the gen.Node interface provides the SendEvent method. This method is similar to the SendEventmethod in the gen.Process interface but includes an additional parameter, gen.MessageOptions. This extra parameter allows for further customization of how the event message is sent, such as setting priority, compression, or other message-related options.

Consumer

To subscribe to a registered event, the gen.Process interface provides the following methods:

  • LinkEvent: This method creates a link to a gen.Event. The process will receive an exit signal if the producer process of the event terminates or if the event is unregistered. To remove the link, use the UnlinkEvent method. When the link is created, the method returns a list of the most recent events from the producer's buffer.

  • MonitorEvent: This method creates a monitor on a gen.Event. The process will receive a gen.MessageDownEventif the producer process terminates or if the event is unregistered. If the event is unregistered, the Reason field in gen.MessageDownEvent will contain gen.ErrUnregistered. To remove the monitor, use the DemonitorEventmethod.

Both methods accept an argument of type gen.Event. For an event registered on the local node, you only need to specify the Name field, and you can leave the Node field empty. This simplifies subscribing to local events while still providing flexibility for handling events from remote nodes.

type myActor {
    act.Actor
}
...
func (a *myActor) HandleMessage(from gen.PID, message any) error {
    ...
    // local event
    event := gen.Event{Name: "exampleEvent"}
    lastEvents, err := a.LinkEvent(event)
    ...
    // remote event
    event := gen.Event{Name: "remoteEvent", Node: "remoteNode"}
    lastEvents, err := a.LinkEvent(event)
}

Upon successfully creating a link or monitor, the function returns a list of events (gen.MessageEvent) provided by the producer process from its message buffer. Each event contains the following information: the event name (gen.Event), the timestamp of when the event was generated (obtained using time.Now().UnixNano()), and the actual event value sent by the producer process. If the list of events is empty, it means that either the producer process has not yet generated any events or the producer registered the event with a zero-sized buffer.

For an example demonstrating the capabilities of the events mechanism, you can refer to the events project in the ergo-services/examples repository:

Last updated