【问题标题】:NHibernate Mapping: Save hierarchy to single table without discriminatorNHibernate 映射:将层次结构保存到没有鉴别器的单个表
【发布时间】:2010-12-17 13:09:43
【问题描述】:

我有一个非常可扩展和模块化的应用程序。我想从其他程序集中扩展映射的实体。然而,我仍然需要对基类进行操作。

例子:

程序集 A 中的父类映射:

    public class PersonMap : ClassMap<Person> 
    {
        public PersonMap()
        {
            Table("Persons");

            Id(x => x.Id).GeneratedBy.Assigned();
        }
}

程序集 B 中的子类映射:

public class EmployeeMap : SubclassMap<Employee>
{
    public EmployeeMap()
    {
        Table("Persons");
        Extends(typeof(Person));

        KeyColumn("Id");

        LazyLoad();

        HasMany<Assignments>(x => x.Assignments).KeyColumn("Id").Inverse().Cascade.AllDeleteOrphan().LazyLoad().NotFound.Ignore();
    }
}

现在,每当我在程序集 A 的某些代码中创建一个 Person 时,NHibernate 都会将它保存为 Employee。每当我保存一个 Person 并尝试在程序集 A 中刷新它时,由于代理而导致类转换异常。程序集 A 不能依赖于程序集 B。

我需要在程序集A的所有方法中对父类进行操作。子类只在其他程序集中使用。

我怎样才能映射这样的东西?我如何告诉 NHibernate 将其保存为父类?我使用 SaveOrUpdate 来持久化实体;如何正确扩展实体并将它们保存到同一个表中而没有区别? NHibernate 不能按对象类型区分吗?有解决方法吗?

我不想指定手动代理,因为我必须为每个实体创建一个代理!由于依赖问题,我无法使用访问者模式。

我需要一种方法来扩展不同程序集中的映射实体而不会出现此类问题!数据库是遗留的,我无法更改它。您将如何解决这个问题?

【问题讨论】:

    标签: c# .net nhibernate orm


    【解决方案1】:

    您在没有鉴别器的情况下将层次结构映射到单个表的目标提出了一个难题。数据层中一定有一些东西可以给 DAL 一个线索,即特定记录是 Employee 而不是 Person。由于您没有在 Persons 表上为 Employee 映射任何其他字段,也没有提供鉴别器,因此 Persons 表的任何单个记录都无法区分 Persons 和更多派生的Employees。

    您能否提供用于检索人员记录的代码?根据我的经验,NHibernate 查询几乎总是需要域类型来补充。可能在这种情况下,NHibernate 试图创建它所知道的最衍生类型的对象,并且因为它无法区分基本 Person 和更衍生的 Employee 之间的区别,所以所有 Person 都是Employees。您可以试试 Linq,它强制强类型对象水合,而不是 HQL 或其他强引用较少的查询。

    【讨论】:

    • 那么,如何将新关系映射到现有实体?
    • 顺便说一句:我使用 LinQ To NHibernate 来检索记录!我得到了一个 Person,但是当我创建一个新的并保存它时,它是一个 ControlliogPerson 代理,它破坏了多态性!
    【解决方案2】:

    通过在同一个表上使用 HasOne 映射而不使用子类来解决它。这不会产生理想的代码,但完全没有问题。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2013-05-20
      • 2021-11-05
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多