Question

I'm modeling a very basic ASP.NET MVC app using NHibernate and I seem to be stuck on my design. Here's a sketch of my model:

model 1

As you can see this is VERY basic but I have some concerns about it. The User root entity and the Organization root entity are accessing the same Organization_Users entity child via two one-to-many relationships. This doesn't seem right and I think I am breaking the aggregate boundaries. This model smells to me but I like the idea because I would like to have code like this:

var user = userRepository.Load(1);
var list = user.Organizations; // All the organizations the user is a part of.

and

var org = orgRepository.Load(1);
var list = org.Users; // All the users in an organization.

Also the extra data in the table like flagged and role would be used by the Organization entity. Is this a bad design? If you have any thoughts that would be great. I'm still trying to get my mind around the thinking of DDD. Thanks

Was it helpful?

Solution

I have used an approach similar to your first model on several occasion. The one catch with this approach is that you need to create an OganizationUser class in your domain to handle the Role and Flagged fields from you Domain. This would leave you with something like this in your code.

var user = userRepository.Load(1);
var list = user.OrganizationUsers; // All the organizations the user is a part of including their role and flagged values.

var organization = list[0].Organization; 

*If you're going to be iterating through all a users organizations quite often you'd likely want to eager load the Organization entity along with OrganzitionUser

With the second design you submitted it looks like you would be able to add a user to the OrgUserDetails without adding the user to OrganizationUser. That doesn't seem like something I would want to support from my Domain.

OTHER TIPS

This is a typical Many-To-Many relationship. And the Organization_Users tables is the bridge table. Infact NHibernate and all the other ORM tools have built-in feature to support bridge table.

This thing should be resolved at data modelling level rather than at application level. You should analyze your data model and it is recommended to avoid many-to-many relationships (in the sense if it is not the necesity of domain model, you should try to avoid many-to-many relationship).

First thing first you need to be sure that many-to-many relationship in data model is necessary for mapping domain entities. Once you have done this then the model represented in your diagram is ok for mapping those relationships at application level

The first things to consider in DDD are :

  • forget your database schema (there's no database !)
  • what actions will you perform on thoses entities from a domain perspective ?

I think your model is fine. I usually think of domain aggregate roots, when I think of them at all, in terms of what is publicly exposed, not internal implementation. With relationships I think of which entity "wears the pants" in the relationship. That is, is it more natural to add a User to an Organization or add an Organization to a User? In this case both may make sense, a User joins an Organization; an Organization accepts a User for membership.

If your domain sees the relationship from the User's perspective, you can put the methods to maintain (add, remove, etc.) the relationship on the User and expose a read-only collection on the Organization.

In response to your second design (it would have been better if you had edited the original question): I don't like it at all. Your original design is fine. I wouldn't necessarily ignore the database while designing your classes, a good design should accurately model the domain and be straightforward to implement in a relational database. Sometimes you have to compromise in both directions to hit the sweet spot. There's no jail term for breaking aggregate boundaries. :-)

My understanding is:

A User can belong to 0-to-many Organizations. AND An Organization consists of 0-to-many Users.

Are both of those correct? If so, that does sound like a many-to-many to me.

In a many-to-many, you pretty much need a relationship-like object of some sort to bridge that gap. The problem is, there is no user_organization in the domain.

This makes me think you shouldn't have user_organization as a part of your domain, per se. It feels like an implementation detail.

On the other hand, maybe it makes sense in your domain to have a Roster which holds the Users in an Organization and stores their role and other information specific to that relationship.

Thanks everyone for your answers. They have been very helpful.

While I was thinking about my model a little bit more, I sketched something new that I think would be better.

alt text

My thinking was this:

  1. When a user logs into the site the system finds their account and then returns a list of organizations they are apart of and it gets this info from the user_organizations object.

  2. When a user clicks on one of the organizations they are apart of it directs them to the organization's control panel.

  3. The selected organization then looks up that user's role in its org_user_details to know what access the user should have to that organizations control panel.

Does that make sense? :)

I feel like that would be good in a model but I'm having some doubts about the DB implementation. I know I shouldn't even worry about it but I can't break my bad habit yet! You can see that there is kind of duplicate data in the user_organizations object and the org_user_details object. I'm not a DB pro but is that a bad DB design? Should I instead combine the data from user_organizations and org_user_details into a table like the one in my first post and just tell NHibernate that User looks at it as a Many-to-Many relationship and Organization looks at it as a One-to-Many relationship? That sounds like I'm tricking the system. Sorry if I seemed really confused about this.

What are your thoughts on this? Am I over thinking this? :P

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