DDD Paradoxes

I read Eric Evans' book on DDD years ago and fall asleep with it. Didn't really took much value from it. Last year I read Vaughn Vernon's book on IDDD and I found it more interesting because of the code examples but still too abstract. Too much prose, too thick. One problem with both books is that their written English style is quite sophisticated for a non-native English speaker like me. But I believe there is a lot of value in DDD, so I've read it several times, on kindle and later on paper. My feeling with DDD is still a bit frustrating. I find many contradictions in Vernon's book. But there is a lot of valuable advise in the book I want to benefit from. I should be able to get more value from the book.

This is the first of a series of posts to myself with the idea of better study the subject, trying to summarize the heuristics that I think are going to be more useful for me and hoping the return the investment of time. I want to fix the ideas that I find good.

The following statements are not necessarily in the book literally, this is just what I have in mind and it could just be my interpretation.

Along the book it's advised not to model the domain based on infrastructure concerns, tools or frameworks. However there are sentences where I think it reads: depending on the persistence mechanism you might choose to model a concept as an entity or as value object. Aggregates are specially contradictory. “Aggregate is synonymous with transactional consistency boundary”. Well, transactionality is purely infrastructural so what's the point with aggregates? I believe the chapter on aggregates has very little to do with modeling, but it can be really useful if I can extract a list of architecture/infrastructure problems and solutions, recipes. I just need to extract a list of architecture solutions from that chapter, will do so in an upcoming post.

The distinction between Application Service and Domain Service is hard to see for me. I understand that an Application Service should not contain domain logic, however I am not sure anymore what “domain logic” is after reading some examples of Application Services. I have to dig further into it.

Choosing an Entity or a Value Object is still a hard decision. Apparently Value Objects should be used more often than they are, developers tend to abuse Entities and end up with anemic models. However my impression is that entities are used way more than values along the book. After reading the chapter on Value Objects for the first time, I thought I got it – if I could consider two objects to be equivalent when they had the same field values, they must be value objects. After working with experienced DDD developers in my team and reading the book again, I see I was wrong. I'll focus on the distinction between entities and values in upcoming posts.

This post is going to be updated as I encounter more paradoxes (from my current understanding).

  • theUniC

    Following the discussion on twitter, I think it’s best seen if you think of every aggregate operation as a sequence of relevant events (domain events): usually each event produced in a single aggregate operation in a relevant order represents an state transition, and thus it should be persisted in a single database transaction. I think there’s a 1:1 relation between aggregate operations and database transactions. So I firmly believe that transactionality should be defined as a critical part of the model.

  • http://www.carlosble.com/ Carlos Ble

    Thank you Christian. I see your point. However, If there was just a single user in the application, a transaction wouldn’t be required. It boils down to infrastructure in this case. I guess the model can’t just be totally free from cross-cutting concerns.

  • https://twitter.com/pasku1 Guillermo Pascual

    An aggregate is just a group/set of associated objects that are considered as a
    whole unit with regard to data changes.

    The aggregate is delimited by a consistency boundary that
    separates the internal objects from the external objects. Each aggregate has a root
    object (the root entity) and it’s the only accessible object from the
    outside. The root entity object has references to all of the objects that comprise the
    aggregate, but an external object can only have references to the root entity-object. If
    there are other entities (these could also be value-objects) within the aggregate’s
    boundary, the identity of these entity-objects is only local and they only make sense if
    they belong to the aggregate. They do not make sense if they are isolated.

    The single point of access to the aggregate (root entity) is precisely what ensures
    data integrity (transactionality). From outside the aggregate, there is no access and no change of data to
    the aggregate’s secondary objects, only through the root, which implies a very
    important control level. If the root entity is erased, the rest of the aggregate’s objects
    must also be erased.

  • Pawel Duda

    To me the word ‘transaction’ seems overloaded. First, it denotes the database concept. But second, it also means a set of operations that only make sense together which I believe is a domain concept. I think it would be fine to talk to a banker about a money transfer from A to B being a transaction of removing money to A and adding it to B. Now, I’m not sure if the word ‘transaction’ is the right one, maybe they prefer something else. In that case I would use that other word in my domain code and implement it via DB transaction mechanism in the infrastructure code.

  • http://www.carlosble.com/ Carlos Ble

    You’re right man, the word “transaction” means different things to different people. That has been one of my problems. Thanks for the tip 😉

  • http://www.carlosble.com/ Carlos Ble

    Thanks for the comment. It might be a good summary of the chapter but it’s not very useful for me. Too abstract, I want code and concrete reasons or examples. After studying the chapter several times I will write a post on aggregates from the point of view of the problems it can solve. Given the kind of problem/pattern X, you can design an aggregate like Y to workaround the problem. And I guess most of those problems have to do with architecture/infrastructure. I see the aggregate as a set of techniques to workaround technical problems.