(N)Hibernate从schema找到内容:Object< - AttributeValue - >属性

时间:2009-09-25 10:11:14

标签: c# java database nhibernate hibernate

我们有一个通用的数据库架构:

对象< - AttributeValue - >属性

我们可以说我们谈论房屋。房子可以有很多很多属性(门形,屋顶颜色等)。混凝土房屋的属性数量尚不清楚。

使用直接映射到对象:

  • House - 包含HouseAttributeValue对象的集合,
  • HouseAttributeValue - 包含Attribute对象及其字符串值
  • HouseAttribute - 包含属性名称

现在简单的按预期工作:

ICriteria criteria = this.Repository.CreateCriteria(typeof(House))
IList<House> searchResult = this.Repository.GetList<House>();

返回具有属性值集合(带有属性对象)的House。

我们需要找到特定的房子(有大窗户和玻璃门)并获得所有属性。

选择我想象的语句(不介意表现)并不神奇:

SELECT 
  this_.*, 
  att_val_fetch.*, 
  att_fetch.*
FROM House this_

INNER JOIN attribute_value att_val_fetch ON this_.versionedobjectid = att_val_fetch.versionedobjectid
INNER JOIN attribute att_fetch ON att_val_fetch.attributeid = att_fetch.attributeid

-- only for filter, no need to fetch
INNER JOIN attribute_value att_val_1 ON this_.versionedobjectid = att_val_1.versionedobjectid
INNER JOIN attribute att_1 ON att_val_1.attributeid = att_1.attributeid

INNER JOIN attribute_value att_val_2 ON this_.versionedobjectid = att_val_2.versionedobjectid
INNER JOIN attribute att_2 ON att_val_2.attributeid = att_2.attributeid

WHERE((att_1.attributename = 'window' AND att_val_1.valuestring IN('big')) 
 and (att_2.attributename = 'door' AND att_val_2.valuestring IN('glass')));

如何使用NHibernate(或Hibernate)完成此操作?很想在代码中看到没有直接SQL语句的解决方案,但实际上任何解决方案都是受欢迎的。

2 个答案:

答案 0 :(得分:1)

也许你需要一个HQL查询示例(QBE)。

答案 1 :(得分:0)

假设这个简单的定义

class House
{
    public int Id{get;set;}
    .
    .
    .
    public IList<AttributeValue> AttributeValues {get;set;} 
}

class AttributeName
{
    public int Id{get;set;}
    .
    .
    .
    public string Name{get;set;}    
}

class AttributeValue
{
    public int Id{get;set;}
    .
    .
    .
    public House House {get;set;}
    public AttributeName Attribute{get;set;}
    public string Value {get;set;}
}

和适当的相应映射,这个标准应该完成工作

ICriteria criteria = this.Repository.CreateCriteria(typeof(House))
criteria.CreateAlias("AttributeValues", "av");
criteria.SetFetchMode("av", FetchMode.Select);
criteria.Add(Expression.Eq("av.Attribute.Name", "door") && Expression.Eq("av.Value", "glass"));
criteria.Add(Expression.Eq("av.Attribute.Name", "window") && Expression.Eq("av.Value", "big"));
IList<House> houses = criteria.List<House>();
如果使用别名集合是正确的,或者需要完整的属性名称,

其中我现在不记得现在设置获取模式

criteria.SetFetchMode("AttributeValues", FetchMode.Select);