If I have an Order class an as aggregate root and 1000 line items.
How do I load just one of the 1000 line items? As far as I understand, a line item can only be accessed through the Order class and has a “local” identity. Would I still create a repository method at the OrderRepository like “GetLineItemById”?
Edit to comment the answer:
Currently I don’t think it’s reasonable to have an immutable children. What if I have an Customer class with several addresses, contracts and even more child collections. A huge entity I want to perform CRUD methods on.
I would have
public class Customer
{
public IEnumerable<Address> Addresses { get; private set; }
public IEnumerable<Contracts> Contracts { get; private set; }
...
}
Would I have to do something like this if a user corrects the street of an address or a property of a contract?
public class Customer
{
public void SetStreetOfAddress(Address address, street){}
public void SetStreetNumberOfAddress(Address address, streetNumber){}
}
The customer class would be full of child manipulation methods then. So I would rather do
addressInstance.Street = "someStreet";
I think I am misunderstanding the whole concept.. 🙂
The important thing is to make sure that all interactions with children are mediated by the aggregate root so that there’s a single, predictable place to guarantee invariants.
So
Order.LineItemsis fine, as long as it returns an immutable collection of (publicly) immutable objects. LikewiseOrder.LineItems[id]. For an example see the source for the canonical Evans-approved ddd example, where the aggregate rootCargoclass exposes several of its children, but the child entites are immutable.If you have "the blue book" (Domain-Driven Design), see the example on page 127, which shows how you might have
Car.Engine, where bothCarandEngineare aggregate roots, but an engine isn’t part of a car’s aggregate and you can’t make changes to an engine using any of the methods ofCar(or vice-versa).Customerclass you proposed sounds like it shouldn’t be an aggregate root at all – just a regular class that holds references toContractandAddressaggregates.