2010-01-26 76 views
1

我試圖獲得連貫NHibernate 1.0 RTM到地圖的用戶實體我,讓我有NHibernate的通過我的ASP.NET MVC應用程序中訪問用戶名和用戶名映射aspnet_Users表格內的一部分。如何使用功能NHibernate

我:

public class User 
{ 
    public virtual Guid UserId { get; protected set; } 
    public virtual string UserName { get; protected set; } 
} 

它代表只相關列aspnet_Users表格內映射。這是未被自動映射的唯一實體。這是我的映射:

public class UserMap : ClassMap<User> 
{ 
    public UserMap() 
    { 
     Id(x => x.UserId); 
     Map(x => x.UserName); 
     WithTable("aspnet_Users"); 
    } 
} 

其他一切正在使用約定自動映射。

這裏是我的PrimaryKeyConvention和TableNameConvention:

public class PrimaryKeyConvention : IIdConvention 
{ 
    public void Apply(IIdentityInstance instance) 
    { 
     instance.Column(instance.Property.ReflectedType.Name + "Id"); 
     instance.UnsavedValue(System.Guid.Empty.ToString()); 
     instance.GeneratedBy.GuidComb(); 
    } 
} 

public class TableNameConvention : IClassConvention 
{ 
    public void Apply(IClassInstance instance) 
    { 
     instance.Table(Inflector.Net.Inflector.Pluralize(instance.EntityType.Name)); 
    } 
} 

映射過程執行類映射代碼(所有自動映射之前其自帶)之後出現故障,其次是TableNameConvention代碼,其次是PrimaryKeyConvention代碼。 PrimaryKeyConvention中的失敗是因爲instance.Property爲null。我想如果(instance.Property!= NULL)做一但 與早期終止映射過程「所需屬性‘類’丟失」的錯誤。我在TableNameConvention中也有一個if(instance.EntityType!= typeof(User)),但是當它沒有任何區別時就取出了。

這是怎麼回事?首先,爲什麼AutoMapping進程調用ClassMap的約定?其次,爲什麼PrimaryKenConvention獲得一個實例.Property == null?我怎樣才能使這個工作,以便映射過程繼續前進,並使用AutoMapping +約定映射我的其他實體?

注意,我有這一切工作了幾個月重構之前的早期版本FNH的下1.0 RTM。

回答

1

我已經想出了這個答案。

public UserMap() 
{ 
    Id(x => x.UserId); 
    Map(x => x.UserName); 
    Table("aspnet_Users"); 
} 

public class PrimaryKeyConvention : IIdConvention 
{ 
    public void Apply(IIdentityInstance instance) 
    { 
     instance.Column(instance.EntityType.Name + "Id"); 
     instance.UnsavedValue(System.Guid.Empty.ToString()); 
     instance.GeneratedBy.GuidComb(); 
    } 
} 

public class TableNameConvention : IClassConvention 
{ 
    public void Apply(IClassInstance instance) 
    { 
     instance.Table(Inflector.Net.Inflector.Pluralize(instance.EntityType.Name)); 
    } 
} 

請注意,PrimaryKeyConvention使用instance.EntityName而不是該實例.Property設置列名稱。後者對於UserMap是空的,所以它會崩潰。

這種方法比使用條件語句上(NULL!= instance.Property),並保持instance.Property.ReflectedType.Name線更好,但兩者的工作。如果您選擇走這條路線,您必須明確設置UserMap中的列名稱:

public UserMap() 
{ 
    Id(x => x.UserId).Column("UserId") 
        .GeneratedBy.Assigned(); 
    Map(x => x.UserName).Column("UserName"); 
    Table("aspnet_Users"); 
} 
0

我不使用自動映射自己,但我認爲你需要通過實施IAutoMappingOverride映射用戶。例如:

public class UserMap : IAutoMappingOverride<User> 
{ 
    public void Override(AutoMapping<User> mapping) 
    { 
     mapping.Id(x => x.UserId); 
     mapping.Map(x => x.UserName); 
     mapping.WithTable("aspnet_Users"); 
    } 
} 
+0

嗨傑米。覆蓋僅適用於由automapper將被映射爲實體的對象。我使用一個名爲Entity的基礎對象來封裝Id,CreatedDate等,並且所有實體都從它繼承。然而,我的用戶對象不繼承任何東西,因爲它不符合實體的需求看如何設計由aspnet_Users表格內決定。設置AutoMap時使用.ignoreBase 。因此,我無法重寫您推薦的方式,因爲用戶從未被映射到開始。 – 2010-01-26 20:16:38