2012-08-09 51 views
1

我无法弄清楚如何配置我的mappins用流利:(功能NHibernate HasOne + ReferencesAny

这里是我的情况: 我有一个元素对象,(理论上)应该有一个一对一与搜索对象关系。然而,所述搜索对象应具有一对多的关系与自身。 换句话说,Element对象可以具有至多1个搜索对象(也可以没有),和一个搜索对象,还有其他的搜索对象的集合。

我开始用下面的映射。他们建立正确的DB模式,我预计可以节省罚款。检索数据时出现的问题开始...

public class ElementMap : ClassMap<Element> 
{ 
    public ElementMap() 
    { 
     Schema("dbo"); 
     Table("Element"); 
     LazyLoad(); 
     Id(x => x.Id) 
      .Column("Id") 
      .CustomType("Int32") 
      .Access.Property() 
      .CustomSqlType("int") 
      .Not.Nullable() 
      .UnsavedValue(0) 
      .GeneratedBy.Identity(); 
     HasOne(x => x.Search) 
      .Cascade.All() 
      .Not.LazyLoad(); 
    } 
} 

public class SearchMap : ClassMap<Search> 
{ 
    public SearchMap() 
    { 
     Schema("dbo"); 
     Table("Search"); 
     LazyLoad(); 
     Id(x => x.Id) 
      .Column("Id") 
      .CustomType("Int32") 
      .Access.Property() 
      .CustomSqlType("int") 
      .Not.Nullable() 
      .UnsavedValue(0) 
      .GeneratedBy.Identity(); 
     ReferencesAny(x => x.Parent) 
      .IdentityType<int>() 
      .MetaType<string>() 
      .EntityTypeColumn("ParentType") 
      .EntityIdentifierColumn("ParentId") 
      .AddMetaValue<Element>("E") 
      .AddMetaValue<Search>("S"); 
     HasMany(x => x.Searches) 
      .Table("Search") 
      .KeyColumn("ParentId") 
      .Where("ParentType = 'S'") 
      .Cascade.All() 
      .LazyLoad(); 
    } 
} 

所以正如所说,模型看起来正确,元素表包含ID 1列,搜索表中包含一个ID列,一ParentType的列设置为“E”如果父元素是Element对象,并且如果父元素是Search对象,则设置为“S”,最后是引用父元素ID的ParentId。

不知怎的,这似乎是罚款,是有道理的(至少对我来说:P)。

下面是在数据库中的数据的一个样本:

Element table 
Id 
----------- 
1 
2 

Search table 
Id   ParentType ParentId 
----------- ---------- ----------- 
1   E   1 
2   S   1 
3   E   2 
4   S   3 
5   S   3 

所以我在这里的第一个元素对象包含包含1个搜寻对象, 和第二个元素对象包含包含2个搜索对象的搜索对象搜索对象。

现在的问题是,当我检索数据,第一个元素对象是正确的,但第二个一个不是。其搜索对象ID'd 2,在那里真的应该是3(第二搜索对象whoses父的ID在数据库中标记为E)。

我的猜测是,我应该以某种方式为Element对象映射添加一个.Where(“ParentType ='E'”),就像我为搜索对象所做的那样,但HasOne上没有.Where()方法()方法(因为它通常没有意义)。所以我真的不知道如何指定它:(

我希望这是清楚的问题总是很难解释:) 任何帮助将不胜感激,因为这是一个非常重要的项目我:(

谢谢大家!

勒布:)

+0

从我所了解的HasOne应该用于真正的一对一映射,这不是我所拥有的,但是,使用HasMany需要一个集合作为参数...是否有其他选择? – Seb 2012-08-10 07:28:19

回答

1

HasOne不考虑ReferenceAny的任何部分,因此它不能在这里使用的。我所看到的唯一选项是将私人搜索地图与相应的地图ParentType = 'E'进行映射,并将其转换为属性Search中的参考。

+0

是的Firo,这是我所做的,因为我还没有找到任何其他的工作... 无论如何感谢您的答案! :) – Seb 2012-08-16 05:50:28