This is a handler where commands are received and delivered to the addressed aggregate. Such a handler is called an application service. This is the "write" side in CQRS.
An application service is a command handler for a specific aggregate. One aggregate has one application service whose purpose is to orchestrate how commands will be fulfilled. Its the application service's responsibility to invoke the appropriate aggregate methods and pass the command's payload. It mediates between Domain and infrastructure and it shields any domain model from the "outside". Only the application service interacts with the domain model.
You can create an application service with Cronus by using the AggregateRootApplicationService
base class. Specifying which commands the application service can handle is done using the ICommandHandler<T>
interface.
AggregateRootApplicationService
provides a property of type IAggregateRepository
that you can use to load and save the aggregate state. There is also a helper method Update(IAggregateRootId id, Action update)
that loads and aggregate based on the provided id invokes the action and saves the new state if there are any changes.
You can/should/must...
an application service can load an aggregate root from the event store
an application service can save new aggregate root events to the event store
an application service can establish calls to the read model (not a common practice but sometimes needed)
an application service can establish calls to external services
you can do dependency orchestration
an application service must be stateless
an application service must update only one aggregate root. Yes, you can create one aggregate and update another one but think twice before doing so.
You should not...
an application service should not update more than one aggregate root in a single command/handler
you should not place domain logic inside an application service
you should not use an application service to send emails, push notifications etc. Use a port or a gateway instead
an application service should not update the read model