Ols*_*sen 6 c# entity-framework repository repository-pattern objectcontext
我的应用程序中有多个存储库.我应该把ObjectContext放在哪里?现在,我ObjectContext ctx;在每个存储库中都有一个引用.什么是最聪明,最安全的方法?
sma*_*man 10
ObjectContext只有在Repository方法提交事务时,才能接受具有多个实例的设计.否则,提交事务的外部调用可能无法保留您想要的所有内容,因为您将保留对该实例的不同实例的引用ObjectContext.
如果要将数据限制ObjectContext为单个实例,则可以构建一个RepositoryProvider包含该实例的类ObjectContext,并管理存储库操作到数据提交的传播.这可以通过以下任一方式实现: - 将ObjectContext引用注入每个存储库,或者 - 将存储库的事件订阅到EventHandler调用适当方法的s ObjectContext.
以下是我使用的高度可插拔的实现:
public interface IRepositoryProvider
{
IRepository this[Type repositoryType] { get; }
}
Run Code Online (Sandbox Code Playgroud)
实现依赖于IEnumerable<IFilteredRepositoryFactory>.
public interface IFilteredRepositoryFactory{
bool CanCreateRepository(Type repositoryType);
IRepository CreateRepository(Type repositoryType, ObjectContext context);
}
Run Code Online (Sandbox Code Playgroud)
所以,实现看起来像:
public class RepositoryProvider
{
public RepositoryProvider(ObjectContext context, IEnumerable<IFilteredRepositoryFactory> repositoryFactories)
{
_context = context;
_repositoryFactories = repositoryFactories;
}
private readonly ObjectContext _context;
private readonly IEnumerable<IFilteredRepositoryFactory> _repositoryFactories;
private readonly Dictionary<Type, IRepository> _loadedRepositories;
IRepository this[Type repositoryType]
{
get
{
if(_loadedRepositories.ContainsKey(repositoryType))
{
return _loadedRepositories[repositoryType];
}
var repository = GetFactory(repositoryType).CreateRepository(repositoryType, _context);
_loadedRepositories.Add(repositoryType,repository);
return repository;
}
}
IFilteredRepositoryFactory GetFactory(Type repositoryType)
{
//throws an exception if no repository factory is found
return _repositoryFactories.First(x => x.CanCreateRepository(repositoryType));
}
}
Run Code Online (Sandbox Code Playgroud)
应该注意的Repository是,第一个匹配的工厂实现将创建一个新的.因此,如果工厂集合包含可以Repository为给定存储库创建的多个工厂,则将使用可枚举中Type的第一个IFilteredRepositoryFactory对象,并且将忽略任何后续工厂.另外,如果没有注册工厂,则会抛出异常.