简体   繁体   中英

DDD persisting aggregate on 2 different databases

I have a Generic IRepository<T> which gets implemented under Infrastructure.NHibernate Using Simple Injector to inject the implementation into the interface. IRepository<T> lives in my Domain so that the domain objects can use the repository which was injected.

I have a User``AggregateRoot which holds some detail about the user in the application database, Id , Firstname , Lastname . I know not to care about persistence, but this at stage we are talking about how these objects are persisted.

In my Web.UI (ASP.Net MVC 5) I have a screen where I can update the user details, Firstname , Lastname , Email , Address . Id is stored but can't be updated.

When I update the User details, I use the IRepository<User> to update Firstname and Lastname .

Problem: I need to update the Firstname , Lastname , Email , Address in our OpenLdap server too.

I have an Infrastructure.Ldap project where all the Ldap implementations etc sits. (repositories, services, entities, helpers, converters).

What is the best approach to update the LDap server?

Do I create another ISomeRepository Interface in the Domain which Infrastructure.Ldap implements? This will mean I need to add additional attributes to the User and just override the ORM Mapping to ignore additional attributes. I then use the IRepository , followed by ISomeRepository to update the user in both databases.

Or

Web.UI is already an infrastructure concern, so I just reference the Infrastructure.Ldap project and talk to the ldap repository directly which will work with a LDapUser object. This will let me update the User on Ldap separately.

I'm very confused, business rules are that we need to update user details. I assume from a DDD perspective, all the details that needs to be updated needs to live in the domain. how do I persist this User on 2 different data stores?

Is one of my options above valid and pass good practice, or is there perhaps a different solution? The business requires there to be the 2 different data stores, therefore I need to make this work.

Id , Firstname , Lastname - this is stored in the application database in case Ldap goes down and will be used for auditing purposes later on.

Id , Firstname , Lastname , Email , Address - this is stored in the OpenLdap server part of user administration.

Can someone please point me into the right direction please. Its really hard to think of this case strictly from a DDD perspective due to he constraints of where persistence needs to happen. If it was all on the application database, it would have been easy.

You can use Composite design pattern with your repositories :

public IRepository<T>
{
    void Save(T entity);
}

public class CompositeRepository<T> : IRepository<T>
{
    private readonly IEnumerable<IRepository<T>> repositories;

    public CompositeRepository(IEnumerable<IRepository<T>> repositories)
    {
        if(repositories == null)
        {
            throw new ArgumentNullException("repositories");
        }
        this.repository = repositories;
    }

    public void Save(T entity)
    {
        foreach(var repository in repositories)
        {
            repository.Save(entity);
        }
    }
}

Let's assume that there exists SqlUserRepository and LdapUserRepository and both implements IRepository<User> . Then you can register CompositeUserRepository using container:

container.RegisterCollection<IRepository<User>>(new[] { typeof(SqlUserRepository), 
                                                         typeof(LdapUserRepository) });
container.Register<IRepository<User>, CompositeRepository<User>>();

Thanks to that your services further use IRepository<User> and they don't have to change when you add persisting User to LDAP . We also achieved nice side effect of that way solving this problem - Single Responsibility principle in context of repositories.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM