Class AggregateDeadlineCommandTranslator
- All Implemented Interfaces:
ScopeAware
DeadlineMessage scoped to an AggregateScopeDescriptor into a command, dispatched
through a CommandGateway.
Implements ScopeAware so it can be reached through a ScopeAwareProvider the same way a Saga manager
is. Its send(Message, ProcessingContext, ScopeDescriptor) dispatches the deadline's payload and metadata as
a command named <aggregateType>.<deadlineName>: a QualifiedName with the
aggregate type as namespace and the deadline's
DeadlineMessage.getDeadlineName() as local name. It writes the AggregateScopeDescriptor's identifier
into the dispatched command's metadata under
"scope-descriptor-based-entity-identifier".
AggregateDeadlineEntityIdResolverConfigurationEnhancer registers the resolver that reads this metadata entry
as the application-wide default, used whenever the command's payload carries no @TargetEntityId.
Naming the command after the aggregate type and the deadline keeps deadlines apart that share a payload type, such
as two deadlines carrying a UUID, and deadlines of different aggregate types that share a name. The aggregate
type is the one Axon Framework 4 stored with the deadline: the aggregate's simple class name, unless its
@Aggregate annotation set another type. The migrated handler of a deadline with a payload becomes
@CommandHandler(commandName = "<aggregateType>.<deadlineName>") void handle(<Payload> payload, ...). A
deadline scheduled without a payload carries null as its Message.payload(), and is dispatched with
the deadline name as its payload instead, so its handler becomes
@CommandHandler(commandName = "<aggregateType>.<deadlineName>") void handle(String deadlineName, ...).
Handlers migrated with an earlier version of this translator are named after the deadline's payload type, or after the deadline name alone for a deadline without a payload. To keep them working, a deadline that finds no handler for its qualified name is dispatched again under that earlier name, and a warning asks to rename the handler.
Constructed and registered by the AggregateDeadlineCommandTranslatorConfigurationEnhancer.
- Since:
- 5.4.0
- Author:
- Steven van Beelen
- See Also:
-
Constructor Summary
ConstructorsConstructorDescriptionAggregateDeadlineCommandTranslator(CommandGateway commandGateway) Initializes anAggregateDeadlineCommandTranslator, dispatching translated commands through the givencommandGateway. -
Method Summary
Modifier and TypeMethodDescriptionbooleancanResolve(ScopeDescriptor scopeDescription) Check whether this implementation can resolve aScopeobject based on the providedscopeDescription.voidsend(Message message, ProcessingContext context, ScopeDescriptor scopeDescription)
-
Constructor Details
-
AggregateDeadlineCommandTranslator
Initializes anAggregateDeadlineCommandTranslator, dispatching translated commands through the givencommandGateway.- Parameters:
commandGateway- theCommandGatewayto dispatch a fired aggregate deadline's command through
-
-
Method Details
-
canResolve
Check whether this implementation can resolve aScopeobject based on the providedscopeDescription. Will returntruein case it should be able to resolve the Scope andfalseif it cannot.Returns
truefor everyAggregateScopeDescriptor, regardless of the aggregate type it describes, since routing to the right entity is delegated to the dispatched command's@TargetEntityId, not resolved here.- Specified by:
canResolvein interfaceScopeAware- Parameters:
scopeDescription- aScopeDescriptordescribing theScopeto be resolved- Returns:
truein case it should be able to resolve the Scope andfalseif it cannot
-
send
public void send(Message message, ProcessingContext context, ScopeDescriptor scopeDescription) throws Exception Send aMessageto aScopewhich is described by the givenscopeDescription.Dispatches the
message's payload and metadata as a command named after the aggregate type of thescopeDescriptionandDeadlineMessage.getDeadlineName(), through the configuredCommandGateway, passing the givencontextalong so the command runs within the deadline's firing unit of work. Waits for the command's result withFutureUtils.joinAndUnwrap(java.util.concurrent.CompletableFuture), rethrowing a failure so the caller applies its own failure handling.When the command bus has no handler for that name, the
messageis dispatched again under the name an earlier version of this translator used, for handlers migrated with it: named after the payload's type, or after the deadline name alone for amessagewithout a payload.A
messagewhose payload is anUnknownDeadlinePayload(its stored type could not be resolved) is not dispatched: this method logs a warning naming the deadline, the stored type and the aggregate scope, and returns.A
messagewhose payload isnullis dispatched withDeadlineMessage.getDeadlineName()as its payload.The dispatched command's metadata always carries the
scopeDescription's identifier under "scope-descriptor-based-entity-identifier", so the target entity can be resolved from it instead of from the payload.- Specified by:
sendin interfaceScopeAware- Parameters:
message- TheMessageto be sent to aScope.context- TheProcessingContextin which themessageis being processed.scopeDescription- ADextendingScopeDescriptor, describing theScopeto send the givenmessageto.- Throws:
IllegalArgumentException- if the givenmessageis not aDeadlineMessage, or if the givenscopeDescriptionis not anAggregateScopeDescriptorException- if sending themessagefailed. Might occur if the message handling process throws an exception.
-