Let's say we have a write model (domain) that generates two events:
- CarrierAdded(...)
- BusConnectionCreated(carrier, ...)
Carrier and BusConnection classes are (part of) separate aggregates. BusConnection is assigned to a Carrier and contains its CarrierId (separate aggregates are referenced only by id).
Everything is fine both in write model and read model during the normal flow of commands and events, but the problem appears when we want to rebuild/add new read model from scratch.
Many people suggests (e.g. akka-persistence library) that events are stored per aggregate in the event store. When the denormalizer asks for events to be replied he gets two independent stream of events from each of the aggregates. The problem is that some events from different aggregates like in the example above needs to be replied in the same order they were added to the event store. That means we need some kind of causal dependencies / partial ordering.
And finally my questions:
- Should I rethink my design of the domain (bad aggregate boundaries?) or
- Do I need only to enforce the partial ordering?
If the latter, what is the most efficient way to do that?
- Global counters? Don't seem to be scalable.
- Some kind of vector clocks?
- Detect such problems in denormalizer when they appear? E.g. we got CarrierId, we don't have the CarrierAdded event with this id yet, so we stash the event and wait for the expected one first
- Introduce some order in terms of processing the events in the replay mode? E.g. all events concerning Carriers first, BusConnection related events later?