Assign

Marks a method as command handler.

A command handler method must:

  • be annotated with @Assign;
  • return an event message derived from EventMessage if there is only one event generated; or an Iterable of event messages for two or more events;
  • accept a command message derived from CommandMessage as the first parameter.

Like other message-handling methods, command handlers are designed to be called by the framework only. Therefore, it is recommended to declare them as package-private. It discourages a developer from calling these methods directly from anywhere.

Package-private access level still declares that a command handler method is a part of the Bounded Context-level API. See the BoundedContext description on how the packages and Bounded Contexts relate.

Accepted Parameters

The first parameter of the command handler always declares a type of the handled command.

A command handler method may accept a CommandContext as the second parameter, if handling of the command requires its context.

@Assign
 TaskCreated handler(CreateTask command) { ... }

@Assign
 TaskCompleted handler(CompleteTask command, CommandContext context) { ... }

In case a command may be rejected, a corresponding Throwable should be declared:

@Assign
 TaskStarted handler(StartTask command) throws TaskAlreadyInProgress { ... }

If the annotation is applied to a method which doesn't satisfy any of these requirements, this method is not considered a command handler and is not registered for command dispatching.

Returning Values

As a command is an imperative, it must lead to some outcome. Typically, a command results in an emission of one or more events. Each of them must derive from EventMessage in order to make the code less error-prone.

A command handler method must return either

  • an event message:
    @Assign
     TaskReassigned on(ReassignTask command) { ... }
    
  • an Iterable of event messages:
    @Assign
    Iterable<TaskCompleted> handler(CompleteProject event) { ... }
    
  • a tuple of event messages; being similar to Iterable, tuples allow to declare the exact types of returning values, including Optional values:
    @Assign
    Pair<ProjectCreated, ProjectAssigned> handlerCreateProject event) { ... }
    
    @Assign
    Pair<TaskCreated, Optional<TaskAssigned>> handler(CreateTask event) { ... }
    
  • one of particular events:
    @Assign
    EitherOf2<TaskRemovedFromProject, TaskDeleted> handler(RemoveTask command) { ... }
    

One Handler per Command

An application must have one and only one handler per command message class. This includes the case of transforming an incoming command into one or more commands that will to be handled instead of the received one.

Declaring two methods that handle the same command class will result in run-time error.

See also

Returning Two or More Event Messages

Returning One of Event Messages

Transforming Commands

Inherited functions

Link copied to clipboard
public abstract Class<? extends Annotation> annotationType()
Link copied to clipboard
public abstract boolean equals(Object p)
Link copied to clipboard
public abstract int hashCode()
Link copied to clipboard
public abstract String toString()