SharpRepository EF5,如何共享dbcontext

时间:2013-03-07 13:57:34

标签: c# entity-framework repository sharp-repository

使用EF5 implementation of SharpRepository,如何在使用RepositoryFactory时在IRepository的不同实例之间共享DBContext?

代码段:

using SharpRepository.Repository;

public class PersonManager()
{

    private IRepository<Domain.PersonIdentifier, int> personIdentifierRepository;
    private IRepository<Domain.NextNumber, string> nextNumberRepository;

    public PersonManager()
    {

        //HOW TO SHARE A SINGLE DBCONTEXT INSTANCE BETWEEN THESE TWO INSTANTIATIONS ??
        this.personIdentifierRepository = RepositoryFactory.GetInstance<Domain.PersonIdentifier, int>();
        this.nextNumberRepository = RepositoryFactory.GetInstance<Domain.NextNumber, string>();

    }

}

Web.config文件:

<sharpRepository>
    <repositories default="EF5Repo">
      <repository name="EF5Repo" connectionString="MyContainer" factory="SharpRepository.Ef5Repository.Ef5ConfigRepositoryFactory, SharpRepository.Ef5Repository" />
    </repositories>
    <cachingProviders default="inmemory">
      <cachingProvider name="inmemory" factory="SharpRepository.Repository.Caching.InMemoryConfigCachingProviderFactory, SharpRepository.Repository" />
    </cachingProviders>
    <cachingStrategies default="noCaching">
      <cachingStrategy name="timeout" timeout="30" factory="SharpRepository.Repository.Caching.TimeoutConfigCachingStrategyFactory, SharpRepository.Repository" />
      <cachingStrategy name="standardCachingStrategy" generational="true" writeThrough="true" factory="SharpRepository.Repository.Caching.StandardConfigCachingStrategyFactory, SharpRepository.Repository" />
      <cachingStrategy name="noCaching" factory="SharpRepository.Repository.Caching.NoCachingConfigCachingStrategyFactory, SharpRepository.Repository" />
    </cachingStrategies>
  </sharpRepository>

由于

1 个答案:

答案 0 :(得分:3)

RepositoryFactory和配置位相对较新,不幸的是现在不包含共享单个DbContext的方法,但我会将其作为一个功能请求添加,只需要考虑制作它的最佳方法发生。

话虽如此,我现在就是这样处理的。在我们实现这个新功能之前,您可以使用Ef5Repository进行硬编码,而不是使用RepositoryFactory。 Ef5Repository的构造函数中的第一个参数是DbContext,因此您可以将同一个参数传递到两个存储库中。

不确定您是否正在使用像StructureMap这样的IOC容器,但如果是这样,您可以将其设置为处理为每个线程或.NET请求创建单个DbContext(如果它是Web应用程序)。

StructureMap配置如下所示:

        // Hybrid (once per thread or ASP.NET request if you’re in a web application)
        For<DbContext>()
           .HybridHttpOrThreadLocalScoped()
           .Use<MyEntities>()
           .Ctor<string>("MyContainer").Is(entityConnectionString);

然后你的PersonManager看起来像:

using SharpRepository.Repository;

public class PersonManager()
{

    private IRepository<Domain.PersonIdentifier, int> personIdentifierRepository;
    private IRepository<Domain.NextNumber, string> nextNumberRepository;

    public PersonManager(DbContext dbContext)
    {
        this.personIdentifierRepository = new Ef5Repository<Domain.PersonIdentifier, int>(dbContext);
        this.nextNumberRepository = new Ef5Repository<Domain.NextNumber, string>(dbContext);

    }

}

不幸的是,此时您正在硬编码存储库的类型并且没有获得配置文件的好处,但我们很快就会在那里获得该功能。感谢。

SharpRepository版本1.2的更新

SharpRepository 1.2版(3/14发布)解决了这个问题。现在您可以告诉SharpRepository您正在使用的IoC容器,它将使用它来创建DbContext。这允许您控制DbContext的生命周期并在多个存储库中共享它。

第一步是获取您正在使用的IoC容器的NuGet包。搜索NuGet for SharpRepository.Ioc,您将看到我们创建并开箱即用的5个IoC软件包(Autofac,Ninject,StructureMap,Unity和Windsor),如果您使用的话,您可以随时创建自己的软件包。我们现在没有涉及的不同IoC。

安装完成后,您需要在App_Start代码,Global.asax或bootstrapper代码中设置RepositoryDe​​pendencyResolver,以便它在应用程序启动时运行。如果使用StructureMap,您将如何操作。

RepositoryDependencyResolver.SetDependencyResolver(new StructureMapDependencyResolver(ObjectFactory.Container));

我告诉它使用StructureMap并传入Container。然后,您只需确保IoC已设置并知道如何处理DbContext的请求。 (参见上面的结构图中使用ASP.NET请求生命周期的示例)