2012-05-14 49 views
0

當通過使用具有唯一約束的多對一映射一對一關係時,我得到一個異常「爲AccountDetail生成的null id」。NHibernate一對一:爲帳戶詳細信息生成的null id

這裏是我的SQL表:

Account(Id, Name) 
AccountDetail(AccountId, Remark) 

ACCOUNTID的初級和外鍵。

這裏是我的域模型(賬戶和AccountDetail):

public class Account 
{ 
    public virtual int Id { get; set; } 

    public virtual string Name { get; set; } 

    public virtual AccountDetail Detail { get; set; } 

    public Account() 
    { 
     Detail = new AccountDetail 
     { 
      Account = this 
     }; 
    } 
} 

public class AccountDetail 
{ 
    public virtual int AccountId { get; set; } 

    public virtual Account Account { get; set; } 

    public virtual string Remark { get; set; } 
} 

映射(代碼NHibenrate 3.3映射):

class AccountMap : ClassMapping<Account> 
{ 
    public AccountMap() 
    { 
     Table(typeof(Account).Name); 

     Id(c => c.Id, m => m.Generator(Generators.Native)); 

     Property(c => c.Name); 

     OneToOne(c => c.Detail, m => 
     { 
      m.Constrained(true); 
      m.Cascade(Cascade.All); 
      m.PropertyReference(typeof(AccountDetail).GetPropertyOrFieldMatchingName("Account")); 
     }); 
    } 
} 

class AccountDetailMap : ClassMapping<AccountDetail> 
{ 
    public AccountDetailMap() 
    { 
     Table(typeof(AccountDetail).Name); 

     Id(c => c.AccountId, m => 
     { 
      m.Column("AccountId"); 
      m.Generator(Generators.Foreign<AccountDetail>(x => x.Account)); 
     }); 

     Property(c => c.Remark); 

     ManyToOne(c => c.Account, m => 
     { 
      m.Column("AccountId"); 
      m.Unique(true); 
     }); 
    } 
} 

BTW:我可以刪除的AccountID AccountDetail中的屬性?也就是說,只使用Account屬性。在AccountDetail類中使用AccountId和Account屬性看起來並不那麼面向對象。

謝謝!

+0

你嘗試從映射移除的AccountID? – ivowiblo

+0

是的,但沒有AccountId,我不知道如何做Id圖。在NHibernate映射中需要Id映射。 –

回答

1

我不能說什麼其實是錯誤的,但我的工作一到一個關係比較,我想這個映射它:

class AccountMap : ClassMapping<Account> 
{ 
    public AccountMap() 
    { 
     Table(typeof(Account).Name); 

     // creates a auto-counter column "id" 
     Id(c => c.Id, m => m.Generator(Generators.Native)); 

     // doesn't require a column, one-to-one always means to couple primary keys. 
     OneToOne(c => c.Detail, m => 
     { 
      // don't know if this has any effect 
      m.Constrained(true); 

      // cascade should be fine 
      m.Cascade(Cascade.All); 
     }); 
    } 
} 

class AccountDetailMap : ClassMapping<AccountDetail> 
{ 
    public AccountDetailMap() 
    { 
     Id(c => c.AccountId, m => 
     { 
      // creates an id column called "AccountId" with the value from 
      // the Account property. 
      m.Column("AccountId"); 
      m.Generator(Generators.Foreign(x => x.Account)); 
     }); 

     // should be one-to-one because you don't use another foreign-key. 
     OneToOne(c => c.Account); 
    } 
} 
+0

但是,如果像這樣映射,我們無法做出延遲加載。 –

+0

爲什麼不呢?它也應該可以延遲加載...... –

+0

在一對一關聯中不支持延遲加載。請參閱:http://stackoverflow.com/questions/1796574/lazy-load-nhibernate-one-to-one。我想我現在得到答案。它需要將外鍵從子表移動到父表。也就是說,在賬戶表中添加一個AccountDetailId。但從數據庫設計師的角度來看,這看起來不太好。 –

相關問題