如何使用NHibernate在单个应用程序中连接到多个数据库?

Anshu

我们需要连接到两个Oracle数据库和一个DB2数据库。我们正在将NHibernate 5与Oracle Managed Data Access for Oracle一起使用。尽管有一些可用资源,但其中大多数都已经很旧了。

我们使用单个数据库没有问题,但是从来没有使用多个数据库。我仍然不知道如何开始。如果有人可以分享一些见解或一些示例代码,将不胜感激。

阿米特·乔希

要为ISessionFactory每个数据库创建和维护单独的实例是必经之路。因此,在您的情况下,您将有三个实例。我已经在我的一个应用程序中实现了此功能,在该应用程序中,我使用三个不同的RDBMS连接到三个数据库。

如您所说,您已经使用单个数据库和NHibernate,我认为不需要任何特定的代码。相同,只是多个会话工厂实例。无论如何,我已经在答案的末尾复制了我的代码。

创建ISession实例时,请确保要从要连接的会话工厂实例创建它。您其余的应用程序保持不变。

请注意,而像记录它可能会创建一个问题,一个我面对。但是,那只是一个。其他一切都顺利,没有问题。

样例代码:

注意:以下代码中的某些类型不是NHibernate类型。那些是他们的包装。名称相似;因此理解代码应该没有问题。

public sealed class NHSessionFactory
{
    /*
     * This must be instance class.
     * New instance should be created for each Database Schema.
     * Maintain the instance in calling application.
     * This is useful if multiple databases are used in one application.
    */
    NHSessionFactoryInternal nhSessionFactoryInternal = null;

    public void Start(NHSessionFactoryStartParams startParams)
    {
        Configuration nhConfiguration;
        nhConfiguration = new Configuration();

        nhConfiguration.SetProperty(NHibernate.Cfg.Environment.Dialect, startParams.Dialect);
        nhConfiguration.SetProperty(NHibernate.Cfg.Environment.ConnectionString, startParams.ConnectionString);
        if(string.IsNullOrEmpty(startParams.DefaultSchema) == false)
            nhConfiguration.SetProperty(NHibernate.Cfg.Environment.DefaultSchema, startParams.DefaultSchema);
        nhConfiguration.SetProperty(NHibernate.Cfg.Environment.Isolation, "ReadCommitted");
        nhConfiguration.SetProperty(NHibernate.Cfg.Environment.BatchSize, NHSettings.DefaultBatchSize.ToString());
        if(string.IsNullOrEmpty(startParams.LogFilePath) == false)
        {
            nhConfiguration.SetProperty(NHibernate.Cfg.Environment.ShowSql, "true");
            nhConfiguration.SetProperty(NHibernate.Cfg.Environment.FormatSql, "true");
        }
        else
        {
            nhConfiguration.SetProperty(NHibernate.Cfg.Environment.ShowSql, "false");
            nhConfiguration.SetProperty(NHibernate.Cfg.Environment.FormatSql, "false");
        }
        nhConfiguration.AddMapping(startParams.HbmMappingInstance);

        try
        {
            nhSessionFactoryInternal = new NHSessionFactoryInternal();
            nhSessionFactoryInternal.CreateSessionFactory(nhConfiguration);
        }
        catch(Exception exception)
        {
            Stop();
            throw new NHWrapperException("Failed to create session factory.", exception);
        }
    }

    public void Stop()
    {
        if(nhSessionFactoryInternal == null)
            return;

        nhSessionFactoryInternal.CloseSessionFactory();
        nhSessionFactoryInternal = null;
    }

    public INHSession CreateSession(bool readOnly)
    {
        if(nhSessionFactoryInternal == null)
            throw new NHWrapperException("NHWrapper is not started.");

        return nhSessionFactoryInternal.CreateNHSession(readOnly);
    }
}

下面是NHSessionFactoryInternal上面代码中使用class的实现您可以毫无问题地结合使用这两个类。我在那里还有其他部分。所以我更喜欢把它分开。

internal sealed class NHSessionFactoryInternal
{
    ISessionFactory sessionFactory;
    internal ISessionFactory SessionFactory { get { return sessionFactory; } }

    internal void CreateSessionFactory(Configuration nhConfiguration)
    {
        if(sessionFactory != null)
            throw new NHWrapperException("SessionFactory is already created.");

        try
        {
            sessionFactory = nhConfiguration.BuildSessionFactory();
        }
        catch(Exception exception)
        {
            throw new NHWrapperException("Failed to build session factory.", exception);
        }
    }

    internal INHSession CreateNHSession(bool readOnly = false)
    {
        if(sessionFactory == null)
            throw new NHWrapperException("Session factory is not build.");
        return new NHSession(sessionFactory.OpenSession(), NHSettings.DefaultFlushMode, readOnly);
    }

    internal void CloseSessionFactory()
    {
        if(sessionFactory == null)
            return;
        if(sessionFactory.IsClosed == false)
            sessionFactory.Close();
        sessionFactory.Dispose();
        sessionFactory = null;
    }
}

本文收集自互联网,转载请注明来源。

如有侵权,请联系 [email protected] 删除。

编辑于
0

我来说两句

0 条评论
登录 后参与评论

相关文章

C#使用多个应用程序使用实体框架连接单个数据库

流星服务器专用Web应用程序连接到多个数据库

如何在Rails 4中的单个Rails应用程序中访问多个数据库?

在整个应用程序中使用单个数据库连接?

Android:从应用程序中的多个活动访问单个数据库?

如何使用JPA连接到多个数据库?

如何将多个应用程序连接到Firestore数据库

如何从Android应用程序连接到多个Firebase数据库

一个 Web 应用程序中的多个数据库连接 - java

如何使用连接字符串从Winform应用程序连接到Godaddy中的SQL Server数据库

如果您想使用 SQLAlchemy 将多个数据库连接到各种应用程序,那么组织模型、连接的好方法是什么?

如何使用Meteor Up(mup)中的MONGO_URL env变量使流星应用程序连接到数据库?

如何使用IP白名单将Heroku上的应用程序连接到Atlas中的数据库?

如何将MySQL数据库连接到Java中的GWT应用程序?

如何使用JNDI将Java应用程序连接到数据库?

如何使用Php将Android应用程序连接到Amazon RDS MySQL数据库?

如何使用Hibernate检查在多个数据库应用程序中是否正确设置了必要的特权?

如何使用套接字将Windows C#,Android和浏览器连接到一个数据库。(聊天应用程序)

创建具有多个数据库的单个应用程序

NHibernate中的多个数据库驱动程序

在RUNTIME时从Spring Boot应用程序中的两个相同数据库连接到一个数据库

是否可以在Azure中设置可连接到多个本地数据库的Web应用程序?

应用程序连接多个数据库并设置成员身份Cookie

如何允许Tomcat连接到多个数据库?

无法将应用程序连接到数据库

在单个脚本中连接多个数据库的利弊

在 Scala 中连接到多个数据库

如何在Android应用程序的单个数据库中创建两个表?

如何在多个程序包之间共享单个数据库连接