Database 使用Fluent NHibernate和;结构图

Database 使用Fluent NHibernate和;结构图,database,asp.net-mvc-3,fluent-nhibernate,structuremap,multi-tenant,Database,Asp.net Mvc 3,Fluent Nhibernate,Structuremap,Multi Tenant,我目前正在使用StructureMap将一个NHibernateRegistry实例注入到我的DAL中,该实例为单个连接字符串配置NHibernate,并为我的单用户应用程序引导SingletonFluentConfiguration 如何根据路由URL中的{tenant}路由参数修改Fluent NHibernate配置以使用不同的数据库 路由示例: …其中对branch1/Home/Index和branch2/Home/Index的请求使用相同的应用程序代码,但不同的数据库检索显示的数据 过

我目前正在使用StructureMap将一个
NHibernateRegistry
实例注入到我的DAL中,该实例为单个连接字符串配置NHibernate,并为我的单用户应用程序引导Singleton
FluentConfiguration

如何根据路由URL中的
{tenant}
路由参数修改Fluent NHibernate配置以使用不同的数据库

路由示例: …其中对
branch1/Home/Index
branch2/Home/Index
的请求使用相同的应用程序代码,但不同的数据库检索显示的数据

过去,我通过注入每个请求
TenantContext
对象解决了StructureMap和LINQ的这个问题,该对象从
HttpContext
中检索路由参数,它被接受为构造函数参数,并指定了不同的LINQ数据上下文

然而,我怀疑NHibernate在处理这件事上比我想象的更好

部分
NHibernateRegistry
class
我是NHibernate的新手,所以我不确定我的会话和配置的范围。NHibernate有内置的方法来处理这个问题吗?

这在a模块中对我很有效

return Fluently.Configure()
            .Database(MsSqlConfiguration.MsSql2008.ConnectionString(x => x.FromConnectionStringWithKey("IMB"))
            .Cache(c => c.UseQueryCache().QueryCacheFactory<StandardQueryCacheFactory>()
                         .RegionPrefix("IMB")
                         .ProviderClass<HashtableCacheProvider>()
                         .UseMinimalPuts()).UseReflectionOptimizer())
            .Mappings(m => m.FluentMappings.AddFromAssembly(Assembly.Load("IMB.Data")))
           .Mappings(m => m.FluentMappings.AddFromAssembly(Assembly.Load("IMB.Security")))

           .ExposeConfiguration(
            c => c.SetProperty("current_session_context_class", "web"))
            .ExposeConfiguration(cfg => _configuration = cfg)
            .BuildSessionFactory();
流畅地返回。Configure()
.Database(MsSqlConfiguration.MsSql2008.ConnectionString(x=>x.fromConnectionString WithKey(“IMB”))
.Cache(c=>c.UseQueryCache().QueryCacheFactory())
.RegionPrefix(“IMB”)
.ProviderClass()
.useMimimminPuts()).UseReflectionOptimizer())
.Mappings(m=>m.FluentMappings.AddFromAssembly(Assembly.Load(“IMB.Data”))
.Mappings(m=>m.FluentMappings.AddFromAssembly(Assembly.Load(“IMB.Security”))
.曝光配置(
c=>c.SetProperty(“当前会话上下文类”、“web”))
.ExposeConfiguration(cfg=>_configuration=cfg)
.BuildSessionFactory();

这在a模块中对我很有效

return Fluently.Configure()
            .Database(MsSqlConfiguration.MsSql2008.ConnectionString(x => x.FromConnectionStringWithKey("IMB"))
            .Cache(c => c.UseQueryCache().QueryCacheFactory<StandardQueryCacheFactory>()
                         .RegionPrefix("IMB")
                         .ProviderClass<HashtableCacheProvider>()
                         .UseMinimalPuts()).UseReflectionOptimizer())
            .Mappings(m => m.FluentMappings.AddFromAssembly(Assembly.Load("IMB.Data")))
           .Mappings(m => m.FluentMappings.AddFromAssembly(Assembly.Load("IMB.Security")))

           .ExposeConfiguration(
            c => c.SetProperty("current_session_context_class", "web"))
            .ExposeConfiguration(cfg => _configuration = cfg)
            .BuildSessionFactory();
流畅地返回。Configure()
.Database(MsSqlConfiguration.MsSql2008.ConnectionString(x=>x.fromConnectionString WithKey(“IMB”))
.Cache(c=>c.UseQueryCache().QueryCacheFactory())
.RegionPrefix(“IMB”)
.ProviderClass()
.useMimimminPuts()).UseReflectionOptimizer())
.Mappings(m=>m.FluentMappings.AddFromAssembly(Assembly.Load(“IMB.Data”))
.Mappings(m=>m.FluentMappings.AddFromAssembly(Assembly.Load(“IMB.Security”))
.曝光配置(
c=>c.SetProperty(“当前会话上下文类”、“web”))
.ExposeConfiguration(cfg=>_configuration=cfg)
.BuildSessionFactory();

问题在于,您确实希望您的
ISessionFactory
对象是一个单例对象。这意味着在创建
ISessionFactory
时最好不要指定连接字符串。您是否尝试过在不指定连接字符串的情况下创建
ISessionFactory
,然后将手动创建的连接传递到
ISessionFactory.OpenSession

例如:

public ISession CreateSession()
{
    string tennantId = GetTennantId();
    string connStr = ConnectionStringFromTennant(tennantId);
    SqlConnection conn = new SqlConnection(connStr);
    conn.Open();
    session = sessionFactory.OpenSession(conn);
}
然后告诉StructureMap调用此方法


缺点是,您现在无法在创建
ISessionFactory
时构建数据库模式,但也许在web应用程序中创建数据库模式并不是一个好主意?

问题是您确实希望您的
ISessionFactory
对象是一个单例对象。这意味着在创建
ISessionFactory
时最好不要指定连接字符串。您是否尝试过在不指定连接字符串的情况下创建
ISessionFactory
,然后将手动创建的连接传递到
ISessionFactory.OpenSession

例如:

public ISession CreateSession()
{
    string tennantId = GetTennantId();
    string connStr = ConnectionStringFromTennant(tennantId);
    SqlConnection conn = new SqlConnection(connStr);
    conn.Open();
    session = sessionFactory.OpenSession(conn);
}
然后告诉StructureMap调用此方法


缺点是,在创建
ISessionFactory
时,您现在无法从构建数据库模式开始,但也许在web应用程序中创建数据库模式并不是一个好主意?

谢谢,我将尝试一下。所有的
.RegionPrefix(“IMB”)
(可能是租户id)都是NHibernate的本地内容吗?否.RegionPrefix是fn用于处理缓存实体的缓存前缀仔细检查后,这不会影响基于任何租户id的连接字符串。这是一个多租户解决方案吗?对不起,我误解了你的问题。你可以试试这个。你从哪里给你的说唱歌手打电话?全球。尽快?谢谢,我来试一试。所有的
.RegionPrefix(“IMB”)
(可能是租户id)都是NHibernate的本地内容吗?否.RegionPrefix是fn用于处理缓存实体的缓存前缀仔细检查后,这不会影响基于任何租户id的连接字符串。这是一个多租户解决方案吗?对不起,我误解了你的问题。你可以试试这个。你从哪里给你的说唱歌手打电话?global.asax?
public ISession CreateSession()
{
    string tennantId = GetTennantId();
    string connStr = ConnectionStringFromTennant(tennantId);
    SqlConnection conn = new SqlConnection(connStr);
    conn.Open();
    session = sessionFactory.OpenSession(conn);
}