Using forwarding and effects

A command may only act on one entity at a time. Sometimes however, you would like to update multiple entities in a single command. You can accomplish this with forwarding and effects. Forwarding and effects applies to all state models - event sourced entity, replicated entities, and actions.

Forwarding control to another entity

Rather than sending a reply to a command, an entity can forward it to another entity. This is done by sending a forward message back to the proxy, instructing the proxy which call on which entity should be invoked, and passing the message to invoke it with.

The command won’t be forwarded until any state actions requested by the command handler have successfully completed. It is the responsibility of the forwarded action to return a reply that matches the type of the original command handler. Forwards can be chained arbitrarily long.

Emitting effects on another entity

An entity may also emit one or more effects. An effect is something whose result has no impact on the result of the current command—​if it fails, the current command still succeeds. The result of the effect is therefore ignored. Effects are only performed after the successful completion of any state actions requested by the command handler.

Effects may be declared as synchronous or asynchronous. Asynchronous commands run in a "fire and forget" fashion. The code flow of the caller (the command handler of the entity which emitted the asynchronous command) continues while the command is being asynchronously processed. Meanwhile, synchronous commands run in "blocking" mode, that is, the commands are processed in order, one at a time. The final result of the command handler, either a reply or a forward, is not sent until all synchronous commands are completed.

Transactional concerns

It’s important to note that forwarded commands, and commands emitted as side effects, are non-atomic—​there is no guarantee that the transactions either all succeeded or none. If the service implementation or store fails while a forwarded command is executing, the original command that triggered it will not be rolled back.

Hence, forwarding and effects should not be used to update multiple entities at once if partial updates is a problem.