Как обработать разбиение на страницы под-сущностей с помощью шаблона репозитория? - PullRequest
5 голосов
/ 28 августа 2011

Я изучаю предметно-ориентированный дизайн.В настоящее время я пытаюсь написать простое приложение на C #, проектируя его с использованием DDD.Это приложение имеет совокупный корень A, который может содержать 0..n дочерних объектов B. Это может быть представлено чем-то вроде:

class A {
    public int Id { get; }
    public IList<B> { get; }
}

с хранилищем:

class ARepository {
    public A Get(int id) { ... }
    public void SaveOrUpdate(A root) { ... }
    public void Delete(A root) { ... }
}

Однако я хотел бы добавить подкачку при представлении суб-сущностей B для данного экземпляра A.Как бы я поступил так?Лучшее, что я могу придумать, это изменить A и ARepository на что-то вроде:

class A {
    public int Id { get; }
}

class ARepository {
    public A Get(int id) { ... }
    public void SaveOrUpdate(A root) { ... }
    public void Delete(A root) { ... }

    public IList<B> GetBForA(A root, int offset, int pageSize, out int numPages) { ... }
}

Это бы сработало, конечно, но я бы потерял простоту и элегантность модели предметной области.

Какова лучшая практика для обработки подстраниц с помощью шаблона репозитория?Я не ищу, как справиться с этим, используя определенные библиотеки и т. Д., А скорее, как справиться с этим на «уровне шаблона».

Ответы [ 2 ]

3 голосов
/ 29 августа 2011

Краткий ответ: вы не должны делать это так. Цель репозитория - сделать доступ к объектам домена явным. Они не должны использоваться для отображения данных в целях пользовательского интерфейса. Это совершенно другая роль, которую я называю Finder . Зачем? Вы не хотите загрязнять свой домен (репозиторий принадлежит домену) такими понятиями пользовательского интерфейса, как пейджинг. Вы можете найти более подробное объяснение здесь , в моем блоге.

0 голосов
/ 29 августа 2011

Если вы используете ORM, такой как NHibernate, вы можете достичь этого, установив лениво загруженное свойство коллекции (IList) и охотно выбирая требуемую страницу или критерии для самого объекта вместо репозитория. например:

var a = ARepository.Get(1);
var secondPageOfBs = a.BList.AsQueryable()
                                          .OrderBy(c => c.Name)
                                          .Skip(PageSize * 2)
                                          .Take(PageSize)
                                          .ToList();

Вы также можете построить эти запросы в хранилище и получить результат в доменном объекте, например:

var a = ARepository.GetWithPagedChildren(1, PageSize * 2, PageSize);

вы также можете создавать более сложные запросы, как описано: http://ayende.com/blog/4367/eagerly-loading-entity-associations-efficiently-with-nhibernate

...