unique validation in DDD

I have a question regarding checking of uniqueness in DDD. I know already have some questions about this on stackoverflow, but they don't really answer my doubt

Is it possible for an aggregate root to hold reference of repository to check the uniqueness when updating/inserting to database? Or this is the task done by application service instead of domain model?

Let's say I want to check whether username of User model is unique when user register There are several approaches that I can think of:

  • User model reference UserRepository, do the uniqueness checking in Validate()
  • Create a domain service to do uniqueness checking, using UserRepository (this seems a bit odd for me because I think normally domain service is used only in case the logic span to more than one domain models)
  • Create a specification object in domain layer, with reference to UserRepository to encapsulate unique checking rule, and application service layer use this to do the checking before update/insert
  • And if I use dependency injection, I'm still wondering about how to inject UserRepository into User in approach 1, or domain service in approach 2, or application service in approach 3, because in any case, for User/domain service/specification object, I need to instantiate the object manually, so the only option I have seem to be using service locator in IoC to get instance. But service locator is an anti-pattern so I want to avoid it

    Any sample code will be much appreciated


    I think that checking for uniqueness falls into Repository responsibility. Repository knows about all aggregates because it suppose to simulate domain collection, so it is natural to ask Repository for uniqueness (like you would expect from HashMap for example).

    // repository
    interface Users {
      // implementation executes SQL COUNT in case of relation DB
      bool IsNameUnique(String name);
    
      // implementation will call IsNameUnique and throw if it fails
      void Add(User user);
    }
    

    It is a leaky abstraction in a sense because in a multiuser environment this need to be enforced on a data store side (UNIQUE SQL constraint for example, or locking).

    IsNameUnique should probably not be called from User aggregate, I would move this call into Application or Domain Service, depending on how rest of your application is structured.

    See Uniqueness validation in CQRS Architecture for alternative approach.

    链接地址: http://www.djcxy.com/p/71722.html

    上一篇: 如何使用`local`和`Reader` monad和Scrap您的Boilerplate(SYB)?

    下一篇: 独特的DDD验证