com.github.rahulsom.grooves.queries.internal.JoinExecutor Maven / Gradle / Ivy
package com.github.rahulsom.grooves.queries.internal;
import com.github.rahulsom.grooves.api.AggregateType;
import com.github.rahulsom.grooves.api.events.*;
import com.github.rahulsom.grooves.api.snapshots.internal.BaseJoin;
import io.reactivex.Flowable;
import java.util.List;
import static io.reactivex.Flowable.fromPublisher;
import static io.reactivex.Flowable.just;
/**
* Executes a query as a Join.
*
* @param The Aggregate this join represents
* @param The type for the {@link EventT}'s id field
* @param The base type for events that apply to {@link AggregateT}
* @param The type for the join's id field
* @param The type for the id of the other aggregate that {@link AggregateT}
* joins to
* @param The type for the other aggregate that {@link AggregateT} joins to
* @param The type of Snapshot that is computed
* @param The type of the Join Event
* @param The type of the disjoin event
*
* @author Rahul Somasunderam
*/
public class JoinExecutor<
AggregateIdT,
AggregateT extends AggregateType,
EventIdT,
EventT extends BaseEvent,
JoinedAggregateIdT,
JoinedAggregateT extends AggregateType,
SnapshotIdT,
SnapshotT extends BaseJoin,
JoinEventT extends JoinEvent,
DisjoinEventT extends DisjoinEvent,
QueryT extends BaseQuery
>
extends
QueryExecutor {
private final Class classJoinE;
private final Class classDisjoinE;
public JoinExecutor(Class classJoinE, Class classDisjoinE) {
this.classJoinE = classJoinE;
this.classDisjoinE = classDisjoinE;
}
@Override
public Flowable applyEvents(
QueryT query,
SnapshotT initialSnapshot,
Flowable events,
List> deprecatesList,
AggregateT aggregate) {
// s -> snapshotObservable
return events.reduce(just(initialSnapshot), (s, event) -> s.flatMap(snapshot -> {
if (!query.shouldEventsBeApplied(snapshot)) {
return just(snapshot);
} else {
log.debug(" -> Applying Event: {}", event);
if (event instanceof Deprecates) {
Deprecates deprecatesEvent =
(Deprecates) event;
return applyDeprecates(
deprecatesEvent, query, events, deprecatesList, aggregate);
} else if (event instanceof DeprecatedBy) {
DeprecatedBy deprecatedByEvent =
(DeprecatedBy) event;
return applyDeprecatedBy(deprecatedByEvent, initialSnapshot);
} else if (classJoinE.isAssignableFrom(event.getClass())) {
JoinEventT joinEvent = (JoinEventT) event;
return fromPublisher(joinEvent.getJoinAggregateObservable())
.map(joinedAggregate -> {
initialSnapshot.getJoinedIds().add(joinedAggregate.getId());
return initialSnapshot;
});
} else if (classDisjoinE.isAssignableFrom(event.getClass())) {
DisjoinEventT disjoinEvent = (DisjoinEventT) event;
return fromPublisher(disjoinEvent.getJoinAggregateObservable())
.map(joinedAggregate -> {
initialSnapshot.getJoinedIds().remove(joinedAggregate.getId());
return initialSnapshot;
});
} else {
return just(initialSnapshot);
}
}
})).toFlowable().flatMap(it -> it);
}
}
© 2015 - 2025 Weber Informatics LLC | Privacy Policy