Let's say that we have an Entity
(the Root
) with a property identifier
, and another Entity
(a child / local entity to Root
) with a property name
, with the rule that the Child
's name must start with the Root
identifier. There is a changeIdentifier
operation and a renameChild
operation, and the Child::name
property must always be consistent with the Root
identifier.
The renameChild
operation, after checking the validity of the new name, raises a ChildRenamed
domain event, containing the Root
and the Child
identities and the new name value.
The chengeIdentifier
operation changes the Root
's identifier and raises a RootIdentifierChanged
event, then goes on and changes all the Child
's names. What should happen now? Should ChildRenamed
events be raised or not? And are importantly, why? What is the rationale behind one choice or the other? I guess the answer also depends on the event being raised from the Root
or the Child
.
class Root extends AggregateRoot {
private GUID _identity
private name _identifier
private Collection<Child> _children
function changeIdentifier(newIdentifier: string): void {
oldIdentifier = _identifier
_identifier = newIdentifier
addDomainEvent(new RootIdentifierChanged(_identity, _identifier))
// this...
// raises `ChildRenamed` events
for (child in _children) {
newName = child.name().replace(oldIdentifier, _identifier, STR_START)
renameChild(child.identity(), newName)
}
// ... or this
// no `ChildRenamed` events raised
for (child in _children) {
newName = child.name().replace(oldIdentifier, _identifier, STR_START)
child.rename(newName)
}
// ... or event this?
// `ChildRenamed` events raised or not depending on
// `renameAfterRootIdentifierChange` implementation
for (child in _children) {
child.renameAfterRootIdentifierChange(_identifier)
}
}
function renameChild(childIdentity: GUID, newName: string): void {
checkRule(new ChildNameIsConsistent(_identifier, newName))
child = _children.find(fn(child) => child.identity().is(childIdentity))
child.rename(newName) // the event is not raised here, in the child...
// ... but here, in the root
addDomainEvent(new ChildRenamed(_identity, child.identity(), newName))
}
}
question from:
https://stackoverflow.com/questions/65887683/should-operations-on-aggregate-root-that-cause-changes-in-child-entities-raise-t 与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…