Reputation: 3514
I am having an architecture issue, and I hope someone can point me in the right direction. My problem is: handling DTOs with one-to-many or many-to-many relationships.
I have 5 projects and they should mostly depending to the next one respectively.
But i cannot figure out how they should be referred with each other. I have tried few approach and end up with circular reference. Any suggestions are welcome.
Upvotes: 0
Views: 247
Reputation: 5753
Here is what I would do with what you've described:
Common (shared logic, utility)
|
Model (Business objects, pocos)
|
DAL (Entity Framework -- DbContext definition of Model, migrations etc)
|
Repository (CRUD implementation using DAL context(s))
|
Service Layer (Implementation of business logic, using repositories)
DTO Mappers (Translation of business objects to client consumables using repos)
|
Any API or outward facing interface (webapi, signalr, wcf, mvc)
Usually you use DI to manage these dependencies with some sort of lifetime scope (http request): API -> Service -> Mappers -> Repositories -> DAL.
In my experience I've used the "service" layer to perform unit-of-work operations -- eg. Using the Repository's methods that implement complex and simple queries -> Do business logic -> End UoW -> Return mapped business objects as dto.
Your entity model should be shared throughout. Here are a few resources that might help you develop the architecture right for your application(s)
Hope this helps!
Upvotes: 1
Reputation: 14072
The Domain layer is at the core of your system, as a general rule it shouldn't depend on other modules - i.e. it should be unaware of how domain entities are persisted, presented to the user, communicated to external systems, etc.
The Onion Architecture is a good starting place for a DDD approach.
When faced with a circular reference problem, ask yourself which module is closer to the center of the onion - which one is essential to your domain and which one is a peripheral detail. If module A has to use something in module B which is further away from the center, make it depend on an abstraction of it instead. Declare the abstraction in module A but implement it in module B and inject it at runtime (see Dependency Inversion principle).
Events can also be used to achieve dependency inversion and help a great deal in decoupling your modules.
Upvotes: 0