流畅的NHibernate +多个数据库

时间:2010-04-16 20:19:18

标签: .net nhibernate fluent-nhibernate nhibernate-mapping

我的项目需要处理三个数据库,这意味着三个会话工厂。问题是如果我用流利的nhibernate做这样的事情:

.Mappings(m => m.FluentMappings.AddFromAssembly(Assembly.GetExecutingAssembly()))

工厂将获取所有映射,甚至是与另一个数据库相对应的映射

我已经看到,当使用自动化时,您可以执行类似的操作,并按名称空间进行过滤:

.Mappings(m => m.AutoMappings.Add(
    AutoMap
       .AssemblyOf<Product>()
       .Where(t => t.Namespace == "Storefront.Entities")))

我没有找到这样的流利映射,有可能吗?我能想到的唯一解决方案是:为每个db映射类创建单独的程序集,或者将每个实体显式添加到工厂配置中。

如果可能的话,我宁愿避免这两种情况。感谢。

4 个答案:

答案 0 :(得分:6)

我在Fluent映射文件中使用(我自己的)属性来实现这个,以指示实体所属的DB。我还有一个'默认'数据库的概念,没有属性的映射文件是假设驻留在默认DB中(它可能会减少您需要装饰的类的数量)。 然后我有初始化代码,它为每个数据库创建一个会话工厂,并为每个数据库使用反射来查找所有ClassMap类,检查属性以确定它属于哪个DB,并相应地注册每个ClassMap。

映射文件示例:

  [FluentNHibernateDatabase("MySecurityDatabase")]
  public class SystemUserMap : ClassMap<SystemUser>
  {
    public SystemUserMap()
    {
      Id(x => x.SystemUserId);
      Map(x => x.LoginId);
      Map(x => x.LoginPassword);
      Map(x => x.UserFirstName);
      Map(x => x.UserSurname);
      References(x => x.UserOrganisation, "OrganisationId");
    }
  }

显然我已经定义了引用/使用的DB列表 我的实施工作到目前为止我已经采取了它,但我遇到了障碍(我希望有人可以提供帮助):

我在这里问了我的问题: How to identify a particular entity's Session Factory with Fluent NHibernate and Multiple Databases

答案 1 :(得分:5)

这样做的简单方法是将数据库名称放入Schema

public sealed class CustomerMapping: ClassMap<Customer>
{
    public CustomerMapping()
    {
        Schema("Northwind.dbo");
        Table("Customer");
    }
}

public sealed class Customer2Mapping: ClassMap<Customer2>
{
    public CustomerMapping()
    {
        Schema("Northwind2.dbo");
        Table("Customer");
    }
}

然后,如果可以在同一个连接字符串上访问所有表,则只需要一个会话工厂

答案 2 :(得分:1)

您还可以按类型进行过滤。这是来自“绿色字段”AutoPersistenceModel的一行评论代码,我在同一个程序集中使用“棕色字段一”(即两个数据库)。但是我只需要过滤一种类型,所以我没有打算拆分传统的程序集。如果每个db有很多它们,那么按程序集拆分它们可能是最好的IMO。

如果FNH可以提供某种内置的多数据库支持,那将会很酷,但我不知道如何才能真正做到这一点;某种类型的SessionFactories字典可能,但每种情况都是如此独特。

HTH,
Berryl

    /// <summary>
    /// This would simply call <see cref="AutoMapHelpers.GetAutoMappingFilter"/> but we need to 
    /// exclude <see cref="LegacyProject"/> also for now.
    /// </summary>
    private static bool _getIncludedTypesFilter(Type t) {
        return _isNotLegacy(t) && AutoMapHelpers.GetAutoMappingFilter(t);
    }
    private static bool _isNotLegacy(Type t) { return !t.Equals(typeof(LegacyProject)); }

答案 3 :(得分:0)

虽然回复非常晚,但我建议你仔细阅读以下网址,其中有一些解决方案需要解决,因此你可以在答案中找到解决方案。 Here是您在url

的帮助下实施的答案的解决方案

通过我实现的解决方案,您现在只能实现数据库优先模型。 尝试在我提到的问题中避免使用GenerateSchema方法,因为它仍未实现,就像使用该方法一样,您将能够看到创建了相同表和关系的多个数据库。