Question

In applications following DDD I worked on, we tend to have a Service Layer that contains the Services + Repositories + the interfaces for repositories and services, they all live in the same assembly, while the domain model will live in a different assembly. It feels like everything that doesn't fit the domain model is cluttered in this one big project.

In an application that follows DDD principles and patterns, how do you package the repositories and the interfaces they implement? What are the best practices for packaging different logical parts of DDD application (or packaging in general for that matter)? Should every logical partition live in its own assembly? Does it even matter?

Was it helpful?

Solution

I would look at the Onion Architecture. Basically all domain model and interfaces for domain services are considered core. Layers depend only on layers above them that are closer to the core. Their actual implementation is handled by infrastructure.

See here http://jeffreypalermo.com/blog/the-onion-architecture-part-1/

Ultimately your interfaces are what defines your application. The logic of how that gets implemented is externalised. So I'd expect you to have assemblies with Domain Models and domain services, a front end (e.g. MVC etc) and then an infrastructure assembly that implements things like NHibernate for providing data etc.

You can see various samples that implement the architecture in the various parts of the linked article. The simplest one is here https://bitbucket.org/jeffreypalermo/onion-architecture/get/1df2608bc383.zip

You can see questions related to it here https://stackoverflow.com/questions/tagged/onion-architecture

The main benefit is that it is largely the infrastructural concerns that will change the most often. New data layer technologies, new file storage, etc. Also your core domain should be reasonably stable as it isn't implementing anything just defining by contract(interfaces) what it requires. By putting the implementation concerns in one location you minimise the amount of changes that will be required across your assemblies.

OTHER TIPS

You can find guidelines for designing your layers in the DDD book. You've basically got :

  • Domain
  • Infrastructure
  • Application
  • UI

Services come in 3 kinds : Application layer service, Infrastructure layer service and Domain layer service, depending on what the service does. As for the Repositories, their contracts (interfaces) often reside in the Domain while their concrete implementations are in the Infrastructure layer.

Regarding assemblies, I'd recommend at least one per layer. Assemblies and dll's are all about reusability, separation of concerns and decoupling - will I be able to pick that dll and drop it to reuse it in another application ? Will I be able to do so without dragging along a bunch of unrelated features that will bring unnecessary complexity to that other application ? Will I be able to substitute my dll easily for another one by just changing one line of code in my dependency injection module ? and so on.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top