序
本文次要钻研一下JESA的EventRecorder
EventRecorder
JESA/src/main/java/Jesa/EventRecorder.java
public class EventRecorder{ private final ArrayList records; public EventRecorder() { this.records = new ArrayList(); } public void record(Object event) throws IllegalArgumentException { if(event == null) throw new IllegalArgumentException("The event can not be null."); this.records.add(event); } public Object[] toArray() { return this.records.toArray(); } public void clear() { this.records.clear(); } public boolean hasEvents() { return !records.isEmpty(); }}
EventRecorder定义了records,提供了record、clear、hasEvents、toArray办法
InstanceEventRouter
JESA/src/main/java/Jesa/InstanceEventRouter.java
public interface InstanceEventRouter { <T> void configureRoute(Class<T> eventClass, Consumer<T> eventHandler) throws IllegalArgumentException; void route(Object event) throws IllegalArgumentException;}
InstanceEventRouter接口定义了configureRoute、route办法
Entity
JESA/src/main/java/Jesa/Entity.java
public class Entity implements InstanceEventRouter { private final Consumer<Object> eventApplier; private final InstanceEventRouter router; public Entity(Consumer<Object> eventApplier) { if(eventApplier == null) throw new IllegalArgumentException("eventApplier cannot be null"); this.eventApplier = eventApplier; this.router = new EventRouter(); } @Override public <T> void configureRoute(Class<T> eventClass, Consumer<T> eventHandler) throws IllegalArgumentException { if(eventClass == null) throw new IllegalArgumentException("eventClass cannot be null"); if(eventHandler == null) throw new IllegalArgumentException("eventHandler cannot be null"); router.configureRoute(eventClass, eventHandler); } @Override public void route(Object event) throws IllegalArgumentException { if(event == null) throw new IllegalArgumentException("Cannot route a null event"); router.route(event); } protected void apply(Object event) { if(event == null) throw new IllegalArgumentException("Cannot apply a null event"); eventApplier.accept(event); }}
Entity实现了InstanceEventRouter接口,其configureRoute、route办法代理给了router
AggregateRootEntity
JESA/src/main/java/Jesa/AggregateRootEntity.java
public interface AggregateRootEntity extends AggregateInitializer, AggregateTrackChanges {}public interface AggregateInitializer { void initialize(Iterable<Object> events);}public interface AggregateTrackChanges { /** * Does this aggregate instance have state changes. * @return true if this aggregate instance has changes, else false. */ boolean hasChanges(); /** * Get the changes applied to this instance * @return an iterable sequence of events that have been applied. */ Object[] getChanges(); /** * Clears the events. */ void clearChanges();}
AggregateRootEntity接口继承了AggregateInitializer、AggregateTrackChanges接口
AggregateRootEntityBase
JESA/src/main/java/Jesa/AggregateRootEntityBase.java
public abstract class AggregateRootEntityBase implements AggregateRootEntity { private final EventRecorder eventRecorder; private final InstanceEventRouter eventRouter; protected AggregateRootEntityBase() { eventRecorder = new EventRecorder(); eventRouter = new EventRouter(); } public void initialize(Iterable<Object> events) { if(events == null) throw new IllegalArgumentException("Argument Events cannot be null"); if(hasChanges()) throw new IllegalArgumentException("Cannot initialize an AggregateRootEntity that already has changes."); for(Object event : events) { play(event); } } public <T> void register(Class<T> eventType, Consumer<T> handler) { if(handler == null) throw new IllegalArgumentException("Argument handler cannot be null"); eventRouter.configureRoute(eventType, handler); } public boolean hasChanges() { return eventRecorder.hasEvents(); } public Object[] getChanges() { return eventRecorder.toArray(); } public void clearChanges() { eventRecorder.clear(); } protected void applyChange(Object event) { if(event == null) throw new IllegalArgumentException("The event cannot be null."); beforeApplyChanges(event); play(event); record(event); afterApplyChanges(event); } protected void beforeApplyChanges(Object event) {} protected void afterApplyChanges(Object event) {} private void play(Object event) { eventRouter.route(event); } private void record(Object event) { eventRecorder.record(event); }}
AggregateRootEntityBase申明实现AggregateRootEntity接口,其initialize办法遍历events,挨个执行eventRouter.route(event);其applyChange办法先后执行beforeApplyChanges、play、record、afterApplyChanges办法
Aggregate
JESA/src/main/java/Jesa/Aggregate.java
public class Aggregate { private String identifier; private int expectedVersion; private AggregateRootEntity rootEntity; public Aggregate(String identifier, int expectedVersion, AggregateRootEntity rootEntity) { if(identifier == null) throw new IllegalArgumentException("identifier cannot be null"); if(rootEntity == null) throw new IllegalArgumentException("rootEntity cannot be null"); this.identifier = identifier; this.expectedVersion = expectedVersion; this.rootEntity = rootEntity; } public String getIdentifier() { return identifier; } public int getExpectedVersion() { return expectedVersion; } public AggregateRootEntity getRootEntity() { return rootEntity; }}
Aggregate定义了identifier、expectedVersion、rootEntity属性
小结
JESA的EventRecorder定义了records,提供了record、clear、hasEvents、toArray办法;InstanceEventRouter接口定义了configureRoute、route办法;Entity实现了InstanceEventRouter接口,其configureRoute、route办法代理给了router。
doc
- JESA