基于子类接口的NHibernate代理的意外行为

时间:2015-10-15 23:33:39

标签: c# nhibernate proxy fluent-nhibernate nhibernate-mapping

在尝试将我的实体接口作为“代理”时,我发现了实体代理的奇怪行为。

我使用了以下模型

/* interfaces declaration */
public interface IBaseUser {}
public interface ITeacher : IBaseUser {}
public interface IStudent : IBaseUser {}

public interface IProfile {
  public IBaseUser User {get; set;};
}

/* entities implementation */    
public abstract class AbstractUser : IBaseUser {}
public class Teacher : AbstractUser, ITeacher {}
public class Student : AbstractUser, IStudent {}

public class Profile : IProfile {
  //profile may point to ether Student or Teacher
  public virtual IBaseUser User {get; set;}
}

这些实体通过NFluent以编程方式进行映射(小例子如下所示)

/* abstract class mapping declaration example */
class AbstractUserMap : ClassMap<AbstractUser>
{
  public AbstractUserMap()
  {
    //force NHibernate to use interface based proxy 
    Proxy<IBaseUser>();

    DiscriminateSubClassesOnColumn("type").Not.Nullable();
  }
}

/* subclass mapping declaration example */
class TeacherMap : SubclassMap<Teacher>
{
  public TeacherMap()
  {
    //force NHibernate to use interface based proxy 
    Proxy<ITeacher>();

    DiscriminatorValue("teacher");
  }
}

拥有这些模型我正在尝试按ID

获取个人资料
var profile = Session.Get<IProfile>(ID)

在结果中我希望NHibernate在会话缓存中创建2个对象:

[
  new Profile {Id = ID, ...},
  new IBaseUserProxy {Id = ID1, ...} //<< due to lazy nature of the referenced entity
] 

实际上到目前为止一切进展顺利。

但是当我试图检查如何构造IBaseUserProxy时,我可以看到代理继承了以下接口:

  • NHibernate.Proxy.INHibernateProxy
  • NHibernate.Proxy.DynamicProxy.Proxy
  • System.Runtime.Serialization.ISerializable
  • IBaseUser
  • ITeacher
  • IStudent

最后两项对我来说完全不清楚。除了ITeacher之外,为什么NHibernate使用IStudentIBaseUser接口?我知道在构建时确切的代理类型是未知的。但仅仅从最近的接口 - IBaseUser继承这个代理是不够的呢?

否则,接口的这种“不可能的复合物”会导致以下问题:

profile.User is IBaseUser //true, OK
profile.User is ITeacher  //true, OK
profile.User is IStudent //true BUT isn't a true, threw an exception of type 'System.Reflection.TargetException' when you access any property specific to student after casting 

0 个答案:

没有答案