4

I was learning about DDD recently and didn't quite understand the concepts. I have some questions about a sample blog application.

Let's assume that there are four domain objects in the blog system: User, Blog, Post and Comment. One User can have only one Blog, a Blog has multiple Post entities and a Post has many Comment entities.

My design is that Blog is the aggregate root:

class Blog {
    private User;
    private List<Post> posts;
}

class Post {
    private List<Comment> comments;
}

class BlogRepository {
    public void saveBlog(Blog blog);
    public void findBlogById(long id);
    public void getAllBlogs();
}

Am I right to design the aggregate root and repository like this?

I have some requirements to get all the Comment entities added by an user for all Blog entities, and also the User is allowed to modify her/his own Comment.

My question is how can I implement these requirements?

Dave New
  • 38,496
  • 59
  • 215
  • 394
davenkin
  • 131
  • 2
  • 8
  • 1
    Try to avoid thinking any domain modelling like designing a db schema. 1 to 1 or 1 to many relations are typical relational db thinking. They have no place in DDD. – MikeSW Apr 29 '13 at 07:39

1 Answers1

6

While the model you present reflects the domain, it isn't an optimal DDD implementation. With DDD, in addition to considering relationships between entities, you must also consider transactional consistency boundaries. As a result, it would be better to design a Blog, Post and User as separate aggregates which reference each other by ID only. Moreover, there is no reason that the Blog entity needs to have a collections of posts. You will never need to load the entire blog and behaviors never span multiple posts. Instead, provide a paginated repository method to load a subset of posts for a blog. A Comment however can be a value object and so the comments collection should be loaded together with the Post aggregate. The easiest way to get all comments for a user is to create a repository query method which returns a read-model to prevent conflating queries with behavior in your entities. For more on designing aggregates take a look at Effective Aggregate Design.

eulerfx
  • 36,769
  • 7
  • 61
  • 83
  • 3
    Since I'm developing a blog engine using DDD I gave a lot of thought on these matters and I can say that a Comment isn't a value object. It's an entity: the Comment itself has no direct relation to the Post and the Post AR (i'm speaking only about the domain here) doesn't have a reason to know about comments. Posts and Comments are attached to each other but they are quite independent. One can function without other. The read model 'marries' them and even then, only the relevant bits for the context. – MikeSW Apr 29 '13 at 07:28
  • That certainly makes sense. It seems you can evolve from initially modelling a comment as a VO, then when more functionality surrounding comments is called for it can be "promoted" to an AR. – eulerfx Apr 29 '13 at 17:05
  • @MikeSW: does that mean I need to have a CommentRepository? – davenkin May 01 '13 at 00:54
  • 1
    @davenkin While I'd answer 'yes' to your question, it's not because it's a 'need', but because it makes sense to have one. – MikeSW May 01 '13 at 06:41