I recently went through a real learning experience WRT DDD. It was one of those fundamental first step type of learning experiences which I want to record because it’s something I can’t afford to forget.
So, I am currently playing the role of architect in a larger organisation than I am used to, with all the trappings that you would expect; red tape, “committee-ism” etc. The application I am “architecting”, will be complex and big. We are going through the initial period of POCs and discovery in an attempt to mitigate the risk of the unknown. It’s a good move by James (the proj manager).
So, we were going through the motions of deciding how things will fit together and I while I am trying to keep things as simple as possible, I know that transaction scripts as a solution across the board are just not going to cut it. Enter DDD. I have been chomping at the bit for an opportunity to implement DDD in a situation that truly warrants the effort.
Straight off the bat we are also implementing CQRS as it’s easy and the value I believe is just immense. More on that in another post perhaps. So we have a read and write side, with commands being sent via an in-memory bus on the write side.
I initially presented the expected archicture:
MVC Controller == sends command ==> Command Handler
where the command handler behaves as an Application Service. It may access the database and perform basic functionality.
THIS IS MY VIEW AT THE TIME, IS NOT DDD. THIS IS TRANSACTION SCRIPTS, WITH THE COMMAND HANDLER BEHAVING AS A CLASSIC SERVICE.
The second part of the puzzle was that when things get “more complicated” we will opt to “implement DDD”, in which case:
MVC Controller == sends command ==> Command Handler ==> Invokes functionalty in Aggregate Root
So, the logic moves from the Transaction Script into the Aggregate when justified.
The mistake I made was that I was considering one option as “being DDD” and the other as “not being DDD”.
I felt off about all this. It was gnawing at me; I know I had something wrong. My “thing” is really focussing on delivery and doing the responsibly most simple thing which solves a given problem; but the way that DDD slotted in or not just felt like I was missing something. Doing DDD, not doing DDD… that line was going to get blurry and DDD would become a blunt instrument. Not ideal.
I consulted the DDD Immersion discussion group and shamelessly let me noobness show to all the world. I posed a question asking how aggressively people would implement DDD in a greenfields project. I got one gracious response from Ariel Valantin, who asked me some good questions. Answering them got me on the right track. I decided to trawl through the discussion group in search of answers. I came across a discussion between Eric and another chap and the crux of the thing was that the guy had a bad model and Eric helped him distill it into something more valuable.
En-route to the distilled model, it was clear that Eric was not concerned with things that were not “domain level concerns” as opposed to “application level concerns”. The behaviour of the system, for that BC, was in aggregates and modelled accordingly. These concerns are the “domain level concerns”. The other “stuff” just didn’t make it into the model. It was just updated / deleted or whatever directly from the application services because it didn’t contribute to the model and there was no behavior associated.
The lesson here? IT’S ALL DDD! There is no switching it on and off; it’s just GOOD DESIGN.
MAKE SURE THE BEHAVIOR RELEVANT TO THE BC IS MODELED. LEAVE THE BENIGN BORING CRAP OUT OF IT, AND TAKE CARE OF THOSE “APPLICATION LEVEL CONCERNS” OUTSIDE OF THE MODEL – THEY WILL JUST MUDDY THE INTENT OF THE MODEL ANYWAY.
So, in my context, what did this mean? Well, the command handlers are free to take care of application level concerns. But, in a given bounded context, make sure that the BEHAVIOUR relevant to the BC is modeled, and pushed into the building blocks as appropriate.
I feel so much better now. Perhaps very obvious in hindsight, but it was a mindset thing. Glad I got it now.
Link to my noobness on DDD Immersion Discussion Group: https://groups.google.com/d/topic/ddd-immersion-alumni/zLl1iJxvJTU/discussion. Note: mostly for me as you will need to be a member of the DDD Immersion Alumni to have access.