В нашем проекте мы используем репозиторий, который ведет себя как набор сущностей, а UnitOfWork используется для отслеживания изменений в этих сущностях и для записи их обратно в хранилище данных.
Если вы используете LinqToSql или какой-либо другой OR Mapper, то, скорее всего, он реализует сам шаблон UnitOfWork, поэтому часто мы просто используем экземпляр ORMapper в нашем собственном IUnitOfWork.
Интерфейс нашего репозитория обычно похож на ..
IEnumerable<Order> FindByCustomerId(string customerId);
void Add(Order order);
void Remove(Order order);
У нас нет метода сохранения в репозитории. Если нам не нужен UnitOfWork, то методы Add / Remove действуют непосредственно в хранилище данных.
Если нам нужен UnitOfWork, тогда общедоступный интерфейс - это что-то вроде ...
void Commit();
void Rollback();
Репозиторий имеет внутренний интерфейс с UnitOfWork, поэтому, когда мы запрашиваем репозиторий, возвращаемые объекты отслеживаются UnitOfWork на предмет изменений. Метод commit записывает изменения обратно в хранилище данных, а метод отката просто очищает их изменения.
Когда мы используем LinqToSql, DataContext заботится об отслеживании изменений, при откате мы просто создаем новый контекст. Настойчивость обрабатывается через корень и его детей. Один экземпляр UnitOfWork является общим для всех репозиториев.
Когда мы не используем LinqToSql, тогда мы реализуем наш собственный UnitOfWork, может быть, он вызывает веб-сервис или что-то еще, в этом случае мы отслеживаем изменения в самих классах сущностей, используя класс EntityBase.
У нас есть репозиторий для каждого корня, но иногда дочерние элементы одного корня сами используются в качестве корней, поэтому нам часто нужно что-то вроде OrderLineRepository, потому что в нашей системе есть вариант использования, в котором пользователь хочет найти Order линии.