Last updated
Was this helpful?
Last updated
Was this helpful?
In this section we will discuss using Commands, Events and Queries.
We will start with Commands and Command Handlers. Even so we will be discussing Commands the functionality which we will tackle, applies to Queries
and Events
also.
Understanding this part will give us understanding of the whole.
External Command Handlers
are Services available in Dependency Container, which are defined to handle Commands
. We call them External to differentiate from Aggregate Command Handlers, which will be described in later part of the section.
In Ecotone we enable Command Handlers using attributes. By marking given method with #[CommandHandler]
we state it should be used as a Command Handler
.
In case of Ecotone the class itself is not a Command Handler, it's a method that is considered to be Command Handler. This way we may join multiple Command Handlers under same class without introducing new classes if that's not needed.
Command Handlers
are methods where we would typically places our business logic.
In above example using #[CommandHandler]
we stated that createTicket
method will be handling CreateTicketCommand
.
The first parameter of Command Handler method is indicator of the Command Class we want to handle, so in this case it will be CreateTicketCommand
.
Now whenever we will send this CreateTicketCommand
using Command Bus
, it will be delivered to createTicket
method.
We send Command using Command Bus.
After Ecotone is installed all Buses are available out of the box in Dependency Container, this way we may start using them directly after installation.
In order to use the Command we first need to define it:
All Messages (Command/Queries/Events) just like Message Handlers (Command/Query/Event Handlers) are simple Plain old PHP Objects, which means they do not extend or implement any framework specific classes. This way we keep our business code clean and easy to understand.
To send an Command we will be using send
method on CommandBus
.
Command will be delivered to corresponding Command Handler.
We may send Command with Metadata
(Message Headers) via Command Bus.
This way we may provide additional information that should not be part of the Command or details which will be reused across Command Handlers
without copy/pasting it to each of the related Command
classes.
#[Header]
provides information that we would like to fetch metadata which is under executorId
. This way Ecotone knows what to pass to the Command Handler.
If we need additional Services (which are available in Dependency Container) to perform our business logic, we may pass them to the Command Handler using #[Reference]
attribute:
In case Service is defined under custom id in DI, we may pass the reference name to the attribute:
There may be cases where creating Command classes is unnecessary boilerplate, in those situations, we may simplify the code and make use scalars
, arrays
or non-command classes
directly.
Ecotone provides flexibility which allows to create Command classes when there are actually needed. In other cases we may use routing functionality together with simple types in order to fulfill our business logic.
It happens that after performing action, we would like to return some value. This may happen for scenarios that require immediate response, for taking an payment may generate redirect URL for the end user.
The returned data will be available as result of the Command Bus.
Take under consideration that returning works for synchronous Command Handlers. in case of asynchronous scenarios this will not be possible.
If we use Command Handler, Ecotone will ensure our metadata will be serialized and deserialized correctly.
In Ecotone we may register Command Handlers under routing instead of a class name.
This is especially useful if we will register to tell Ecotone how to deserialize given Command. This way we may simplify higher level code like Controllers
or Console Line Commands
by avoid transformation logic.
Ecotone is using message routing for . This way applications can stay decoupled from each other, as there is no need to share the classes between them.
Commands CQRS PHP