Вы действительно подняли здесь вопрос, который в настоящее время вызывает много дискуссий в сообществе разработчиков - см. Последующие комментарии к Должен ли мой репозиторий предоставлять IQueryable?
Хранилище может - и должно - создавать сложные комбинированные объекты, содержащие несколько связанных объектов. В доменном дизайне они называются агрегатами - коллекциями связанных объектов, организованными в некую связную структуру. Ваш код не должен вызывать GetCustomer()
, GetOrdersForCustomer()
, GetInvoicesForCustomer()
отдельно - вы просто вызываете myCustomerRepository.Load(customerId)
, и вы получаете глубокий объект customer с уже созданными экземплярами этих свойств. Я также должен добавить, что если вы возвращаете отдельные объекты на основе определенных таблиц базы данных, то это совершенно правильный подход, но на самом деле это не репозиторий per se - это просто слой доступа к данным.
С одной стороны, существует убедительный аргумент в пользу того, что объекты Linq-to-SQL с их «умными» свойствами и их отложенным выполнением (т.е. без загрузки Customer.Orders, пока вы на самом деле не используете его), являются полностью допустимой реализацией шаблон репозитория, поскольку на самом деле вы не выполняете код базы данных, вы выполняете операторы LINQ (которые затем преобразуются в код БД базовым поставщиком LINQ)
С другой стороны, как указывает пост Мэтта Бриггса, L2S довольно тесно связан с вашей структурой базы данных (один класс на таблицу) и имеет ограничения (например, нет много-много отображений) - и вы можете быть лучше отключите использование L2S для доступа к данным в вашем хранилище, но затем сопоставьте объекты L2S с вашими объектами модели домена и верните их.