Class AggregateRoot<ID,EVENT_TYPE extends Event<ID>,AGGREGATE_TYPE extends AggregateRoot<ID,EVENT_TYPE,AGGREGATE_TYPE>>
- java.lang.Object
-
- dk.cloudcreate.essentials.components.eventsourced.aggregates.stateful.classic.AggregateRoot<ID,EVENT_TYPE,AGGREGATE_TYPE>
-
- Type Parameters:
ID- the aggregate id typeEVENT_TYPE- the type of eventAGGREGATE_TYPE- the aggregate self type (i.e. your concrete aggregate type)
- All Implemented Interfaces:
Aggregate<ID,AGGREGATE_TYPE>,StatefulAggregate<ID,EVENT_TYPE,AGGREGATE_TYPE>
- Direct Known Subclasses:
AggregateRootWithState
public abstract class AggregateRoot<ID,EVENT_TYPE extends Event<ID>,AGGREGATE_TYPE extends AggregateRoot<ID,EVENT_TYPE,AGGREGATE_TYPE>> extends Object implements StatefulAggregate<ID,EVENT_TYPE,AGGREGATE_TYPE>
A specialized and opinionated mutableAggregatedesign
ThisAggregateRootis designed to work with Class based Event's that inherit fromEvent.
This design is deliberate and will manage a lot of things for you as a developer at the cost of some flexibility.Specifically you only have to supply the Aggregate ID, through
Event.aggregateId(), on the FIRST/initialEventthat's being applied to theAggregateRootusing theapply(Event)method.
Every consecutiveEventapplied will automatically have itsEvent.aggregateId(Object)method called IF it doesn't already have a value.
I.e. you can be lazy and skip setting the aggregate id on the Event if you don't want to.
TheAggregateRootalso automatically keeps track of theEvent.eventOrder()value and will set it for you and ensure that it's consecutively growing.Note: The
AggregateRootworks best in combination with theStatefulAggregateRepositoryYou don't have to use the
AggregateRootIF it doesn't fit your purpose. It's always possible to build your ownAggregateconcept.- See Also:
AggregateRootWithState
-
-
Constructor Summary
Constructors Constructor Description AggregateRoot()
-
Method Summary
All Methods Instance Methods Concrete Methods Modifier and Type Method Description IDaggregateId()The id of the aggregate (aka.protected voidapply(EVENT_TYPE event)Apply a new non persisted/uncommitted Event to this aggregate instance.
If it is the very FIRSTEventthat is being applied thenEvent.aggregateId()MUST return the ID of the aggregate the event relates to
Every consecutiveEventapplied will have itsEvent.aggregateId(Object)method called IF it doesn't already have a value.protected voidapplyEventToTheAggregateState(Event<ID> event)Apply the event to the aggregate instance to reflect the event as a state change to the aggregate
The default implementation will automatically call any (private) methods annotated withEventHandlerdk.cloudcreate.essentials.components.eventsourced.eventstore.postgresql.types.EventOrdereventOrderOfLastAppliedEvent()Get theof the last {}@link Eventthat was applied to theAggregateRoot(either usingrehydrate(AggregateEventStream)/rehydrate(Stream)or usingapply(Event)dk.cloudcreate.essentials.components.eventsourced.eventstore.postgresql.types.EventOrdereventOrderOfLastRehydratedEvent()Get the eventOrder of the last event during aggregate hydration (using theAggregate.rehydrate(AggregateEventStream)method)EventsToPersist<ID,EVENT_TYPE>getUncommittedChanges()The the events that have been applied to this aggregate instance but not yet persisted to the underlyingEventStorebooleanhasBeenRehydrated()Hasrehydrate(Stream)orrehydrate(AggregateEventStream)been usedprotected voidinitialize()Initialize the aggregate, e.g.protected booleanisRehydrating()Is the event being supplied toapplyEventToTheAggregateState(Event)a previously persisted (i.e.voidmarkChangesAsCommitted()Resets thegetUncommittedChanges()- effectively marking them as having been persisted and committed to the underlyingEventStoreAGGREGATE_TYPErehydrate(dk.cloudcreate.essentials.components.eventsourced.eventstore.postgresql.eventstream.AggregateEventStream<ID> persistedEvents)Effectively performs a leftFold over all the previously persisted events related to this aggregate instanceAGGREGATE_TYPErehydrate(Stream<EVENT_TYPE> previousEvents)Effectively performs a leftFold over all the previous events related to this aggregate instance
-
-
-
Method Detail
-
initialize
protected void initialize()
Initialize the aggregate, e.g. setting up state objects,PatternMatchingMethodInvoker, etc.
-
rehydrate
public AGGREGATE_TYPE rehydrate(dk.cloudcreate.essentials.components.eventsourced.eventstore.postgresql.eventstream.AggregateEventStream<ID> persistedEvents)
Effectively performs a leftFold over all the previously persisted events related to this aggregate instance
-
rehydrate
public AGGREGATE_TYPE rehydrate(Stream<EVENT_TYPE> previousEvents)
Effectively performs a leftFold over all the previous events related to this aggregate instance- Parameters:
previousEvents- the previous events related to this aggregate instance, aka. the aggregates history- Returns:
- the same aggregate instance (self)
-
eventOrderOfLastRehydratedEvent
public dk.cloudcreate.essentials.components.eventsourced.eventstore.postgresql.types.EventOrder eventOrderOfLastRehydratedEvent()
Description copied from interface:AggregateGet the eventOrder of the last event during aggregate hydration (using theAggregate.rehydrate(AggregateEventStream)method)- Specified by:
eventOrderOfLastRehydratedEventin interfaceAggregate<ID,EVENT_TYPE extends Event<ID>>- Returns:
- the event order of the last applied
EventorEventOrder.NO_EVENTS_PREVIOUSLY_PERSISTEDin case no events has ever been applied to the aggregate
-
apply
protected void apply(EVENT_TYPE event)
Apply a new non persisted/uncommitted Event to this aggregate instance.
If it is the very FIRSTEventthat is being applied thenEvent.aggregateId()MUST return the ID of the aggregate the event relates to
Every consecutiveEventapplied will have itsEvent.aggregateId(Object)method called IF it doesn't already have a value. I.e. you can be lazy and skip setting the aggregate id on the Event if you don't want to.The
AggregateRootautomatically keeps track of theEvent.eventOrder()value and will set it for you and ensure that it's growing consecutively.- Parameters:
event- the event to apply
-
aggregateId
public ID aggregateId()
Description copied from interface:AggregateThe id of the aggregate (aka. the stream-id)- Specified by:
aggregateIdin interfaceAggregate<ID,EVENT_TYPE extends Event<ID>>
-
hasBeenRehydrated
public boolean hasBeenRehydrated()
Hasrehydrate(Stream)orrehydrate(AggregateEventStream)been used- Specified by:
hasBeenRehydratedin interfaceAggregate<ID,EVENT_TYPE extends Event<ID>>
-
isRehydrating
protected final boolean isRehydrating()
Is the event being supplied toapplyEventToTheAggregateState(Event)a previously persisted (i.e. a historic event)
-
applyEventToTheAggregateState
protected void applyEventToTheAggregateState(Event<ID> event)
Apply the event to the aggregate instance to reflect the event as a state change to the aggregate
The default implementation will automatically call any (private) methods annotated withEventHandler- Parameters:
event- the event to apply to the aggregate- See Also:
isRehydrating()
-
eventOrderOfLastAppliedEvent
public dk.cloudcreate.essentials.components.eventsourced.eventstore.postgresql.types.EventOrder eventOrderOfLastAppliedEvent()
Get theof the last {}@link Eventthat was applied to theAggregateRoot(either usingrehydrate(AggregateEventStream)/rehydrate(Stream)or usingapply(Event)- Returns:
- the event order of the last applied
EventorEventOrder.NO_EVENTS_PREVIOUSLY_PERSISTEDin case no events has ever been applied to the aggregate
-
getUncommittedChanges
public EventsToPersist<ID,EVENT_TYPE> getUncommittedChanges()
The the events that have been applied to this aggregate instance but not yet persisted to the underlyingEventStore- Specified by:
getUncommittedChangesin interfaceStatefulAggregate<ID,EVENT_TYPE extends Event<ID>,AGGREGATE_TYPE extends AggregateRoot<ID,EVENT_TYPE,AGGREGATE_TYPE>>- Returns:
- the changes to the aggregate
-
markChangesAsCommitted
public void markChangesAsCommitted()
Resets thegetUncommittedChanges()- effectively marking them as having been persisted and committed to the underlyingEventStore- Specified by:
markChangesAsCommittedin interfaceStatefulAggregate<ID,EVENT_TYPE extends Event<ID>,AGGREGATE_TYPE extends AggregateRoot<ID,EVENT_TYPE,AGGREGATE_TYPE>>
-
-