2013-03-19 29 views
2

我有一個類層次結構,在概念上類似於這樣繼承:加入子類的映射的,抽象的中間階級

enter image description here

也就是說,有一個抽象基類(Relation)和一對夫婦派生類。在實踐中,CustomerSupplier共享很多代碼,所以我將共同性重構爲抽象類BusinessContact。現在實際的類層次結構是這樣的:

enter image description here

或者代碼:

public abstract class Relation 
{ 
    public virtual int Id { get; set; } 
} 

public class ContactPerson : Relation 
{ 
    public virtual string PhoneNumber { get; set; } 
} 

public abstract class BusinessContact : Relation 
{ 
    public virtual string Name { get; set; } 
} 

public class Customer : BusinessContact 
{ 
    public virtual string CustomerNumber { get; set; } 
} 

public class Supplier : BusinessContact 
{ 
    public virtual string SupplierNumber { get; set; } 
} 

我想這個層次結構映射到使用四個表(RelationContactPersonCustomerSupplier) NHibernate中的加入子類,使用映射代碼(ModelMapper)。我的映射是這樣的:

var mapper = new ModelMapper(); 

mapper.Class<Relation>(map => 
{ 
    map.Id(x => x.Id, id => id.Generator(Generators.Native)); 
}); 

mapper.JoinedSubclass<ContactPerson>(map => 
{ 
    map.Key(key => key.Column("Id")); 
    map.Property(x => x.PhoneNumber); 
}); 

mapper.JoinedSubclass<Customer>(map => 
{ 
    map.Key(key => key.Column("Id")); 
    map.Property(x => x.Name); 
    map.Property(x => x.CustomerNumber); 
}); 

mapper.JoinedSubclass<Supplier>(map => 
{ 
    map.Key(key => key.Column("Id")); 
    map.Property(x => x.Name); 
    map.Property(x => x.SupplierNumber); 
}); 

然而,當我嘗試將映射添加到配置我得到一個異常:

NHibernate.MappingException: Cannot extend unmapped class: BusinessContact 

我基本上明白爲什麼會這樣。所生成的映射如下所示:

<?xml version="1.0" encoding="utf-8"?> 
<hibernate-mapping xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema" namespace="JoinedSubClassMapping" assembly="JoinedSubClassMapping" xmlns="urn:nhib ernate-mapping-2.2"> 
    <class name="Relation" abstract="true"> 
    <id name="Id" type="Int32"> 
     <generator class="native" /> 
    </id> 
    </class> 
    <joined-subclass name="ContactPerson" extends="Relation"> 
    <key column="Id" /> 
    <property name="PhoneNumber" /> 
    </joined-subclass> 
    <joined-subclass name="Customer" extends="BusinessContact"> 
    <key column="Id" /> 
    <property name="CustomerNumber" /> 
    </joined-subclass> 
    <joined-subclass name="Supplier" extends="BusinessContact"> 
    <key column="Id" /> 
    <property name="SupplierNumber" /> 
    </joined-subclass> 
</hibernate-mapping> 

CustomerSupplier在其extends屬性定義BusinessContact,彷彿BusinessContact是在模型中「正常」的實體。由於BusinessContact沒有映射,所以這個失敗,或者當然。注意,「名稱」屬性(在BusinessContact定義沒有出現在映射或者

映射的樣子是這樣的:

<?xml version="1.0" encoding="utf-8" ?> 
<hibernate-mapping xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema" namespace="JoinedSubClassMapping" assembly="JoinedSubClassMapping" xmlns="urn:nhibernate-mapping-2.2"> 
    <class name="Relation" abstract="true"> 
    <id name="Id" type="Int32"> 
     <generator class="native" /> 
    </id> 
    </class> 
    <joined-subclass name="ContactPerson" extends="Relation"> 
    <key column="Id" /> 
    <property name="PhoneNumber" /> 
    </joined-subclass> 
    <joined-subclass name="Customer" extends="Relation"> 
    <key column="Id" /> 
    <property name="CustomerNumber" /> 
    <property name="Name" /> 
    </joined-subclass> 
    <joined-subclass name="Supplier" extends="Relation"> 
    <key column="Id" /> 
    <property name="SupplierNumber" /> 
    <property name="Name" /> 
    </joined-subclass> 
</hibernate-mapping> 

也就是說,讓SupplierCustomer擴展關係和包括(否則未映射)的所有映射屬性BusinessContact類。

我怎樣才能做到這一點?

回答

2

這裏是一個解決方案:

class MyInspector : ExplicitlyDeclaredModel { 
    public override bool IsEntity(Type type) { 
     if (type == typeof (BusinessContact)) 
      return false; 
     return base.IsEntity(type); 
    } 
} 

var mapper = new ModelMapper(new MyInspector()); 
+0

非常感謝,這是訣竅。直到現在我還不知道「IModelInspector」。我想我會創建一個屬性並讓模型檢查器查找它以使其可重用。 – 2013-03-20 22:04:44