Hi Allard,
Thanks for your answer !
Ok in DDD transaction boundaries are limited to one aggregate, and so we can only have eventual consistency in processing involving multiple aggregates, but I wonder if in some use cases we should not consider that aggregate boundaries change (not static) between use cases, at least conceptually.
For ex, in this article : http://www.udidahan.com/2009/06/29/dont-create-aggregate-roots/ Udi says that most of the time new aggregates are created from another one, that can also perform some checking during the creation process (in his exemple check that name contains no space).
For exemple in my application, the administrator can register new Users (Aggregate Root), but the login and email must be unique among all users in the repository.
Eventual consistency could be a problem here, as for example the “retrieve lost password from email” function wouldnt work if 2 users had the same email at the same time (low probability but still exists)
Does it make sense to have another higher level aggregate root “UserRegistry” that handle the creation of new users ? In that use case (user creation), the aggregate root would not be User but UserRegistry. And in another use case that doesn’t involve the modification of the user email, the aggregate root would be the User.
So, even if statically the 2 classes are declared as AggregateRoot (no choice as java is a static language), conceptually I wonder if in fact aggregate root boundaries should depend on use case, and if so, could we use axon framework this way, by making an AR “UserRegistry” handle the creation of another AR “User”, in the same transaction (no eventual consistency in this case) ?
In fact in this use case, the UserRegistry should not contains the collections of all Users as it would be inefficient. It should contains only the minimum info : UserId and email.
So in fact the user in the registry is not the same “User” class, but a “UserRegistryEntry”, that is not an AR, but an entity.
In this case we would call “registerNewUser” on the registry first, and an EventHandler would then create the User AR (in separate transactions)
But my problem here is that I would like to ensure that the only way to create a new User is to call a command on the UserRegistry AR, and not directly on the User AR. If a new developper in the team find a command “create” on the User AR, he could be tempted to use it without knowing that he must use the “registerNewUser” of the UserRegistry AR.
Regards,
Mael