2015-07-16 8 views
0

Я хотел бы реализовать простые интерфейсы IGenericRepository и IUnitOfWork в моем приложении, но я не уверен, что это лучший способ сделать это.Единица работы и шаблон хранилища

Насколько я понял, UnitOfWork следует использовать для записи, в то время как репозиторий должен использоваться для чтения. Я столкнулся с одной архитектурой, и мне это очень нравится, но я нашел интерфейсы, а не реализации, и я не уверен, как их реализовать.

public interface IGenericRepository : IDisposable 
{ 
    IUnitOfWork CreateUnitOfWork(); 
    T FirstOrDefault<T>(Expression<Func<T, bool>> predicate) where T : class, IBaseEntity; 
    IQueryable<T> Get<T>(Expression<Func<T, bool>> predicate = null, Func<IQueryable<T>, IOrderedQueryable<T>> sorter = null, params string[] includeProperties) where T : class, IBaseEntity; 
    IQueryable<T> GetAll<T>() where T : class, IBaseEntity; 
    IDbContext GetDbContext(); 
} 

public interface IUnitOfWork : IDisposable 
{ 
    int Commit(); 
    bool Delete<T>(T entity) where T : class, IBaseEntity; 
    int DeleteItems<T>(IList<T> entities) where T : class, IBaseEntity; 
    bool Insert<T>(T entity) where T : class, IBaseEntity; 
    int InsertItems<T>(IList<T> entities) where T : class, IBaseEntity; 
    bool Update<T>(T entity) where T : class, IBaseEntity; 
    int UpdateItems<T>(IList<T> entities) where T : class, IBaseEntity; 
} 

Я не уверен, как это должно работать. Должен ли я использовать IDbContextFactory в репозитории для совместного использования DbContext между репозиторием и UnitOfWork или у них должны быть отдельные DbContexts? Если я реализую UnitOfWork для записи и репозитория для чтения, должен ли быть модуль UnitOfWorks DbContext для записи и репозитория DbContext для чтения, или они должны делиться одним и тем же DbContext?

Я бы очень признателен за хорошее объяснение того, как должны работать DbContext и UnitOfWork/Repository.

Те будут реализованы в процессе эксплуатации таким образом:

public CustomerService(IGenericRepository repository) 
{ 
    this.repository = repository; 
    this.context = this.repository.GetDbContext(); 
} 

public void UpdateCustomer(Customer customer) 
{ 
    var uow = this.repository.CreateUnitOfWork(); 
    uow.AddForSave(customer); 
    uow.Commit(); 
} 

public List<Customer> GetAll() 
{ 
    return this.repository.GetAll<Customer>(); 
} 

Любая помощь, объяснение о DbContext и UOW/Repository отношения, или хороший учебник, подобной этой реализации поможет.

С уважением.

+1

'UnitOfWork следует использовать для записи, в то время как репозиторий следует использовать для чтения. Я никогда не слышал об этом. – Jonesopolis

+0

Не нужно как« обязано », но рекомендуется для многих обновлений сущностей (один объект может быть обновлен с помощью репозитория) , Хотя есть много отличных шаблонов для использования репозитория для обоих, но я хотел бы придерживаться этого. – zhuber

+0

@Disappointed имеет хорошую ссылку для вас. Но имейте в виду, что шаблоны UoW и Repository очень обсуждаются, некоторые говорят, что они устарели. Конечно, в среде EF/MVC, где DbContext и DbSet уже выполняют большую часть этой функции. –

ответ

1

Я думаю, this - это то, что вам нужно. Все ваши метки в одной статье)

+0

Это отличная статья. Если вы разместили некоторую релевантную информацию со связанной страницы, она может даже квалифицироваться как достойный ответ. –

+0

Привет, я видел этот учебник, но я бы пропустил настройки репозиториев как свойства UoW и вместо этого получил UoW из репозитория, используя контекст, введенный из DbContextFactory. Спасибо, в любом случае! – zhuber

0

Я бы рекомендовал вам избежать шаблона хранилища, конечно же, для вставок/обновлений.

Вы должны рассмотреть «команду/объекты запроса» в качестве альтернативы, вы можете найти кучу интересных статей вокруг этой области, но здесь хороший один:

https://rob.conery.io/2014/03/03/repositories-and-unitofwork-are-not-a-good-idea/

Вы бы придерживаться один командный объект для каждой команды для включения простых транзакций, избегая необходимости в сложности шаблона Unit Of Work.

Однако, если вы думаете, что объект запроса для каждого запроса является излишним, это часто бывает правильным. Вместо этого вы можете начать с объекта FooQueries, который по существу является репозиторием, но только для запросов. «Foo» может быть вашим «агрегированием домена» в смысле DDD.

Позже вы можете обнаружить, что отдельные объекты запросов стоит использовать, если вы хотите добавить проблемы с перекрестными разрезами через атрибуты, вы даже можете подать объект запроса в конвейер.